Edgewall Software

TracOnWindows: trac-0.10.3-win32-install.py

File trac-0.10.3-win32-install.py, 11.7 KB (added by Christian Boos, 17 years ago)

All-in-one installer (not a graphical installer)

Line 
1#!/bin/env python
2"""Trac installer"""
3
4
5#!python
6"""Bootstrap setuptools installation
7
8If you want to use setuptools in your package's setup.py, just include this
9file in the same directory with it, and add this to the top of your setup.py::
10
11 from ez_setup import use_setuptools
12 use_setuptools()
13
14If you want to require a specific version of setuptools, set a download
15mirror, or use an alternate download directory, you can do so by supplying
16the appropriate options to ``use_setuptools()``.
17
18This file can also be run as a script to install or upgrade setuptools.
19"""
20import sys
21DEFAULT_VERSION = "0.6c2"
22DEFAULT_URL = "http://cheeseshop.python.org/packages/%s/s/setuptools/" % sys.version[:3]
23
24md5_data = {
25 'setuptools-0.6b1-py2.3.egg': '8822caf901250d848b996b7f25c6e6ca',
26 'setuptools-0.6b1-py2.4.egg': 'b79a8a403e4502fbb85ee3f1941735cb',
27 'setuptools-0.6b2-py2.3.egg': '5657759d8a6d8fc44070a9d07272d99b',
28 'setuptools-0.6b2-py2.4.egg': '4996a8d169d2be661fa32a6e52e4f82a',
29 'setuptools-0.6b3-py2.3.egg': 'bb31c0fc7399a63579975cad9f5a0618',
30 'setuptools-0.6b3-py2.4.egg': '38a8c6b3d6ecd22247f179f7da669fac',
31 'setuptools-0.6b4-py2.3.egg': '62045a24ed4e1ebc77fe039aa4e6f7e5',
32 'setuptools-0.6b4-py2.4.egg': '4cb2a185d228dacffb2d17f103b3b1c4',
33 'setuptools-0.6c1-py2.3.egg': 'b3f2b5539d65cb7f74ad79127f1a908c',
34 'setuptools-0.6c1-py2.4.egg': 'b45adeda0667d2d2ffe14009364f2a4b',
35 'setuptools-0.6c2-py2.3.egg': 'f0064bf6aa2b7d0f3ba0b43f20817c27',
36 'setuptools-0.6c2-py2.4.egg': '616192eec35f47e8ea16cd6a122b7277',
37}
38
39import sys, os
40
41# TRACBEGIN
42
43TRAC_VERSION = "0.10.3"
44
45def get_python():
46 """Displays information about where to download Python for your system.
47 Currently, this will always return False. The idea is that eventually
48 it may actually download Python if you want it to (in which case, it
49 would return True)."""
50 print """
51The recommended Python for Trac is Python 2.4.3. You can download
52it here:
53
54http://www.python.org/ftp/python/2.4.3/python-2.4.3.msi
55"""
56 return False
57
58def get_yesno(default="y"):
59 """Gets a valid 'y' or 'n' answer from the user."""
60 while True:
61 fromuser = raw_input("(y|n, default %s)" % default)
62 if fromuser:
63 val = fromuser[0].lower()
64 if val == "y" or val == "n":
65 break
66 else:
67 return default
68 return val
69
70def check_python():
71 if sys.version_info[:2] != (2,4):
72 print """
73This installer requires Python 2.4
74"""
75 if not get_python():
76 sys.exit(1)
77
78def check_directory():
79 """Ensures that the current directory does not contain a Trac
80 directory that setuptools will attempt to install from."""
81 if os.path.exists("trac") or os.path.exists("Trac"):
82 print """There is a 'trac' directory in the current directory.
83 EasyInstall will normally try to install from this directory rather
84 than picking up the installation package from the net."""
85 if os.access("..", os.W_OK) and not \
86 os.path.exists(os.path.join("..", "trac")) and not \
87 os.path.exists(os.path.join("..", "Trac")):
88 print """
89This installer needs a place to store the setuptools installation
90package to do its work. The parent directory of this one is writeable.
91Should the installation proceed from there ('n' to exit)?"""
92 upone = get_yesno()
93 if upone == "n":
94 sys.exit(1)
95 os.chdir("..")
96 else:
97 print """
98This installer needs to run in a directory that does not contain a
99'trac' directory and it also needs to run in a directory that
100you have write access to. Please change directories and rerun this
101installer.
102"""
103 sys.exit(1)
104
105def check_subversion(args):
106 try:
107 from svn import fs
108 except ImportError:
109 pass
110 else:
111 return
112 print """
113Would you like to use Trac with a Subversion repository
114"""
115 usesvn = get_yesno()
116 if usesvn:
117 args.insert(0, '-Z')
118 args.append('http://subversion.tigris.org/downloads/'
119 'svn-python-1.4.0-py2.4.exe')
120
121def update_args():
122 """Sets up the command line arguments for ez_setup.py"""
123 if len(sys.argv) > 1:
124 args = sys.argv[1:]
125 else:
126 args = []
127 args.append("-f")
128 args.append("http://clearsilver.net/downloads")
129 args.append("-U")
130 args.append("clearsilver==0.9.14")
131 args.append("pysqlite")
132 args.append("http://ftp.edgewall.com/pub/trac/trac-%s.tar.gz" % TRAC_VERSION)
133 return args
134
135def fix_siteconfig():
136 import pkg_resources
137 del sys.modules['trac']
138 pkg_resources.require('trac')
139 siteconfig = pkg_resources.resource_filename('trac', 'siteconfig.py')
140 open(siteconfig, 'w').write("""# PLEASE DO NOT EDIT THIS FILE!
141# This file was autogenerated when installing Trac %s.
142#
143import os
144import pkg_resources
145_sharedir = os.path.normpath(pkg_resources.resource_filename('trac', '../share/trac'))
146
147__default_conf_dir__ = os.path.join(_sharedir, 'conf')
148__default_templates_dir__ = os.path.join(_sharedir, 'templates')
149__default_htdocs_dir__ = os.path.join(_sharedir, 'htdocs')
150__default_wiki_dir__ = os.path.join(_sharedir, 'wiki-default')
151__default_macros_dir__ = os.path.join(_sharedir, 'wiki-macros')
152__default_plugins_dir__ = os.path.join(_sharedir, 'plugins')
153""" % TRAC_VERSION)
154
155def trac_main():
156 print "Trac Windows Installer"
157 check_python()
158 check_directory()
159 args = update_args()
160 check_subversion(args)
161 print "Beginning setuptools/EasyInstall installation and Trac" \
162 "download"
163 main(args)
164 fix_siteconfig()
165
166# TRACEND
167
168def _validate_md5(egg_name, data):
169 if egg_name in md5_data:
170 from md5 import md5
171 digest = md5(data).hexdigest()
172 if digest != md5_data[egg_name]:
173 print >>sys.stderr, (
174 "md5 validation of %s failed! (Possible download problem?)"
175 % egg_name
176 )
177 sys.exit(2)
178 return data
179
180
181def use_setuptools(
182 version=DEFAULT_VERSION, download_base=DEFAULT_URL, to_dir=os.curdir,
183 download_delay=15
184):
185 """Automatically find/download setuptools and make it available on sys.path
186
187 `version` should be a valid setuptools version number that is available
188 as an egg for download under the `download_base` URL (which should end with
189 a '/'). `to_dir` is the directory where setuptools will be downloaded, if
190 it is not already available. If `download_delay` is specified, it should
191 be the number of seconds that will be paused before initiating a download,
192 should one be required. If an older version of setuptools is installed,
193 this routine will print a message to ``sys.stderr`` and raise SystemExit in
194 an attempt to abort the calling script.
195 """
196 try:
197 import setuptools
198 if setuptools.__version__ == '0.0.1':
199 print >>sys.stderr, (
200 "You have an obsolete version of setuptools installed. Please\n"
201 "remove it from your system entirely before rerunning this script."
202 )
203 sys.exit(2)
204 except ImportError:
205 egg = download_setuptools(version, download_base, to_dir, download_delay)
206 sys.path.insert(0, egg)
207 import setuptools; setuptools.bootstrap_install_from = egg
208
209 import pkg_resources
210 try:
211 pkg_resources.require("setuptools>="+version)
212
213 except pkg_resources.VersionConflict, e:
214 # XXX could we install in a subprocess here?
215 print >>sys.stderr, (
216 "The required version of setuptools (>=%s) is not available, and\n"
217 "can't be installed while this script is running. Please install\n"
218 " a more recent version first.\n\n(Currently using %r)"
219 ) % (version, e.args[0])
220 sys.exit(2)
221
222def download_setuptools(
223 version=DEFAULT_VERSION, download_base=DEFAULT_URL, to_dir=os.curdir,
224 delay = 15
225):
226 """Download setuptools from a specified location and return its filename
227
228 `version` should be a valid setuptools version number that is available
229 as an egg for download under the `download_base` URL (which should end
230 with a '/'). `to_dir` is the directory where the egg will be downloaded.
231 `delay` is the number of seconds to pause before an actual download attempt.
232 """
233 import urllib2, shutil
234 egg_name = "setuptools-%s-py%s.egg" % (version,sys.version[:3])
235 url = download_base + egg_name
236 saveto = os.path.join(to_dir, egg_name)
237 src = dst = None
238 if not os.path.exists(saveto): # Avoid repeated downloads
239 try:
240 from distutils import log
241 if delay:
242 log.warn("""
243---------------------------------------------------------------------------
244This script requires setuptools version %s to run (even to display
245help). I will attempt to download it for you (from
246%s), but
247you may need to enable firewall access for this script first.
248I will start the download in %d seconds.
249
250(Note: if this machine does not have network access, please obtain the file
251
252 %s
253
254and place it in this directory before rerunning this script.)
255---------------------------------------------------------------------------""",
256 version, download_base, delay, url
257 ); from time import sleep; sleep(delay)
258 log.warn("Downloading %s", url)
259 src = urllib2.urlopen(url)
260 # Read/write all in one block, so we don't create a corrupt file
261 # if the download is interrupted.
262 data = _validate_md5(egg_name, src.read())
263 dst = open(saveto,"wb"); dst.write(data)
264 finally:
265 if src: src.close()
266 if dst: dst.close()
267 return os.path.realpath(saveto)
268
269def main(argv, version=DEFAULT_VERSION):
270 """Install or upgrade setuptools and EasyInstall"""
271
272 try:
273 import setuptools
274 except ImportError:
275 egg = None
276 try:
277 egg = download_setuptools(version, delay=0)
278 sys.path.insert(0,egg)
279 from setuptools.command.easy_install import main
280 return main(list(argv)+[egg]) # we're done here
281 finally:
282 if egg and os.path.exists(egg):
283 os.unlink(egg)
284 else:
285 if setuptools.__version__ == '0.0.1':
286 # tell the user to uninstall obsolete version
287 use_setuptools(version)
288
289 req = "setuptools>="+version
290 import pkg_resources
291 try:
292 pkg_resources.require(req)
293 except pkg_resources.VersionConflict:
294 try:
295 from setuptools.command.easy_install import main
296 except ImportError:
297 from easy_install import main
298 main(list(argv)+[download_setuptools(delay=0)])
299 sys.exit(0) # try to force an exit
300 else:
301 if argv:
302 from setuptools.command.easy_install import main
303 main(argv)
304 else:
305 print "Setuptools version",version,"or greater has been installed."
306 print '(Run "ez_setup.py -U setuptools" to reinstall or upgrade.)'
307
308
309
310def update_md5(filenames):
311 """Update our built-in md5 registry"""
312
313 import re
314 from md5 import md5
315
316 for name in filenames:
317 base = os.path.basename(name)
318 f = open(name,'rb')
319 md5_data[base] = md5(f.read()).hexdigest()
320 f.close()
321
322 data = [" %r: %r,\n" % it for it in md5_data.items()]
323 data.sort()
324 repl = "".join(data)
325
326 import inspect
327 srcfile = inspect.getsourcefile(sys.modules[__name__])
328 f = open(srcfile, 'rb'); src = f.read(); f.close()
329
330 match = re.search("\nmd5_data = {\n([^}]+)}", src)
331 if not match:
332 print >>sys.stderr, "Internal error!"
333 sys.exit(2)
334
335 src = src[:match.start(1)] + repl + src[match.end(1):]
336 f = open(srcfile,'w')
337 f.write(src)
338 f.close()
339
340
341if __name__=='__main__':
342 trac_main()