| 
									
										
										
										
											2002-08-28 22:22:10 +00:00
										 |  |  | # Build and install an Apple Help Viewer compatible version of the Python | 
					
						
							|  |  |  | # documentation into the framework. | 
					
						
							|  |  |  | # Code by Bill Fancher, with some modifications by Jack Jansen. | 
					
						
							|  |  |  | # | 
					
						
							|  |  |  | # You must run this as a two-step process | 
					
						
							|  |  |  | # 1. python setupDocs.py build | 
					
						
							|  |  |  | # 2. Wait for Apple Help Indexing Tool to finish | 
					
						
							|  |  |  | # 3. python setupDocs.py install | 
					
						
							|  |  |  | # | 
					
						
							|  |  |  | # To do: | 
					
						
							|  |  |  | # - test whether the docs are available locally before downloading | 
					
						
							|  |  |  | # - fix buildDocsFromSource | 
					
						
							|  |  |  | # - Get documentation version from sys.version, fallback to 2.2.1 | 
					
						
							|  |  |  | # - See if we can somehow detect that Apple Help Indexing Tool is finished | 
					
						
							|  |  |  | # - data_files to setup() doesn't seem the right way to pass the arguments | 
					
						
							|  |  |  | # | 
					
						
							|  |  |  | import sys, os, re | 
					
						
							|  |  |  | from distutils.cmd import Command | 
					
						
							|  |  |  | from distutils.command.build import build | 
					
						
							|  |  |  | from distutils.core import setup | 
					
						
							|  |  |  | from distutils.file_util import copy_file | 
					
						
							|  |  |  | from distutils.dir_util import copy_tree | 
					
						
							|  |  |  | from distutils.log import log | 
					
						
							|  |  |  | from distutils.spawn import spawn | 
					
						
							|  |  |  | from distutils import sysconfig, dep_util | 
					
						
							| 
									
										
										
										
											2003-02-14 23:46:22 +00:00
										 |  |  | from distutils.util import change_root | 
					
						
							| 
									
										
										
										
											2003-05-27 22:47:55 +00:00
										 |  |  | import HelpIndexingTool | 
					
						
							|  |  |  | import Carbon.File | 
					
						
							|  |  |  | import time | 
					
						
							| 
									
										
										
										
											2002-08-28 22:22:10 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2005-04-17 21:30:52 +00:00
										 |  |  | MAJOR_VERSION='2.4' | 
					
						
							|  |  |  | MINOR_VERSION='2.4.1' | 
					
						
							|  |  |  | DESTDIR='/Applications/MacPython-%s/PythonIDE.app/Contents/Resources/English.lproj/PythonDocumentation' % MAJOR_VERSION | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2002-08-28 22:22:10 +00:00
										 |  |  | class DocBuild(build): | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |     def initialize_options(self): | 
					
						
							|  |  |  |         build.initialize_options(self) | 
					
						
							|  |  |  |         self.build_html = None | 
					
						
							|  |  |  |         self.build_dest = None | 
					
						
							| 
									
										
										
										
											2005-04-17 21:30:52 +00:00
										 |  |  |         self.download = 1 | 
					
						
							|  |  |  |         self.doc_version = MINOR_VERSION # Only needed if download is true | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  |     def finalize_options(self): | 
					
						
							|  |  |  |         build.finalize_options(self) | 
					
						
							|  |  |  |         if self.build_html is None: | 
					
						
							|  |  |  |             self.build_html = os.path.join(self.build_base, 'html') | 
					
						
							|  |  |  |         if self.build_dest is None: | 
					
						
							|  |  |  |             self.build_dest = os.path.join(self.build_base, 'PythonDocumentation') | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def spawn(self, *args): | 
					
						
							|  |  |  |         spawn(args, 1,  self.verbose, self.dry_run) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def downloadDocs(self): | 
					
						
							|  |  |  |         workdir = os.getcwd() | 
					
						
							| 
									
										
										
										
											2005-04-17 21:30:52 +00:00
										 |  |  |         # XXX Note: the next strings may change from version to version | 
					
						
							|  |  |  |         url = 'http://www.python.org/ftp/python/doc/%s/html-%s.tar.bz2' % \ | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |                 (self.doc_version,self.doc_version) | 
					
						
							| 
									
										
										
										
											2005-04-17 21:30:52 +00:00
										 |  |  |         tarfile = 'html-%s.tar.bz2' % self.doc_version | 
					
						
							|  |  |  |         dirname = 'Python-Docs-%s' % self.doc_version | 
					
						
							| 
									
										
										
										
											2005-04-20 17:45:13 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2005-04-17 21:30:52 +00:00
										 |  |  |         if os.path.exists(self.build_html): | 
					
						
							| 
									
										
										
										
											2007-08-31 00:04:24 +00:00
										 |  |  |             raise RuntimeError('%s: already exists, please remove and try again' % self.build_html) | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |         os.chdir(self.build_base) | 
					
						
							|  |  |  |         self.spawn('curl','-O', url) | 
					
						
							| 
									
										
										
										
											2005-04-17 21:30:52 +00:00
										 |  |  |         self.spawn('tar', '-xjf', tarfile) | 
					
						
							|  |  |  |         os.rename(dirname, 'html') | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |         os.chdir(workdir) | 
					
						
							| 
									
										
										
										
											2005-04-17 21:30:52 +00:00
										 |  |  | ##        print "** Please unpack %s" % os.path.join(self.build_base, tarfile) | 
					
						
							|  |  |  | ##        print "** Unpack the files into %s" % self.build_html | 
					
						
							|  |  |  | ##        raise RuntimeError, "You need to unpack the docs manually" | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  |     def buildDocsFromSource(self): | 
					
						
							|  |  |  |         srcdir = '../../..' | 
					
						
							|  |  |  |         docdir = os.path.join(srcdir, 'Doc') | 
					
						
							|  |  |  |         htmldir = os.path.join(docdir, 'html') | 
					
						
							|  |  |  |         spawn(('make','--directory', docdir, 'html'), 1, self.verbose, self.dry_run) | 
					
						
							|  |  |  |         self.mkpath(self.build_html) | 
					
						
							|  |  |  |         copy_tree(htmldir, self.build_html) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def ensureHtml(self): | 
					
						
							|  |  |  |         if not os.path.exists(self.build_html): | 
					
						
							|  |  |  |             if self.download: | 
					
						
							|  |  |  |                 self.downloadDocs() | 
					
						
							|  |  |  |             else: | 
					
						
							|  |  |  |                 self.buildDocsFromSource() | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def hackIndex(self): | 
					
						
							|  |  |  |         ind_html = 'index.html' | 
					
						
							|  |  |  |         #print 'self.build_dest =', self.build_dest | 
					
						
							|  |  |  |         hackedIndex = file(os.path.join(self.build_dest, ind_html),'w') | 
					
						
							|  |  |  |         origIndex = file(os.path.join(self.build_html,ind_html)) | 
					
						
							|  |  |  |         r = re.compile('<style type="text/css">.*</style>', re.DOTALL) | 
					
						
							|  |  |  |         hackedIndex.write(r.sub('<META NAME="AppleTitle" CONTENT="Python Documentation">',origIndex.read())) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def hackFile(self,d,f): | 
					
						
							|  |  |  |         origPath = os.path.join(d,f) | 
					
						
							|  |  |  |         assert(origPath[:len(self.build_html)] == self.build_html) | 
					
						
							|  |  |  |         outPath = os.path.join(self.build_dest, d[len(self.build_html)+1:], f) | 
					
						
							|  |  |  |         (name, ext) = os.path.splitext(f) | 
					
						
							|  |  |  |         if os.path.isdir(origPath): | 
					
						
							|  |  |  |             self.mkpath(outPath) | 
					
						
							|  |  |  |         elif ext == '.html': | 
					
						
							| 
									
										
										
										
											2007-08-30 18:39:28 +00:00
										 |  |  |             if self.verbose: print('hacking %s to %s' % (origPath,outPath)) | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |             hackedFile = file(outPath, 'w') | 
					
						
							|  |  |  |             origFile = file(origPath,'r') | 
					
						
							|  |  |  |             hackedFile.write(self.r.sub('<dl><dt><dd>', origFile.read())) | 
					
						
							|  |  |  |         else: | 
					
						
							|  |  |  |             copy_file(origPath, outPath) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def hackHtml(self): | 
					
						
							|  |  |  |         self.r = re.compile('<dl><dd>') | 
					
						
							|  |  |  |         os.path.walk(self.build_html, self.visit, None) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def visit(self, dummy, dirname, filenames): | 
					
						
							|  |  |  |         for f in filenames: | 
					
						
							|  |  |  |             self.hackFile(dirname, f) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def makeHelpIndex(self): | 
					
						
							|  |  |  |         app = '/Developer/Applications/Apple Help Indexing Tool.app' | 
					
						
							|  |  |  |         self.spawn('open', '-a', app , self.build_dest) | 
					
						
							| 
									
										
										
										
											2007-08-30 18:39:28 +00:00
										 |  |  |         print("Please wait until Apple Help Indexing Tool finishes before installing") | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  |     def makeHelpIndex(self): | 
					
						
							|  |  |  |         app = HelpIndexingTool.HelpIndexingTool(start=1) | 
					
						
							|  |  |  |         app.open(Carbon.File.FSSpec(self.build_dest)) | 
					
						
							|  |  |  |         sys.stderr.write("Waiting for Help Indexing Tool to start...") | 
					
						
							|  |  |  |         while 1: | 
					
						
							|  |  |  |             # This is bad design in the suite generation code! | 
					
						
							|  |  |  |             idle = app._get(HelpIndexingTool.Help_Indexing_Tool_Suite._Prop_idleStatus()) | 
					
						
							|  |  |  |             time.sleep(10) | 
					
						
							|  |  |  |             if not idle: break | 
					
						
							|  |  |  |             sys.stderr.write(".") | 
					
						
							|  |  |  |         sys.stderr.write("\n") | 
					
						
							|  |  |  |         sys.stderr.write("Waiting for Help Indexing Tool to finish...") | 
					
						
							|  |  |  |         while 1: | 
					
						
							|  |  |  |             # This is bad design in the suite generation code! | 
					
						
							|  |  |  |             idle = app._get(HelpIndexingTool.Help_Indexing_Tool_Suite._Prop_idleStatus()) | 
					
						
							|  |  |  |             time.sleep(10) | 
					
						
							|  |  |  |             if idle: break | 
					
						
							|  |  |  |             sys.stderr.write(".") | 
					
						
							|  |  |  |         sys.stderr.write("\n") | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def run(self): | 
					
						
							|  |  |  |         self.ensure_finalized() | 
					
						
							|  |  |  |         self.mkpath(self.build_base) | 
					
						
							|  |  |  |         self.ensureHtml() | 
					
						
							|  |  |  |         if not os.path.isdir(self.build_html): | 
					
						
							| 
									
										
										
										
											2007-08-31 00:04:24 +00:00
										 |  |  |             raise RuntimeError("Can't find source folder for documentation.") | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |         self.mkpath(self.build_dest) | 
					
						
							|  |  |  |         if dep_util.newer(os.path.join(self.build_html,'index.html'), os.path.join(self.build_dest,'index.html')): | 
					
						
							|  |  |  |             self.mkpath(self.build_dest) | 
					
						
							|  |  |  |             self.hackHtml() | 
					
						
							|  |  |  |             self.hackIndex() | 
					
						
							|  |  |  |             self.makeHelpIndex() | 
					
						
							| 
									
										
										
										
											2002-08-28 22:22:10 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2003-02-14 23:46:22 +00:00
										 |  |  | class AHVDocInstall(Command): | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |     description = "install Apple Help Viewer html files" | 
					
						
							|  |  |  |     user_options = [('install-doc=', 'd', | 
					
						
							|  |  |  |             'directory to install HTML tree'), | 
					
						
							|  |  |  |              ('root=', None, | 
					
						
							|  |  |  |              "install everything relative to this alternate root directory"), | 
					
						
							|  |  |  |             ] | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def initialize_options(self): | 
					
						
							|  |  |  |         self.build_dest = None | 
					
						
							|  |  |  |         self.install_doc = None | 
					
						
							|  |  |  |         self.prefix = None | 
					
						
							|  |  |  |         self.root = None | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     def finalize_options(self): | 
					
						
							|  |  |  |         self.set_undefined_options('install', | 
					
						
							|  |  |  |                 ('prefix', 'prefix'), | 
					
						
							|  |  |  |                 ('root', 'root')) | 
					
						
							|  |  |  | #               import pdb ; pdb.set_trace() | 
					
						
							|  |  |  |         build_cmd = self.get_finalized_command('build') | 
					
						
							|  |  |  |         if self.build_dest == None: | 
					
						
							|  |  |  |             build_cmd = self.get_finalized_command('build') | 
					
						
							|  |  |  |             self.build_dest = build_cmd.build_dest | 
					
						
							|  |  |  |         if self.install_doc == None: | 
					
						
							| 
									
										
										
										
											2005-04-17 21:30:52 +00:00
										 |  |  |             self.install_doc = os.path.join(self.prefix, DESTDIR) | 
					
						
							| 
									
										
										
										
											2007-08-30 18:39:28 +00:00
										 |  |  |         print('INSTALL', self.build_dest, '->', self.install_doc) | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  |     def run(self): | 
					
						
							|  |  |  |         self.finalize_options() | 
					
						
							|  |  |  |         self.ensure_finalized() | 
					
						
							| 
									
										
										
										
											2007-08-30 18:39:28 +00:00
										 |  |  |         print("Running Installer") | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |         instloc = self.install_doc | 
					
						
							|  |  |  |         if self.root: | 
					
						
							|  |  |  |             instloc = change_root(self.root, instloc) | 
					
						
							|  |  |  |         self.mkpath(instloc) | 
					
						
							|  |  |  |         copy_tree(self.build_dest, instloc) | 
					
						
							| 
									
										
										
										
											2007-08-30 18:39:28 +00:00
										 |  |  |         print("Installation complete") | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2002-08-28 22:22:10 +00:00
										 |  |  | def mungeVersion(infile, outfile): | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |     i = file(infile,'r') | 
					
						
							|  |  |  |     o = file(outfile,'w') | 
					
						
							|  |  |  |     o.write(re.sub('\$\(VERSION\)',sysconfig.get_config_var('VERSION'),i.read())) | 
					
						
							|  |  |  |     i.close() | 
					
						
							|  |  |  |     o.close() | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2002-08-28 22:22:10 +00:00
										 |  |  | def main(): | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |     # turn off warnings when deprecated modules are imported | 
					
						
							|  |  |  | ##      import warnings | 
					
						
							|  |  |  | ##      warnings.filterwarnings("ignore",category=DeprecationWarning) | 
					
						
							|  |  |  |     setup(name = 'Documentation', | 
					
						
							|  |  |  |             version = '%d.%d' % sys.version_info[:2], | 
					
						
							|  |  |  |             cmdclass = {'install_data':AHVDocInstall, 'build':DocBuild}, | 
					
						
							|  |  |  |             data_files = ['dummy'], | 
					
						
							|  |  |  |             ) | 
					
						
							| 
									
										
										
										
											2002-08-28 22:22:10 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  | if __name__ == '__main__': | 
					
						
							| 
									
										
										
										
											2004-07-18 06:16:08 +00:00
										 |  |  |     main() |