Move LICENSE->COPYING and package ez_setup.py without installing it.
[calibcant.git] / ez_setup.py
1 #!python
2 """Bootstrap setuptools installation
3
4 If you want to use setuptools in your package's setup.py, just include this
5 file in the same directory with it, and add this to the top of your setup.py::
6
7     from ez_setup import use_setuptools
8     use_setuptools()
9
10 If you want to require a specific version of setuptools, set a download
11 mirror, or use an alternate download directory, you can do so by supplying
12 the appropriate options to ``use_setuptools()``.
13
14 This file can also be run as a script to install or upgrade setuptools.
15 """
16 import sys
17 DEFAULT_VERSION = "0.6c9"
18 DEFAULT_URL     = "http://pypi.python.org/packages/%s/s/setuptools/" % sys.version[:3]
19
20 md5_data = {
21     'setuptools-0.6b1-py2.3.egg': '8822caf901250d848b996b7f25c6e6ca',
22     'setuptools-0.6b1-py2.4.egg': 'b79a8a403e4502fbb85ee3f1941735cb',
23     'setuptools-0.6b2-py2.3.egg': '5657759d8a6d8fc44070a9d07272d99b',
24     'setuptools-0.6b2-py2.4.egg': '4996a8d169d2be661fa32a6e52e4f82a',
25     'setuptools-0.6b3-py2.3.egg': 'bb31c0fc7399a63579975cad9f5a0618',
26     'setuptools-0.6b3-py2.4.egg': '38a8c6b3d6ecd22247f179f7da669fac',
27     'setuptools-0.6b4-py2.3.egg': '62045a24ed4e1ebc77fe039aa4e6f7e5',
28     'setuptools-0.6b4-py2.4.egg': '4cb2a185d228dacffb2d17f103b3b1c4',
29     'setuptools-0.6c1-py2.3.egg': 'b3f2b5539d65cb7f74ad79127f1a908c',
30     'setuptools-0.6c1-py2.4.egg': 'b45adeda0667d2d2ffe14009364f2a4b',
31     'setuptools-0.6c2-py2.3.egg': 'f0064bf6aa2b7d0f3ba0b43f20817c27',
32     'setuptools-0.6c2-py2.4.egg': '616192eec35f47e8ea16cd6a122b7277',
33     'setuptools-0.6c3-py2.3.egg': 'f181fa125dfe85a259c9cd6f1d7b78fa',
34     'setuptools-0.6c3-py2.4.egg': 'e0ed74682c998bfb73bf803a50e7b71e',
35     'setuptools-0.6c3-py2.5.egg': 'abef16fdd61955514841c7c6bd98965e',
36     'setuptools-0.6c4-py2.3.egg': 'b0b9131acab32022bfac7f44c5d7971f',
37     'setuptools-0.6c4-py2.4.egg': '2a1f9656d4fbf3c97bf946c0a124e6e2',
38     'setuptools-0.6c4-py2.5.egg': '8f5a052e32cdb9c72bcf4b5526f28afc',
39     'setuptools-0.6c5-py2.3.egg': 'ee9fd80965da04f2f3e6b3576e9d8167',
40     'setuptools-0.6c5-py2.4.egg': 'afe2adf1c01701ee841761f5bcd8aa64',
41     'setuptools-0.6c5-py2.5.egg': 'a8d3f61494ccaa8714dfed37bccd3d5d',
42     'setuptools-0.6c6-py2.3.egg': '35686b78116a668847237b69d549ec20',
43     'setuptools-0.6c6-py2.4.egg': '3c56af57be3225019260a644430065ab',
44     'setuptools-0.6c6-py2.5.egg': 'b2f8a7520709a5b34f80946de5f02f53',
45     'setuptools-0.6c7-py2.3.egg': '209fdf9adc3a615e5115b725658e13e2',
46     'setuptools-0.6c7-py2.4.egg': '5a8f954807d46a0fb67cf1f26c55a82e',
47     'setuptools-0.6c7-py2.5.egg': '45d2ad28f9750e7434111fde831e8372',
48     'setuptools-0.6c8-py2.3.egg': '50759d29b349db8cfd807ba8303f1902',
49     'setuptools-0.6c8-py2.4.egg': 'cba38d74f7d483c06e9daa6070cce6de',
50     'setuptools-0.6c8-py2.5.egg': '1721747ee329dc150590a58b3e1ac95b',
51     'setuptools-0.6c9-py2.3.egg': 'a83c4020414807b496e4cfbe08507c03',
52     'setuptools-0.6c9-py2.4.egg': '260a2be2e5388d66bdaee06abec6342a',
53     'setuptools-0.6c9-py2.5.egg': 'fe67c3e5a17b12c0e7c541b7ea43a8e6',
54 }
55
56 import sys, os
57 try: from hashlib import md5
58 except ImportError: from md5 import md5
59
60 def _validate_md5(egg_name, data):
61     if egg_name in md5_data:
62         digest = md5(data).hexdigest()
63         if digest != md5_data[egg_name]:
64             print >>sys.stderr, (
65                 "md5 validation of %s failed!  (Possible download problem?)"
66                 % egg_name
67             )
68             sys.exit(2)
69     return data
70
71 def use_setuptools(
72     version=DEFAULT_VERSION, download_base=DEFAULT_URL, to_dir=os.curdir,
73     download_delay=15
74 ):
75     """Automatically find/download setuptools and make it available on sys.path
76
77     `version` should be a valid setuptools version number that is available
78     as an egg for download under the `download_base` URL (which should end with
79     a '/').  `to_dir` is the directory where setuptools will be downloaded, if
80     it is not already available.  If `download_delay` is specified, it should
81     be the number of seconds that will be paused before initiating a download,
82     should one be required.  If an older version of setuptools is installed,
83     this routine will print a message to ``sys.stderr`` and raise SystemExit in
84     an attempt to abort the calling script.
85     """
86     was_imported = 'pkg_resources' in sys.modules or 'setuptools' in sys.modules
87     def do_download():
88         egg = download_setuptools(version, download_base, to_dir, download_delay)
89         sys.path.insert(0, egg)
90         import setuptools; setuptools.bootstrap_install_from = egg
91     try:
92         import pkg_resources
93     except ImportError:
94         return do_download()       
95     try:
96         pkg_resources.require("setuptools>="+version); return
97     except pkg_resources.VersionConflict, e:
98         if was_imported:
99             print >>sys.stderr, (
100             "The required version of setuptools (>=%s) is not available, and\n"
101             "can't be installed while this script is running. Please install\n"
102             " a more recent version first, using 'easy_install -U setuptools'."
103             "\n\n(Currently using %r)"
104             ) % (version, e.args[0])
105             sys.exit(2)
106         else:
107             del pkg_resources, sys.modules['pkg_resources']    # reload ok
108             return do_download()
109     except pkg_resources.DistributionNotFound:
110         return do_download()
111
112 def download_setuptools(
113     version=DEFAULT_VERSION, download_base=DEFAULT_URL, to_dir=os.curdir,
114     delay = 15
115 ):
116     """Download setuptools from a specified location and return its filename
117
118     `version` should be a valid setuptools version number that is available
119     as an egg for download under the `download_base` URL (which should end
120     with a '/'). `to_dir` is the directory where the egg will be downloaded.
121     `delay` is the number of seconds to pause before an actual download attempt.
122     """
123     import urllib2, shutil
124     egg_name = "setuptools-%s-py%s.egg" % (version,sys.version[:3])
125     url = download_base + egg_name
126     saveto = os.path.join(to_dir, egg_name)
127     src = dst = None
128     if not os.path.exists(saveto):  # Avoid repeated downloads
129         try:
130             from distutils import log
131             if delay:
132                 log.warn("""
133 ---------------------------------------------------------------------------
134 This script requires setuptools version %s to run (even to display
135 help).  I will attempt to download it for you (from
136 %s), but
137 you may need to enable firewall access for this script first.
138 I will start the download in %d seconds.
139
140 (Note: if this machine does not have network access, please obtain the file
141
142    %s
143
144 and place it in this directory before rerunning this script.)
145 ---------------------------------------------------------------------------""",
146                     version, download_base, delay, url
147                 ); from time import sleep; sleep(delay)
148             log.warn("Downloading %s", url)
149             src = urllib2.urlopen(url)
150             # Read/write all in one block, so we don't create a corrupt file
151             # if the download is interrupted.
152             data = _validate_md5(egg_name, src.read())
153             dst = open(saveto,"wb"); dst.write(data)
154         finally:
155             if src: src.close()
156             if dst: dst.close()
157     return os.path.realpath(saveto)
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194 def main(argv, version=DEFAULT_VERSION):
195     """Install or upgrade setuptools and EasyInstall"""
196     try:
197         import setuptools
198     except ImportError:
199         egg = None
200         try:
201             egg = download_setuptools(version, delay=0)
202             sys.path.insert(0,egg)
203             from setuptools.command.easy_install import main
204             return main(list(argv)+[egg])   # we're done here
205         finally:
206             if egg and os.path.exists(egg):
207                 os.unlink(egg)
208     else:
209         if setuptools.__version__ == '0.0.1':
210             print >>sys.stderr, (
211             "You have an obsolete version of setuptools installed.  Please\n"
212             "remove it from your system entirely before rerunning this script."
213             )
214             sys.exit(2)
215
216     req = "setuptools>="+version
217     import pkg_resources
218     try:
219         pkg_resources.require(req)
220     except pkg_resources.VersionConflict:
221         try:
222             from setuptools.command.easy_install import main
223         except ImportError:
224             from easy_install import main
225         main(list(argv)+[download_setuptools(delay=0)])
226         sys.exit(0) # try to force an exit
227     else:
228         if argv:
229             from setuptools.command.easy_install import main
230             main(argv)
231         else:
232             print "Setuptools version",version,"or greater has been installed."
233             print '(Run "ez_setup.py -U setuptools" to reinstall or upgrade.)'
234
235 def update_md5(filenames):
236     """Update our built-in md5 registry"""
237
238     import re
239
240     for name in filenames:
241         base = os.path.basename(name)
242         f = open(name,'rb')
243         md5_data[base] = md5(f.read()).hexdigest()
244         f.close()
245
246     data = ["    %r: %r,\n" % it for it in md5_data.items()]
247     data.sort()
248     repl = "".join(data)
249
250     import inspect
251     srcfile = inspect.getsourcefile(sys.modules[__name__])
252     f = open(srcfile, 'rb'); src = f.read(); f.close()
253
254     match = re.search("\nmd5_data = {\n([^}]+)}", src)
255     if not match:
256         print >>sys.stderr, "Internal error!"
257         sys.exit(2)
258
259     src = src[:match.start(1)] + repl + src[match.end(1):]
260     f = open(srcfile,'w')
261     f.write(src)
262     f.close()
263
264
265 if __name__=='__main__':
266     if len(sys.argv)>2 and sys.argv[1]=='--md5update':
267         update_md5(sys.argv[2:])
268     else:
269         main(sys.argv[1:])
270
271
272
273
274
275