aboutsummaryrefslogtreecommitdiffstats
path: root/Library/Contributions/cmds
diff options
context:
space:
mode:
authorMike McQuaid2012-03-18 15:33:21 +1300
committerMike McQuaid2012-03-18 15:34:41 +1300
commitb27b761931b987b9dd8a9fc080bbf35270af7cca (patch)
treefc4adbbfcf47fa8eba4f011630037f461cc5162c /Library/Contributions/cmds
parentd2ad0d02326634d5ff9b92899b60190271e45786 (diff)
downloadhomebrew-b27b761931b987b9dd8a9fc080bbf35270af7cca.tar.bz2
Rename external commands directory from examples.
Fixes #10829.
Diffstat (limited to 'Library/Contributions/cmds')
-rwxr-xr-xLibrary/Contributions/cmds/brew-beer.rb179
-rwxr-xr-xLibrary/Contributions/cmds/brew-dirty.rb7
-rwxr-xr-xLibrary/Contributions/cmds/brew-graph311
-rwxr-xr-xLibrary/Contributions/cmds/brew-grep3
-rwxr-xr-xLibrary/Contributions/cmds/brew-leaves.rb27
-rwxr-xr-xLibrary/Contributions/cmds/brew-linkapps.rb31
-rwxr-xr-xLibrary/Contributions/cmds/brew-man51
-rwxr-xr-xLibrary/Contributions/cmds/brew-mirror-check.rb55
-rwxr-xr-xLibrary/Contributions/cmds/brew-missing.rb37
-rwxr-xr-xLibrary/Contributions/cmds/brew-pull.rb78
-rwxr-xr-xLibrary/Contributions/cmds/brew-readall.rb14
-rwxr-xr-xLibrary/Contributions/cmds/brew-server208
-rwxr-xr-xLibrary/Contributions/cmds/brew-switch.rb40
-rwxr-xr-xLibrary/Contributions/cmds/brew-unpack.rb93
-rwxr-xr-xLibrary/Contributions/cmds/brew-which.rb49
15 files changed, 1183 insertions, 0 deletions
diff --git a/Library/Contributions/cmds/brew-beer.rb b/Library/Contributions/cmds/brew-beer.rb
new file mode 100755
index 000000000..4ce1f9b9d
--- /dev/null
+++ b/Library/Contributions/cmds/brew-beer.rb
@@ -0,0 +1,179 @@
+HOMEBREW_BEER = <<-EOS
+Recipe stolen from: http://allrecipes.com/howto/beer-brewing-for-beginners/
+
+**The Key Ingredients**
+Before beginning the brewing process, you must first understand the four key
+ingredients necessary to brew a batch of beer: water, fermentable sugar, hops,
+and yeast. Each ingredient is integral to the recipe and must be cooked in a
+certain way to yield a successful batch of brew. Understanding their basic
+qualities and how each ingredient is meant to react with the others is an
+important aspect of beer brewing.
+
+Water: Water is the primary ingredient in beer, so it is very important the
+water tastes good. If the tap water at your house tastes good to you, then it
+is fine to use for beer brewing. If you don't like the way your tap water
+tastes, then you can use bottled or distilled water instead. If you use tap
+water, boil it first to evaporate the chlorine and other chemicals that may
+interfere with the brewing process. Let the water cool before using.
+
+Fermented Sugar: Malted barley is the ingredient commonly used to fill the
+sugar quota in a home brew recipe. Some brewers will substitute a percentage
+of corn, rice, wheat, or other grains to add a lighter flavor to the beer.
+Beginning brewers should purchase a ready-to-use form of malted barley called
+malt syrup or malt extract, rather than attempting to malt the grain from
+scratch, as it is a very complex and touchy process. Using a malt extract will
+guarantee the fermented sugar is prepared in just the right manner and will
+act as it needs to throughout the beer brewing process.
+
+Hops: Hops are cone-like flowers found on a hop vine. They lend the bitter
+flavor to beer that balances out sweetness. Hops also inhibit spoilage and
+help keep the "head" (the frothy top when a beer is poured) around longer.
+
+Yeast: First things first: Do not use bread yeast for beer brewing! Beer yeast
+is cultivated especially for use in brewing. There are two broad categories of
+beer yeast: ale and lager. Ale yeasts are top-fermenting, which means they
+tend to hang out at the top of the carboy while fermenting and rest at the
+bottom after the majority of fermenting has occurred. Ale yeasts will not
+actively ferment below 50 degrees F (20 degrees C). Lager yeasts are
+bottom-fermenters and are best used at a temperature ranging from 55 degrees F
+(25 degrees C) down to 32 degrees F (0 degrees C). As their names suggest, the
+type of yeast used plays an important part in influencing the type of beer
+that will be made. Do not rely on the yeast to define the beer, however, as
+all of the ingredients play a part in the taste and type of beer you will
+create.
+
+**Ready to Brew?**
+We've opted to use a simple ale recipe to guide you through the process. The
+first cooking step in brewing is to make the wort, a soupy mixture of malt and
+sugar that is boiled before fermentation. Malt and sugar form the perfect food
+for yeast to grown in--thus making the all-important process of fermentation
+possible. All of the ingredients for beer-making can be found at your local
+brew supply store, or at any number of beer outfitters. Once you've got all
+the necessary equipment and ingredients, you're ready to begin the beer-making
+process by properly sanitizing your equipment, making and cooling the wort,
+fermenting the wort, and bottling your brew.
+
+Ingredients:
+
+1.5 gallons water
+6 pounds canned pre-hopped light malt syrup
+1 ounce hop pellets (choose your flavor)
+Ice poured into a water bath (do not use store-bought ice)
+3 gallons cool water
+2 (7-gram) packets ale yeast
+1 cup warm water (about 90 degrees F or 35 degrees C)
+3/4 cup liquid corn syrup (or 4 ounces dry corn syrup)
+1 (4-ounce) container iodine solution
+1 tablespoon bleach
+
+A bottle of household bleach or an iodine solution that can be bought at your
+local home brew shop to sanitize all of your materials or use will be
+necessary. (Make a bleach disinfecting solution with 1 tablespoon bleach to 1
+gallon water.) Be sure to rinse the equipment well with boiling water before
+using it.
+
+Part I: Make and Cool the Wort
+
+Sanitize the pot, stirring spoon and fermenter with the sanitizing solution.
+Rinse everything in boiling water.
+
+Bring 1.5 gallons of water to a boil. When the water begins to boil, remove it
+from the heat and stir in the malt syrup until it dissolves. Do not allow any
+syrup to stick to the bottom or sides of the pot, as it will burn and taste
+awful. Return the pot to the heat and bring the mixture to a boil for 50
+minutes, stir frequently and watch constantly to prevent boil-overs. If the
+mixture threatens to boil over, reduce the heat.
+
+After 50 minutes have elapsed, stir in the hop pellets. Hops will create a
+foam on the top of the liquid--so if the pot is very full, the hops may cause
+a boil-over. You want to avoid this at all costs by lowering the heat or
+spraying the foam down with a water bottle (sanitized, of course). Let the
+hops cook for 10 to 20 minutes.
+
+While the wort is being made, prep the yeast by placing 1 packet of yeast in 1
+cup of warm water (90 degrees F or 35 degrees C; stir and cover for 10
+minutes. If the yeast does not react (form foam), discard the yeast solution
+and try again with the second yeast packet.
+
+At about the time hops are added to the wort, you should prepare an ice-cold
+water bath in either a large sink or tub to quick-cool the wort. Once the wort
+is finished cooking, float the pot in the water bath. Stir the wort while it
+is sitting in the bath so that the maximum amount of wort reaches the pot's
+sides where it can cool quickly. If the water bath heats up, add more ice to
+keep the water bath cold. It should take approximately 20 minutes to cool the
+wort to approximately 80 degrees F (27 degrees C).
+
+
+Part II: Ferment
+
+Pour the 3 gallons cool water into your sanitized carboy. Funnel in the warm
+wort. Sprinkle the prepared yeast into the carboy. Cover the carboy's mouth
+with plastic wrap and cap it with a lid. Holding your hand tight over the lid,
+shake the bottle up and down to distribute the yeast. Remove the plastic wrap,
+wipe any wort around the carboy's mouth off and place the fermentation lock
+(with a little water added into its top) on.
+
+Store the carboy in a cool (60 to 75 degrees F or 15 to 24 degrees C) safe
+place without direct sunlight where you will be able to easily clean up or
+drain any foam that escapes. A bathtub is an excellent place to store your
+fermenter if there are no windows in the room. If the temperature in the
+storage room drops and bubbling in the carboy's airlock stops, move the carboy
+to a warmer room. The fermenting will resume. Fermentation should begin within
+24 hours. A clear sign of fermentation is the production of foam and air
+bubbles in the fermentation lock.
+
+When fermentation begins, it produces a slow trickle of bubbles that will
+increase in amount for a few days, and then reduce to a slow trickle again.
+Let the beer ferment for approximately 14 days when the primary fermentation
+has taken place. If the fermenting process pops the fermentation lock out of
+the carboy, re-sanitize it and place it back into the carboy.
+
+
+Part III: Bottle
+
+Sanitize all of your bottles by soaking them in the sanitizing solution (make
+sure to hold them under the solution so the water gets inside of the bottles)
+for 1 hour. Rinse the bottles with boiling water. Also sanitize a small
+cooking pot, bottling bucket, siphon and racking cane. Follow the instructions
+that came with the bottle caps to sanitize them. Let everything air dry.
+Combine the corn syrup and 1 cup water in the sanitized cooking pot. Let boil
+10 minutes. Pour mixture into the bottling bucket. Be careful not to add too
+much corn syrup to the bottling bucket, because this will over-carbonate the
+beer and cause bottles to explode! Place the fermenter full of beer on the
+kitchen counter and the bottling bucket on the ground below it. Attach the
+racking cane to the siphon. Prepare the siphon by filling it with tap water.
+Pinch both ends of the siphon to prevent the water from running out. Place one
+end of the racking cane and siphon into the iodine solution and one end into
+an empty jar. When the solution has run into the siphon and expelled all of
+the water into the jar, pinch both ends and let the iodine sit in the siphon
+for 5 minutes to re-sanitize the siphon. (Resist the temptation to blow into
+the siphon with your mouth to encourage the flow of iodine solution.)
+
+Place one end of the sanitized siphon into the fermenter and the other end
+into the jar; once the beer has begun flowing through the siphon, transfer its
+end to the bottling bucket. Monitor the speed that the beer transfers into the
+bottling bucket by pinching and releasing the siphon with your fingers (or use
+a specialty clamp). The beer should not splash into the bucket; it should
+gently rush into it. Once all of the beer has been siphoned into the bucket,
+cover it (with a sanitized cover ) and wait 30 minutes for the sediment to
+settle at the bottom of the bucket.
+
+Place the bottling bucket on the counter, attach the siphon and run the other
+end of the siphon into a bottle. Fill each bottle with beer to 3/4 inch from
+the top of the bottle. Cap each bottle with the bottle-capper. Check and
+double-check that the caps are secure. Sure Signs of Infection:
+
+Keep your eyes peeled for strands of slime in the beer and a milky layer at
+the top and/or residue bumps clinging to the air space in the bottleneck. If
+the beer has strands, it most likely has a lacto infection and should be
+discarded. The milky layer is a sign of a micro-derm infection; this beer
+should also be discarded.
+
+Age the bottles at room temperature for up to two months, but for at least two
+weeks, before cracking one open, proposing a toast to yourself and impressing
+your friends! Ready to expand your brewing prowess?
+
+Thanks for brewin'
+EOS
+
+puts HOMEBREW_BEER
diff --git a/Library/Contributions/cmds/brew-dirty.rb b/Library/Contributions/cmds/brew-dirty.rb
new file mode 100755
index 000000000..e22ad75c6
--- /dev/null
+++ b/Library/Contributions/cmds/brew-dirty.rb
@@ -0,0 +1,7 @@
+# See: http://github.com/mxcl/homebrew/issues/issue/1359
+
+to_list = HOMEBREW_CELLAR.children.select { |pn| pn.directory? }
+to_list.each do |d|
+ versions = d.children.select { |pn| pn.directory? }.collect { |pn| pn.basename.to_s }
+ puts "#{d.basename} (#{versions.join(', ')})" if versions.size > 1
+end
diff --git a/Library/Contributions/cmds/brew-graph b/Library/Contributions/cmds/brew-graph
new file mode 100755
index 000000000..27c80af83
--- /dev/null
+++ b/Library/Contributions/cmds/brew-graph
@@ -0,0 +1,311 @@
+#!/usr/bin/env python
+"""
+$ brew install graphviz
+$ brew graph | dot -Tsvg -ohomebrew.svg
+$ open homebrew.svg
+"""
+from __future__ import with_statement
+
+from contextlib import contextmanager
+import re
+from subprocess import Popen, PIPE
+import sys
+
+
+def run(command, print_command=False):
+ "Run a command, returning the exit code and output."
+ if print_command: print command
+ p = Popen(command, stdout=PIPE)
+ output, errput = p.communicate()
+ return p.returncode, output
+
+
+def _quote_id(id):
+ return '"' + id.replace('"', '\"') + '"'
+
+
+def format_attribs(attrib):
+ if len(attrib) == 0:
+ return ''
+
+ values = ['%s="%s"' % (k, attrib[k]) for k in attrib]
+ return '[' + ','.join(values) + ']'
+
+
+class Output(object):
+ def __init__(self, fd=sys.stdout, tabstyle=" "):
+ self.fd = fd
+ self.tabstyle = tabstyle
+ self.tablevel = 0
+
+ def close(self):
+ self.fd = None
+
+ def out(self, s):
+ self.tabout()
+ self.fd.write(s)
+
+ def outln(self, s=None):
+ if s is not None:
+ self.tabout()
+ self.fd.write(s)
+ self.fd.write('\n')
+
+ @contextmanager
+ def indented(self):
+ self.indent()
+ yield self
+ self.dedent()
+
+ def indent(self):
+ self.tablevel += 1
+
+ def dedent(self):
+ if self.tablevel == 0:
+ raise Exception('No existing indent level.')
+ self.tablevel -= 1
+
+ def tabout(self):
+ if self.tablevel:
+ self.fd.write(self.tabstyle * self.tablevel)
+
+
+class NodeContainer(object):
+ def __init__(self):
+ self.nodes = list()
+ self.node_defaults = dict()
+ # Stack of node attribs
+ self._node_styles = list()
+
+ def _node_style(self):
+ if (len(self._node_styles) > 0):
+ return self._node_styles[-1]
+ else:
+ return dict()
+
+ def _push_node_style(self, attrib):
+ self._node_styles.append(attrib)
+
+ def _pop_node_style(self):
+ return self._node_styles.pop()
+
+ @contextmanager
+ def node_styles(self, attrib):
+ self._push_node_style(attrib)
+ yield
+ self._pop_node_style()
+
+ def node(self, nodeid, label, attrib=None):
+ _attrib = dict(self._node_style())
+ if attrib is not None:
+ _attrib.update(attrib)
+
+ n = Node(nodeid, label, _attrib)
+ self.nodes.append(n)
+ return n
+
+ def nodes_to_dot(self, out):
+ if len(self.node_defaults) > 0:
+ out.outln("node " + format_attribs(self.node_defaults) + ";")
+
+ if len(self.nodes) == 0:
+ return
+
+ id_width = max([len(_quote_id(n.id)) for n in self.nodes])
+ for node in self.nodes:
+ node.to_dot(out, id_width)
+
+
+class Node(object):
+ def __init__(self, nodeid, label, attrib=None):
+ self.id = nodeid
+ self.label = label
+ self.attrib = attrib if attrib is not None else dict()
+
+ def as_dot(self, id_width=1):
+ _attribs = dict(self.attrib)
+ _attribs['label'] = self.label
+
+ return '%-*s %s' % (id_width, _quote_id(self.id), format_attribs(_attribs))
+
+
+ def to_dot(self, out, id_width=1):
+ out.outln(self.as_dot(id_width))
+
+
+class ClusterContainer(object):
+ def __init__(self):
+ self.clusters = list()
+
+ def cluster(self, clusterid, label, attrib=None):
+ c = Cluster(clusterid, label, self, attrib)
+ self.clusters.append(c)
+ return c
+
+
+class Cluster(NodeContainer, ClusterContainer):
+ def __init__(self, clusterid, label, parentcluster=None, attrib=None):
+ NodeContainer.__init__(self)
+ ClusterContainer.__init__(self)
+
+ self.id = clusterid
+ self.label = label
+ self.attrib = attrib if attrib is not None else dict()
+ self.parentcluster = parentcluster
+
+ def cluster_id(self):
+ return _quote_id("cluster_" + self.id)
+
+ def to_dot(self, out):
+ out.outln("subgraph %s {" % self.cluster_id())
+ with out.indented():
+ out.outln('label = "%s"' % self.label)
+ for k in self.attrib:
+ out.outln('%s = "%s"' % (k, self.attrib[k]))
+
+ for cluster in self.clusters:
+ cluster.to_dot(out)
+
+ self.nodes_to_dot(out)
+ out.outln("}")
+
+
+class Edge(object):
+ def __init__(self, source, target, attrib=None):
+ if attrib is None:
+ attrib = dict()
+
+ self.source = source
+ self.target = target
+ self.attrib = attrib
+
+ def to_dot(self, out):
+ out.outln(self.as_dot())
+
+ def as_dot(self):
+ return " ".join((_quote_id(self.source), "->", _quote_id(self.target), format_attribs(self.attrib)))
+
+
+class EdgeContainer(object):
+ def __init__(self):
+ self.edges = list()
+ self.edge_defaults = dict()
+ # Stack of edge attribs
+ self._edge_styles = list()
+
+ def _edge_style(self):
+ if (len(self._edge_styles) > 0):
+ return self._edge_styles[-1]
+ else:
+ return dict()
+
+ def _push_edge_style(self, attrib):
+ self._edge_styles.append(attrib)
+
+ def _pop_edge_style(self):
+ return self._edge_styles.pop()
+
+ @contextmanager
+ def edge_styles(self, attrib):
+ self._push_edge_style(attrib)
+ yield
+ self._pop_edge_style()
+
+ def link(self, source, target, attrib=None):
+ _attrib = dict(self._edge_style())
+ if attrib is not None:
+ _attrib.update(attrib)
+
+ e = Edge(source, target, _attrib)
+ self.edges.append(e)
+ return e
+
+ def edges_to_dot(self, out):
+ if len(self.edge_defaults) > 0:
+ out.outln("edge " + format_attribs(self.edge_defaults) + ";")
+
+ if len(self.edges) == 0:
+ return
+
+ for edge in self.edges:
+ edge.to_dot(out)
+
+
+class Graph(NodeContainer, EdgeContainer, ClusterContainer):
+ """
+ Contains the nodes, edges, and subgraph definitions for a graph to be
+ turned into a Graphviz DOT file.
+ """
+
+ def __init__(self, label=None, attrib=None):
+ NodeContainer.__init__(self)
+ EdgeContainer.__init__(self)
+ ClusterContainer.__init__(self)
+
+ self.label = label if label is not None else "Default Label"
+ self.attrib = attrib if attrib is not None else dict()
+
+ def dot(self, fd=sys.stdout):
+ try:
+ self.o = Output(fd)
+ self._dot()
+ finally:
+ self.o.close()
+
+ def _dot(self):
+ self.o.outln("digraph G {")
+
+ with self.o.indented():
+ self.o.outln('label = "%s"' % self.label)
+ for k in self.attrib:
+ self.o.outln('%s = "%s"' % (k, self.attrib[k]))
+
+ self.nodes_to_dot(self.o)
+
+ for cluster in self.clusters:
+ self.o.outln()
+ cluster.to_dot(self.o)
+
+ self.o.outln()
+ self.edges_to_dot(self.o)
+
+ self.o.outln("}")
+
+
+def main():
+ cmd = ["brew", "deps"]
+ cmd.extend(sys.argv[1:] or ["--all"])
+ code, output = run(cmd)
+ output = output.strip()
+ depgraph = list()
+
+ for f in output.split("\n"):
+ stuff = f.split(":",2)
+ name = stuff[0]
+ deps = stuff[1].strip()
+ if not deps:
+ deps = list()
+ else:
+ deps = deps.split(" ")
+ depgraph.append((name, deps))
+
+ hb = Graph("Homebrew Dependencies", attrib={'labelloc':'b', 'rankdir':'LR', 'ranksep':'5'})
+
+ used = set()
+ for f in depgraph:
+ for d in f[1]:
+ used.add(f[0])
+ used.add(d)
+
+ for f in depgraph:
+ if f[0] not in used:
+ continue
+ n = hb.node(f[0], f[0])
+ for d in f[1]:
+ hb.link(d, f[0])
+
+ hb.dot()
+
+
+if __name__ == "__main__":
+ main()
diff --git a/Library/Contributions/cmds/brew-grep b/Library/Contributions/cmds/brew-grep
new file mode 100755
index 000000000..027f97c4c
--- /dev/null
+++ b/Library/Contributions/cmds/brew-grep
@@ -0,0 +1,3 @@
+#!/bin/bash
+
+grep $@ $HOMEBREW_REPOSITORY/Library/Formula/*
diff --git a/Library/Contributions/cmds/brew-leaves.rb b/Library/Contributions/cmds/brew-leaves.rb
new file mode 100755
index 000000000..d24709229
--- /dev/null
+++ b/Library/Contributions/cmds/brew-leaves.rb
@@ -0,0 +1,27 @@
+# Outputs formulas that are installed but are not a dependency for
+# any other installed formula.
+# See: http://github.com/mxcl/homebrew/issues/issue/1438
+
+require 'formula'
+
+def get_used_by
+ used_by = {}
+ Formula.all.each do |f|
+ next if f.deps == nil
+
+ f.deps.each do |dep|
+ _deps = used_by[dep] || []
+ _deps << f.name unless _deps.include? f.name
+ used_by[dep] = _deps
+ end
+ end
+
+ return used_by
+end
+
+deps_graph = get_used_by()
+installed = HOMEBREW_CELLAR.children.select { |pn| pn.directory? }.collect { |pn| pn.basename.to_s }
+installed.each do |name|
+ deps = deps_graph[name] || []
+ puts name unless deps.any? { |dep| installed.include? dep }
+end
diff --git a/Library/Contributions/cmds/brew-linkapps.rb b/Library/Contributions/cmds/brew-linkapps.rb
new file mode 100755
index 000000000..5a36bb4d1
--- /dev/null
+++ b/Library/Contributions/cmds/brew-linkapps.rb
@@ -0,0 +1,31 @@
+# Links any Applications (.app) found in installed prefixes to ~/Applications
+require "formula"
+
+HOME_APPS = File.expand_path("~/Applications")
+
+unless File.exist? HOME_APPS
+ opoo "#{HOME_APPS} does not exist, stopping."
+ puts "Run `mkdir ~/Applications` first."
+ exit 1
+end
+
+HOMEBREW_CELLAR.subdirs.each do |keg|
+ next unless keg.subdirs
+ name = keg.basename.to_s
+
+ if ((f = Formula.factory(name)).installed? rescue false)
+ Dir["#{f.installed_prefix}/*.app", "#{f.installed_prefix}/bin/*.app", "#{f.installed_prefix}/libexec/*.app"].each do |p|
+ puts "Linking #{p}"
+ appname = File.basename(p)
+ target = HOME_APPS+"/"+appname
+ if File.exist? target
+ if File.symlink? target
+ system "rm", target
+ else
+ onoe "#{target} already exists, skipping."
+ end
+ end
+ system "ln", "-s", p, HOME_APPS
+ end
+ end
+end
diff --git a/Library/Contributions/cmds/brew-man b/Library/Contributions/cmds/brew-man
new file mode 100755
index 000000000..8afe2029d
--- /dev/null
+++ b/Library/Contributions/cmds/brew-man
@@ -0,0 +1,51 @@
+#!/bin/bash
+
+set -e
+shopt -s nullglob
+
+SOURCE_PATH="$HOMEBREW_REPOSITORY/Library/Contributions/manpages"
+TARGET_PATH="$HOMEBREW_REPOSITORY/share/man/man1"
+LINKED_PATH="$HOMEBREW_PREFIX/share/man/man1"
+
+
+die (){
+ echo $1
+ exit 1
+}
+
+test "$1" = '--link' || \
+test "$1" = '-l' && {
+ [[ $TARGET_PATH == $LINKED_PATH ]] && exit 0
+
+ for page in "$TARGET_PATH"/*.1
+ do
+ ln -s $page $LINKED_PATH
+ done
+ exit 0
+}
+
+/usr/bin/which -s ronn || die "You need to \"gem install ronn\" and put it in your path."
+
+test "$1" = '--server' || \
+test "$1" = '-s' && {
+ echo "Man page test server: http://localhost:1207/"
+ echo "Control-C to exit."
+ ronn --server $SOURCE_PATH/*
+ exit 0
+}
+
+echo "Writing manpages to $TARGET_PATH"
+
+for i in "$SOURCE_PATH"/*.md
+do
+ # Get the filename only, without the .md extension
+ j=`basename $i`
+ target_file="$TARGET_PATH/${j%\.md}"
+
+ ronn --roff --pipe --organization='Homebrew' --manual='brew' $i > $target_file
+done
+
+if test "$1" = '--verbose' || test "$1" = '-v'
+then
+ man brew
+fi
diff --git a/Library/Contributions/cmds/brew-mirror-check.rb b/Library/Contributions/cmds/brew-mirror-check.rb
new file mode 100755
index 000000000..1ae06ce6a
--- /dev/null
+++ b/Library/Contributions/cmds/brew-mirror-check.rb
@@ -0,0 +1,55 @@
+require 'formula'
+
+class Formula
+ def test_mirror mirror
+ url, specs = mirror.values_at :url, :specs
+ downloader = download_strategy.new url, name, version, specs
+
+ # Force the downloader to attempt the download by removing the tarball if
+ # it is allready cached.
+ tarball_path = downloader.tarball_path
+ tarball_path.unlink if tarball_path.exist?
+
+ begin
+ fetched = downloader.fetch
+ rescue DownloadError => e
+ opoo "Failed to fetch from URL: #{url}"
+ return
+ end
+
+ verify_download_integrity fetched if fetched.kind_of? Pathname
+ end
+end
+
+module Homebrew extend self
+ def check_mirrors
+ mirror_check_usage = <<-EOS
+Usage: brew mirror-check <formulae ...>
+
+Cycle through mirror lists for each formula, attempt a download and validate
+MD5 sums.
+ EOS
+
+ if ARGV.empty?
+ puts mirror_check_usage
+ exit 0
+ end
+
+ formulae = ARGV.formulae
+ raise FormulaUnspecifiedError if formulae.empty?
+
+ formulae.each do |f|
+ if f.mirrors.empty?
+ opoo "#{f.name} has no mirrors"
+ next
+ else
+ oh1 "Testing mirrors for #{f.name}"
+ f.mirrors.each{ |m| f.test_mirror m }
+ end
+ end
+ end
+end
+
+# Here is the actual code that gets run when `brew` loads this external
+# command.
+Homebrew.check_mirrors
diff --git a/Library/Contributions/cmds/brew-missing.rb b/Library/Contributions/cmds/brew-missing.rb
new file mode 100755
index 000000000..50fae12e4
--- /dev/null
+++ b/Library/Contributions/cmds/brew-missing.rb
@@ -0,0 +1,37 @@
+require "formula"
+require "cmd/outdated"
+
+def installed_brews
+ formulae = []
+ HOMEBREW_CELLAR.subdirs.each do |rack|
+ f = Formula.factory rack.basename.to_s rescue nil
+ formulae << f if f and f.installed?
+ end
+ formulae
+end
+
+def main
+ return unless HOMEBREW_CELLAR.exist?
+
+ # Names of outdated brews; they count as installed.
+ outdated = Homebrew.outdated_brews.collect{ |b| b.name }
+
+ formulae_to_check = if ARGV.named.empty?
+ installed_brews
+ else
+ ARGV.formulae
+ end
+
+ formulae_to_check.each do |f|
+ missing_deps = f.recursive_deps.map{ |g| g.name }.uniq.reject do |dep_name|
+ Formula.factory(dep_name).installed? or outdated.include?(dep_name)
+ end
+
+ unless missing_deps.empty?
+ print "#{f.name}: " if formulae_to_check.size > 1
+ puts "#{missing_deps * ' '}"
+ end
+ end
+end
+
+main()
diff --git a/Library/Contributions/cmds/brew-pull.rb b/Library/Contributions/cmds/brew-pull.rb
new file mode 100755
index 000000000..30d04120b
--- /dev/null
+++ b/Library/Contributions/cmds/brew-pull.rb
@@ -0,0 +1,78 @@
+# Gets a patch from a GitHub commit or pull request and applies it to Homebrew.
+# Optionally, installs it too.
+
+require 'utils.rb'
+
+if ARGV.include? '--install'
+ ARGV.delete '--install'
+ install = true
+end
+
+if ARGV.empty?
+ onoe 'This command requires at least one argument containing a URL or pull request number'
+end
+
+HOMEBREW_REPOSITORY.cd do
+ ARGV.named.each do|arg|
+ if arg.to_i > 0
+ url = 'https://github.com/mxcl/homebrew/pull/' + arg + '.patch'
+ else
+ # This regex should work, if it's too precise, feel free to fix it.
+ urlmatch = arg.match 'https:\/\/github.com\/\w+\/homebrew\/(pull\/(\d+)|commit\/\w{4,40})'
+ if !urlmatch
+ ohai 'Ignoring URL:', "Not a GitHub pull request or commit: #{arg}"
+ next
+ end
+
+ # GitHub provides commits'/pull-requests' raw patches using this URL.
+ url = urlmatch[0] + '.patch'
+ end
+
+ # The cache directory seems like a good place to put patches.
+ HOMEBREW_CACHE.mkpath
+ patchpath = (HOMEBREW_CACHE+File.basename(url))
+ curl url, '-o', patchpath
+
+ # Store current revision
+ revision = `git log -n1 --format=%H`.strip()
+
+ ohai 'Applying patch'
+ patch_args = %w[am --signoff]
+ # Normally we don't want whitespace errors, but squashing them can break
+ # patches so an option is provided to skip this step.
+ patch_args << '--whitespace=fix' unless ARGV.include? '--ignore-whitespace'
+ patch_args << patchpath
+
+ safe_system 'git', *patch_args
+
+ issue = arg.to_i > 0 ? arg.to_i : urlmatch[2]
+ if issue
+ ohai "Patch closes issue ##{issue}"
+ message = `git log HEAD^.. --format=%B`
+
+ # If this is a pull request, append a close message.
+ if !message.include? 'Closes #'
+ issueline = "Closes ##{issue}."
+ signed = 'Signed-off-by:'
+ message = message.gsub signed, issueline + "\n\n" + signed
+ safe_system 'git', 'commit', '--amend', '-q', '-m', message
+ end
+ end
+
+ ohai 'Patch changed:'
+ safe_system 'git', 'diff', "#{revision}..", '--stat'
+
+ if install
+ `git diff #{revision}.. --name-status`.each_line do |line|
+ status, filename = line.split()
+ # Don't try and do anything to removed files.
+ if (status == 'A' or status == 'M') and filename.include? '/Formula/'
+ formula = File.basename(filename, '.rb')
+ ohai "Installing #{formula}"
+ # Not sure if this is the best way to install?
+ safe_system 'brew', 'install', '--force', '--build-bottle', formula
+ end
+ end
+ end
+ end
+end
diff --git a/Library/Contributions/cmds/brew-readall.rb b/Library/Contributions/cmds/brew-readall.rb
new file mode 100755
index 000000000..d04de565d
--- /dev/null
+++ b/Library/Contributions/cmds/brew-readall.rb
@@ -0,0 +1,14 @@
+# `brew readall` tries to import all formulae one-by-one.
+# This can be useful for debugging issues across all formulae
+# when making significant changes to formula.rb,
+# or to determine if any current formulae have Ruby issues
+
+require 'formula'
+Formula.names.each do |n|
+ begin
+ f = Formula.factory(n)
+ rescue Exception => e
+ onoe "problem in #{Formula.path(n)}"
+ puts e
+ end
+end
diff --git a/Library/Contributions/cmds/brew-server b/Library/Contributions/cmds/brew-server
new file mode 100755
index 000000000..bcc15c257
--- /dev/null
+++ b/Library/Contributions/cmds/brew-server
@@ -0,0 +1,208 @@
+#!/usr/bin/ruby
+
+## brew server: Run a local webserver for browsing available and installed brews.
+# Note: this external command is ruby, but set up as a shell script, so that it gets exec'd.
+# This is required for sinatra's run-loop to take over.
+
+$:.unshift(ENV['HOMEBREW_LIBRARY_PATH'])
+
+require 'global'
+require 'formula'
+
+require 'rubygems'
+
+begin
+ require 'sinatra'
+rescue LoadError
+ onoe 'Sinatra required but not found'
+ puts 'To install: /usr/bin/gem install sinatra'
+ exit 1
+end
+
+require 'cgi'
+
+
+def link_to_formula name
+ "<a href=\"/formula/#{CGI.escape(name)}\">#{name}</a>"
+end
+
+def css_style
+ "" # No CSS defined yet.
+end
+
+def search_form
+ <<-EOS
+ <form action="/search">
+ Search: <input name="q" type="text"> <input type="submit">
+ </form>
+ EOS
+end
+
+def html_page
+ body = <<-HTML
+ <html>
+ <head>
+ <title>Homebrew Menu</title>
+ #{css_style}
+ </head>
+ <body>
+ <div id="wrap">
+ <div id="header">
+ <h1><a href="./">Homebrew</a></h1>
+ <p id="subtitle"><strong>The missing package manager for OS X</strong></p>
+ <p id="installed"><a href="/installed">Show installed packages</a></p>
+ </div>
+
+ <div id="informations">
+ HTML
+ yield body
+ body += <<-HTML
+ </div>
+ </div>
+ </body>
+ </html>
+ HTML
+ return body
+end
+
+get '/' do
+ return html_page do |s|
+ s << <<-HTML
+ <div class="row">#{search_form}</div>
+ <div class="row">
+ <ul>
+ HTML
+ Formula.names do |name|
+ s << "<li>#{link_to_formula(name)}</li>"
+ end
+ s << <<-HTML
+ </ul>
+ </div>
+ HTML
+ end
+end
+
+get '/search' do
+ q = params['q']
+ results = search_brews(q)
+
+ s = <<-HTML
+ <html>
+ <head>
+ <title>Search Results</title>
+ #{css_style}
+ </head>
+ <body>
+ <h1>Results</h1>
+ #{search_form}
+ <h4>Searched for &ldquo;#{q}&rdquo;</h4>
+ <ul>
+ HTML
+
+ results.each do |name|
+ s << "<li>#{link_to_formula(name)}</li>"
+ end
+
+ s += <<-HTML
+ </ul>
+ </body>
+ </html>
+ HTML
+
+ return s
+end
+
+get '/formula/:name' do
+ klass = Formula.factory(params[:name])
+
+ installed = klass.installed? ? "Installed at" : "Not installed."
+ installed_dd = klass.installed? ? "<a href=\"file://#{klass.prefix}\">#{klass.prefix}</a>" : ""
+
+ s = ""
+ s << <<-HTML
+ <html>
+ <head>
+ <title>Formula: #{klass.name}</title>
+ #{css_style}
+ </head>
+ <body>
+ <div>&larr; <a href="/">Back to menu</a></div>
+ <h1>#{klass.name}</h1>
+ <dl>
+ <dt>Version</dt>
+ <dd>#{klass.version}</dd>
+
+ <dt>Homepage</dt>
+ <dd><a href="#{klass.homepage}">#{klass.homepage}</a></dd>
+
+ <dt>Download</dt>
+ <dd><a href="#{klass.url}">#{klass.url}</a></dd>
+
+ <dt>#{installed}</dt>
+ <dd>#{installed_dd}</dd>
+ HTML
+
+ unless klass.deps.count == 0
+ s << <<-HTML
+ <dt>Depends on</td>
+ HTML
+ klass.deps.each do |dep|
+ s << "<dd>#{link_to_formula(dep.name)}</dd>"
+ end
+ end
+
+ used_by = Formula.all.select{|ff| ff.deps.include?(klass.name)}.map{|f| f.name}.flatten.uniq.sort
+ unless used_by.empty?
+ s << <<-HTML
+ <dt>Used by</td>
+ HTML
+ if used_by != nil
+ used_by.each do |name|
+ s << "<dd>#{link_to_formula(name)}</dd>"
+ end
+ end
+ end
+
+ s += <<-HTML
+ </dl>
+ </body>
+ </html>
+ HTML
+
+ return s
+end
+
+
+def installed_formulas
+ Formula.all.select{|formula| formula.installed?}
+end
+
+get '/installed' do
+
+ s = <<-HTML
+ <html>
+ <head>
+ <title>Installed Formulas</title>
+ #{css_style}
+ </head>
+ <body>
+ <h1>Installed Fomulas</h1>
+ <ul>
+ HTML
+
+ installed_formulas.each do |formula|
+ s << "<li>#{link_to_formula(formula.name)}</li>"
+ end
+
+ s += <<-HTML
+ </ul>
+ <div>&larr; <a href="/">Back to menu</a></div>
+ </body>
+ </html>
+ HTML
+
+ return s
+end
+
+
+puts "View our tasting menu at http://localhost:4567/\nUse \"Control-C\" to exit.\n\n"
diff --git a/Library/Contributions/cmds/brew-switch.rb b/Library/Contributions/cmds/brew-switch.rb
new file mode 100755
index 000000000..3b51f941c
--- /dev/null
+++ b/Library/Contributions/cmds/brew-switch.rb
@@ -0,0 +1,40 @@
+require 'formula'
+require 'keg'
+
+if ARGV.named.length != 2
+ onoe "Usage: brew switch <formula> <version>"
+ exit 1
+end
+
+name = ARGV.shift
+version = ARGV.shift
+
+# Does this formula have any versions?
+f = Formula.factory(name.downcase)
+cellar = f.prefix.parent
+unless cellar.directory?
+ onoe "#{name} not found in the Cellar."
+ exit 2
+end
+
+# Does the target version exist?
+unless (cellar+version).directory?
+ onoe "#{name} does not have a version \"#{version}\" in the Cellar."
+
+ versions = cellar.children.select { |pn| pn.directory? }.collect { |pn| pn.basename.to_s }
+ puts "Versions available: #{versions.join(', ')}"
+
+ exit 3
+end
+
+# Unlink all existing versions
+cellar.children.select { |pn| pn.directory? }.each do |v|
+ keg = Keg.new(v)
+ puts "Cleaning #{keg}"
+ keg.unlink
+end
+
+# Link new version
+
+keg = Keg.new(cellar+version)
+puts "#{keg.link} links created for #{keg}" \ No newline at end of file
diff --git a/Library/Contributions/cmds/brew-unpack.rb b/Library/Contributions/cmds/brew-unpack.rb
new file mode 100755
index 000000000..d4d72623e
--- /dev/null
+++ b/Library/Contributions/cmds/brew-unpack.rb
@@ -0,0 +1,93 @@
+require 'formula'
+
+require 'stringio'
+module ScriptDataReader
+ # This module contains a method for extracting the contents of DATA from a
+ # Ruby file other than the script containing the currently executing
+ # function. Many thanks to Glenn Jackman's Stackoverflow answer which
+ # provided this code:
+ #
+ # http://stackoverflow.com/questions/2156629/can-i-access-the-data-from-a-required-script-in-ruby/2157556#2157556
+ def self.load(filename)
+ data = StringIO.new
+ File.open(filename) do |f|
+ begin
+ line = f.gets
+ end until line.nil? or line.match(/^__END__$/)
+ while line = f.gets
+ data << line
+ end
+ end
+ data.rewind
+ data
+ end
+end
+
+# Need to tweak the Formula class slightly so that patching is option and `DATA`
+# patches work correctly.
+class Formula
+ # Create a reference to the original Formula.patch method and then override
+ # so that paching only happens if the user asks.
+ alias do_patch patch
+ def patch
+ if ARGV.include? '--patch'
+ # Yes Ruby, we are about to redefine a constant. Just breathe.
+ orig_v = $VERBOSE; $VERBOSE = nil
+ Formula.const_set 'DATA', ScriptDataReader.load(path)
+ $VERBOSE = orig_v
+
+ do_patch
+ end
+ end
+
+ # handle_llvm_failure() requires extend/ENV, so let's never fail
+ # with llvm since we don't particularly care in this context.
+ def fails_with_llvm?; false; end
+end
+
+module Homebrew extend self
+ def unpack
+ unpack_usage = <<-EOS
+Usage: brew unpack [--patch] [--destdir=path/to/extract/in] <formulae ...>
+
+Unpack formulae source code for inspection.
+
+Formulae archives will be extracted to subfolders inside the current working
+directory or a directory specified by `--destdir`. If the `--patch` option is
+supplied, patches will also be downloaded and applied.
+ EOS
+
+ if ARGV.empty?
+ puts unpack_usage
+ exit 0
+ end
+
+ formulae = ARGV.formulae
+ raise FormulaUnspecifiedError if formulae.empty?
+
+ unpack_dir = ARGV.options_only.select {|o| o.start_with? "--destdir="}
+ if unpack_dir.empty?
+ unpack_dir = Pathname.new Dir.getwd
+ else
+ unpack_dir = Pathname.new(unpack_dir.first.split('=')[1]).realpath
+ unpack_dir.mkpath unless unpack_dir.exist?
+ end
+
+ raise "Cannot write to #{unpack_dir}" unless unpack_dir.writable?
+
+ formulae.each do |f|
+ # Create a nice name for the stage folder.
+ stage_dir = unpack_dir + [f.name, f.version].join('-')
+ raise "Destination #{stage_dir} allready exists!" if stage_dir.exist?
+
+ f.brew do
+ oh1 "Unpacking #{f.name} to: #{stage_dir}"
+ cp_r Dir.getwd, stage_dir
+ end
+ end
+ end
+end
+
+# Here is the actual code that gets run when `brew` loads this external
+# command.
+Homebrew.unpack
diff --git a/Library/Contributions/cmds/brew-which.rb b/Library/Contributions/cmds/brew-which.rb
new file mode 100755
index 000000000..b3318ee76
--- /dev/null
+++ b/Library/Contributions/cmds/brew-which.rb
@@ -0,0 +1,49 @@
+require 'extend/pathname'
+
+
+module Homebrew extend self
+ def which_versions which_brews=nil
+ brew_links = Array.new
+ version_map = Hash.new
+
+ real_cellar = HOMEBREW_CELLAR.realpath
+
+ paths=%w[bin sbin lib].collect {|d| HOMEBREW_PREFIX+d}
+
+ paths.each do |path|
+ path.find do |path|
+ next unless path.symlink? && path.resolved_path_exists?
+ brew_links << Pathname.new(path.realpath)
+ end
+ end
+
+ brew_links = brew_links.collect{|p|p.relative_path_from(real_cellar).to_s}.reject{|p|p.start_with?("../")}
+
+ brew_links.each do |p|
+ parts = p.split("/")
+ next if parts.count < 2 # Shouldn't happen for normally installed brews
+ brew = parts.shift
+ version = parts.shift
+
+ next unless which_brews.include? brew if which_brews
+
+ versions = version_map[brew] || []
+ versions << version unless versions.include? version
+ version_map[brew] = versions
+ end
+
+ return version_map
+ end
+
+ def which
+ which_brews = ARGV.named.empty? ? nil : ARGV.named
+
+ brews = which_versions which_brews
+ brews.keys.sort.each do |b|
+ puts "#{b}: #{brews[b].sort*' '}"
+ end
+ puts
+ end
+end
+
+Homebrew.which