def build_qt(dev): qrc_path = op.join("qt", "mg.qrc") pyrc_path = op.join("qt", "mg_rc.py") print_and_do("pyrcc5 {0} > {1}".format(qrc_path, pyrc_path)) build_help() print("Creating the run.py file") shutil.copy("run_template_qt.py", "run.py")
def main(): args = parse_args() conf = json.load(open('conf.json')) ui = conf['ui'] dev = conf['dev'] print("Building moneyGuru with UI {}".format(ui)) if dev: print("Building in Dev mode") if args.clean: clean() if not op.exists('build'): os.mkdir('build') if args.doc: build_help(dev) elif args.loc: build_localizations(ui) elif args.updatepot: build_updatepot() elif args.mergepot: build_mergepot() elif args.cocoamod: build_cocoa_proxy_module() build_cocoa_bridging_interfaces() elif args.ext: build_ext() elif args.cocoa_compile: os.chdir('cocoa') print_and_do(cocoa_compile_command()) os.chdir('..') cocoa_app().copy_executable('cocoa/build/moneyGuru') elif args.xibless: build_cocoalib_xibless() build_xibless() else: build_normal(ui, dev)
def build_cocoa(dev): sparkle_framework_path = op.join('cocoa', 'Sparkle', 'build', 'Release', 'Sparkle.framework') if not op.exists(sparkle_framework_path): print("Building Sparkle") os.chdir(op.join('cocoa', 'Sparkle')) print_and_do('make build') os.chdir(op.join('..', '..')) print("Creating OS X app structure") app = cocoa_app() app_version = get_module_version('core') cocoa_project_path = 'cocoa' filereplace(op.join(cocoa_project_path, 'InfoTemplate.plist'), op.join('build', 'Info.plist'), version=app_version) app.create(op.join('build', 'Info.plist')) print("Building localizations") build_localizations('cocoa') print("Building xibless UIs") build_cocoalib_xibless() build_xibless() print("Building Python extensions") build_cocoa_proxy_module() build_cocoa_bridging_interfaces() print("Building the cocoa layer") copy_embeddable_python_dylib('build') pydep_folder = op.join(app.resources, 'py') if not op.exists(pydep_folder): os.mkdir(pydep_folder) shutil.copy(op.join(cocoa_project_path, 'dg_cocoa.py'), 'build') tocopy = [ 'core', 'hscommon', 'cocoa/inter', 'cocoalib/cocoa', 'objp', 'send2trash', 'hsaudiotag', ] copy_packages(tocopy, pydep_folder, create_links=dev) sys.path.insert(0, 'build') # ModuleFinder can't seem to correctly detect the multiprocessing dependency, so we have # to manually specify it. extra_deps = ['multiprocessing'] collect_stdlib_dependencies('build/dg_cocoa.py', pydep_folder, extra_deps=extra_deps) del sys.path[0] # Views are not referenced by python code, so they're not found by the collector. copy_all('build/inter/*.so', op.join(pydep_folder, 'inter')) if not dev: # Important: Don't ever run delete_files_with_pattern('*.py') on dev builds because you'll # be deleting all py files in symlinked folders. compileall.compile_dir(pydep_folder, force=True, legacy=True) delete_files_with_pattern(pydep_folder, '*.py') delete_files_with_pattern(pydep_folder, '__pycache__') print("Compiling with WAF") os.chdir('cocoa') print_and_do('{0} waf configure && {0} waf'.format(sys.executable)) os.chdir('..') app.copy_executable('cocoa/build/dupeGuru') build_help() print("Copying resources and frameworks") image_path = 'cocoa/dupeguru.icns' resources = [image_path, 'cocoa/dsa_pub.pem', 'build/dg_cocoa.py', 'build/help'] app.copy_resources(*resources, use_symlinks=dev) app.copy_frameworks('build/Python', sparkle_framework_path) print("Creating the run.py file") tmpl = open('cocoa/run_template.py', 'rt').read() run_contents = tmpl.replace('{{app_path}}', app.dest) open('run.py', 'wt').write(run_contents)
def main(): args = parse_args() print("Building moneyGuru") if args.dev: print("Building in Dev mode") if args.clean: clean() if not op.exists('build'): os.mkdir('build') if args.doc: build_help() elif args.loc: build_localizations() elif args.updatepot: build_updatepot() elif args.mergepot: build_mergepot() elif args.normpo: build_normpo() elif args.cocoamod: build_cocoa_proxy_module() build_cocoa_bridging_interfaces() elif args.ext: build_ext() elif args.cocoa_compile: os.chdir('cocoa') print_and_do(cocoa_compile_command()) os.chdir('..') cocoa_app().copy_executable('cocoa/build/moneyGuru') elif args.xibless: build_cocoalib_xibless() build_xibless() else: build_normal(args.dev, not args.no_ext)
def package_windows(dev): if sys.platform != "win32": print("Qt packaging only works under Windows.") return add_to_pythonpath('.') add_to_pythonpath('qt') os.chdir('qt') from app import MusicGuru if op.exists('dist'): shutil.rmtree('dist') cmd = 'cxfreeze --base-name Win32GUI --target-name musicGuru.exe --icon ..\\images\\mg_logo.ico start.py' print_and_do(cmd) if not dev: # Copy qt plugins plugin_dest = op.join('dist', 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Compress with UPX libs = [name for name in os.listdir('dist') if op.splitext(name)[1] in ('.pyd', '.dll', '.exe')] for lib in libs: print_and_do("upx --best \"dist\\{0}\"".format(lib)) print_and_do("xcopy /Y /S /I ..\\help\\musicguru_help dist\\help") # AdvancedInstaller.com has to be in your PATH # this copying is so we don't have to re-commit installer.aip at every version change shutil.copy('installer.aip', 'installer_tmp.aip') print_and_do('AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % MusicGuru.VERSION) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip') os.chdir(op.join('..', '..'))
def build_cocoa(dev): print("Creating OS X app structure") app = cocoa_app() # We import this here because we don't want opened module to prevent us replacing .pyd files. from core.app import Application as MoneyGuruApp app_version = MoneyGuruApp.VERSION filereplace('cocoa/InfoTemplate.plist', 'build/Info.plist', version=app_version) app.create('build/Info.plist') print("Building localizations") build_localizations('cocoa') print("Building xibless UIs") build_cocoalib_xibless() build_xibless() print("Building Python extensions") build_cocoa_proxy_module() build_cocoa_bridging_interfaces() print("Building the cocoa layer") copy_embeddable_python_dylib('build') pydep_folder = op.join(app.resources, 'py') ensure_folder(pydep_folder) if dev: hardlink('cocoa/mg_cocoa.py', 'build/mg_cocoa.py') else: copy('cocoa/mg_cocoa.py', 'build/mg_cocoa.py') tocopy = ['core', 'hscommon', 'cocoalib/cocoa', 'objp'] copy_packages(tocopy, pydep_folder, create_links=dev) sys.path.insert(0, 'build') collect_stdlib_dependencies('build/mg_cocoa.py', pydep_folder) del sys.path[0] copy_sysconfig_files_for_embed(pydep_folder) if not dev: # Important: Don't ever run delete_files_with_pattern('*.py') on dev builds because you'll # be deleting all py files in symlinked folders. compileall.compile_dir(pydep_folder, force=True, legacy=True) delete_files_with_pattern(pydep_folder, '*.py') delete_files_with_pattern(pydep_folder, '__pycache__') print("Compiling with WAF") os.chdir('cocoa') print_and_do(cocoa_compile_command()) os.chdir('..') app.copy_executable('cocoa/build/moneyGuru') build_help() print("Copying resources and frameworks") resources = [ 'cocoa/dsa_pub.pem', 'build/mg_cocoa.py', 'build/help', 'data/example.moneyguru', ] + glob.glob('images/*') app.copy_resources(*resources, use_symlinks=dev) app.copy_frameworks( 'build/Python', 'cocoalib/Sparkle.framework', ) print("Creating the run.py file") tmpl = open('run_template_cocoa.py', 'rt').read() run_contents = tmpl.replace('{{app_path}}', app.dest) open('run.py', 'wt').write(run_contents)
def main(): args = parse_args() ui = args.ui if ui not in ("cocoa", "qt"): ui = "cocoa" if ISOSX else "qt" print("Building moneyGuru with UI {}".format(ui)) if args.dev: print("Building in Dev mode") if args.clean: clean() if not op.exists("build"): os.mkdir("build") if args.doc: build_help() elif args.loc: build_localizations(ui) elif args.updatepot: build_updatepot() elif args.mergepot: build_mergepot() elif args.cocoamod: build_cocoa_proxy_module() build_cocoa_bridging_interfaces() elif args.ext: build_ext() elif args.cocoa_compile: os.chdir("cocoa") print_and_do(cocoa_compile_command()) os.chdir("..") cocoa_app().copy_executable("cocoa/build/moneyGuru") elif args.xibless: build_cocoalib_xibless() build_xibless() else: build_normal(ui, args.dev, not args.no_ext)
def main(): options = parse_args() if options.dev: print("Building in Dev mode") if options.clean: for path in [ 'build', op.join('cocoa', 'build'), op.join('cocoa', 'autogen') ]: if op.exists(path): shutil.rmtree(path) if not op.exists('build'): os.mkdir('build') if options.doc: build_help() elif options.loc: build_localizations() elif options.updatepot: build_updatepot() elif options.mergepot: build_mergepot() elif options.normpo: build_normpo() elif options.cocoa_ext: build_cocoa_proxy_module() build_cocoa_bridging_interfaces() elif options.cocoa_compile: os.chdir('cocoa') print_and_do('{0} waf configure && {0} waf'.format(sys.executable)) os.chdir('..') cocoa_app().copy_executable('cocoa/build/dupeGuru') else: build_normal(options.dev)
def package_source_tgz(): print("Creating git archive") app_version = get_module_version('core') name = 'dupeguru-src-{}.tar'.format(app_version) dest = op.join('build', name) print_and_do('git archive -o {} HEAD'.format(dest)) print_and_do('gzip {}'.format(dest))
def build_cocoa(dev): print("Creating OS X app structure") app = cocoa_app() # We import this here because we don't want opened module to prevent us replacing .pyd files. from core.app import Application as MoneyGuruApp app_version = MoneyGuruApp.VERSION filereplace('cocoa/InfoTemplate.plist', 'build/Info.plist', version=app_version) app.create('build/Info.plist') print("Building localizations") build_localizations('cocoa') print("Building xibless UIs") build_cocoalib_xibless() build_xibless() print("Building Python extensions") build_cocoa_proxy_module() build_cocoa_bridging_interfaces() print("Building the cocoa layer") copy_embeddable_python_dylib('build') pydep_folder = op.join(app.resources, 'py') ensure_folder(pydep_folder) if dev: hardlink('cocoa/mg_cocoa.py', 'build/mg_cocoa.py') else: copy('cocoa/mg_cocoa.py', 'build/mg_cocoa.py') tocopy = ['core', 'hscommon', 'cocoalib/cocoa', 'objp', 'sgmllib'] copy_packages(tocopy, pydep_folder, create_links=dev) sys.path.insert(0, 'build') collect_stdlib_dependencies('build/mg_cocoa.py', pydep_folder) del sys.path[0] copy_sysconfig_files_for_embed(pydep_folder) if not dev: # Important: Don't ever run delete_files_with_pattern('*.py') on dev builds because you'll # be deleting all py files in symlinked folders. compileall.compile_dir(pydep_folder, force=True, legacy=True) delete_files_with_pattern(pydep_folder, '*.py') delete_files_with_pattern(pydep_folder, '__pycache__') print("Compiling PSMTabBarControl framework") os.chdir('psmtabbarcontrol') print_and_do('{0} waf configure && {0} waf && {0} waf build_framework'.format(sys.executable)) os.chdir('..') print("Compiling with WAF") os.chdir('cocoa') print_and_do(cocoa_compile_command()) os.chdir('..') app.copy_executable('cocoa/build/moneyGuru') build_help() print("Copying resources and frameworks") resources = [ 'cocoa/dsa_pub.pem', 'build/mg_cocoa.py', 'build/help', 'data/example.moneyguru', 'plugin_examples' ] + glob.glob('images/*') app.copy_resources(*resources, use_symlinks=dev) app.copy_frameworks( 'build/Python', 'cocoalib/Sparkle.framework', 'psmtabbarcontrol/PSMTabBarControl.framework' ) print("Creating the run.py file") tmpl = open('run_template_cocoa.py', 'rt').read() run_contents = tmpl.replace('{{app_path}}', app.dest) open('run.py', 'wt').write(run_contents)
def build_qt(dev): qrc_path = op.join('qt', 'mg.qrc') pyrc_path = op.join('qt', 'mg_rc.py') print_and_do("pyrcc4 -py3 {0} > {1}".format(qrc_path, pyrc_path)) build_help() print("Creating the run.py file") shutil.copy('run_template_qt.py', 'run.py')
def package_windows(): app_version = get_module_version("core") arch = platform.architecture()[0] # Information to pass to pyinstaller and NSIS match = re.search("[0-9]+.[0-9]+.[0-9]+", app_version) version_array = match.group(0).split(".") match = re.search("[0-9]+", arch) bits = match.group(0) if bits == "64": arch = "x64" else: arch = "x86" # include locale files if they are built otherwise exit as it will break # the localization if not op.exists("build/locale"): print("Locale files not built, exiting...") return # include help files if they are built otherwise exit as they should be included? if not op.exists("build/help"): print("Help files not built, exiting...") return # create version information file from template try: version_template = open("win_version_info.temp", "r") version_info = version_template.read() version_template.close() version_info_file = open("win_version_info.txt", "w") version_info_file.write( version_info.format(version_array[0], version_array[1], version_array[2], bits)) version_info_file.close() except Exception: print("Error creating version info file, exiting...") return # run pyinstaller from here: import PyInstaller.__main__ # UCRT dlls are included if the system has the windows kit installed PyInstaller.__main__.run([ "--name=dupeguru-win{0}".format(bits), "--windowed", "--noconfirm", "--icon=images/dgse_logo.ico", "--add-data=build/locale;locale", "--add-data=build/help;help", "--version-file=win_version_info.txt", "--paths=C:\\Program Files (x86)\\Windows Kits\\10\\Redist\\ucrt\\DLLs\\{0}" .format(arch), "run.py", ]) # remove version info file os.remove("win_version_info.txt") # Call NSIS (TODO update to not use hardcoded path) cmd = ( '"C:\\Program Files (x86)\\NSIS\\Bin\\makensis.exe" ' "/DVERSIONMAJOR={0} /DVERSIONMINOR={1} /DVERSIONPATCH={2} /DBITS={3} setup.nsi" ) print_and_do( cmd.format(version_array[0], version_array[1], version_array[2], bits))
def build_qt(): print("Building .ts files") build_all_qt_locs(op.join('qtlib', 'lang')) print("Building Qt stuff") build_all_qt_ui(op.join('qt', 'ui')) os.chdir('qt') print_and_do("pyrcc4 -py3 mg.qrc > mg_rc.py") os.chdir('..')
def build_qt(): print("Building resource file") qrc_path = op.join('qt', 'pm.qrc') pyrc_path = op.join('qt', 'pm_rc.py') print_and_do("pyrcc4 -py3 {0} > {1}".format(qrc_path, pyrc_path)) print("Creating the run.py file") runtemplate_path = op.join('qt', 'runtemplate.py') shutil.copy(runtemplate_path, 'run.py')
def build_qt(edition, dev, conf): print("Building localizations") build_localizations('qt', edition) print("Building Qt stuff") print_and_do("pyrcc4 -py3 {0} > {1}".format(op.join('qt', 'base', 'dg.qrc'), op.join('qt', 'base', 'dg_rc.py'))) fix_qt_resource_file(op.join('qt', 'base', 'dg_rc.py')) print("Creating the run.py file") filereplace(op.join('qt', 'run_template.py'), 'run.py', edition=edition)
def package_source_txz(): print("Creating git archive") app_version = get_module_version("core") name = "dupeguru-src-{}.tar".format(app_version) base_path = os.getcwd() build_path = op.join(base_path, "build") dest = op.join(build_path, name) print_and_do("git archive -o {} HEAD".format(dest)) print_and_do("xz {}".format(dest))
def build_qt(dev): print("Building localizations") build_localizations('qt') print("Building Qt stuff") print_and_do("pyrcc5 {0} > {1}".format(op.join('qt', 'dg.qrc'), op.join('qt', 'dg_rc.py'))) fix_qt_resource_file(op.join('qt', 'dg_rc.py')) build_help() print("Creating the run.py file") shutil.copy(op.join('qt', 'run_template.py'), 'run.py')
def package_windows(dev): if not ISWINDOWS: print("Qt packaging only works under Windows.") return from cx_Freeze import setup, Executable distdir = 'dist' if op.exists(distdir): shutil.rmtree(distdir) options = { 'build_exe': { 'includes': 'atexit', 'excludes': ['tkinter'], 'icon': 'images\\main_icon.ico', 'include_msvcr': True, }, 'install_exe': { 'install_dir': distdir, } } executables = [ Executable( 'run.py', base='Win32GUI', targetDir=distdir, targetName='moneyGuru.exe', ) ] setup( script_args=['install'], options=options, executables=executables ) if not dev: # Copy qt plugins plugin_dest = op.join('dist', 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) print("Copying forgotten DLLs") shutil.copy(find_in_path('msvcp110.dll'), distdir) print("Copying the rest") shutil.copytree('build\\help', 'dist\\help') shutil.copytree('build\\locale', 'dist\\locale') shutil.copytree('plugin_examples', 'dist\\plugin_examples') if not dev: # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change shutil.copy('qt\\installer.aip', 'installer_tmp.aip') print_and_do('AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % MoneyGuru.VERSION) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip')
def build_normal(): print("Building dupeGuru with UI qt") add_to_pythonpath(".") print("Building dupeGuru") build_pe_modules() print("Building localizations") build_localizations() print("Building Qt stuff") print_and_do("pyrcc5 {0} > {1}".format(Path("qt", "dg.qrc"), Path("qt", "dg_rc.py"))) fix_qt_resource_file(Path("qt", "dg_rc.py")) build_help()
def package_windows(): if not ISWINDOWS: print("Qt packaging only works under Windows.") return from cx_Freeze import setup, Executable distdir = 'dist' if op.exists(distdir): shutil.rmtree(distdir) options = { 'build_exe': { 'includes': 'atexit', 'excludes': ['tkinter'], 'icon': 'images\\main_icon.ico', 'include_msvcr': True, }, 'install_exe': { 'install_dir': distdir, } } executables = [ Executable( 'run.py', base='Win32GUI', targetDir=distdir, targetName='moneyGuru.exe', ) ] setup( script_args=['install'], options=options, executables=executables ) # Copy qt plugins plugin_dest = op.join('dist', 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) print("Copying forgotten DLLs") shutil.copy(find_in_path('msvcp110.dll'), distdir) print("Copying the rest") shutil.copytree('build\\help', 'dist\\help') shutil.copytree('build\\locale', 'dist\\locale') # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change shutil.copy('qt\\installer.aip', 'installer_tmp.aip') print_and_do('AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % MoneyGuru.VERSION) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip')
def build_cocoa(dev): print("Creating OS X app structure") app = cocoa_app() # We import this here because we don't want opened module to prevent us replacing .pyd files. from core.app import Application as MoneyGuruApp app_version = MoneyGuruApp.VERSION filereplace("cocoa/InfoTemplate.plist", "build/Info.plist", version=app_version) app.create("build/Info.plist") print("Building localizations") build_localizations("cocoa") print("Building xibless UIs") build_cocoalib_xibless() build_xibless() print("Building Python extensions") build_cocoa_proxy_module() build_cocoa_bridging_interfaces() print("Building the cocoa layer") copy_embeddable_python_dylib("build") pydep_folder = op.join(app.resources, "py") ensure_folder(pydep_folder) if dev: hardlink("cocoa/mg_cocoa.py", "build/mg_cocoa.py") else: copy("cocoa/mg_cocoa.py", "build/mg_cocoa.py") tocopy = ["core", "hscommon", "cocoalib/cocoa", "objp"] copy_packages(tocopy, pydep_folder, create_links=dev) sys.path.insert(0, "build") collect_stdlib_dependencies("build/mg_cocoa.py", pydep_folder) del sys.path[0] copy_sysconfig_files_for_embed(pydep_folder) if not dev: # Important: Don't ever run delete_files_with_pattern('*.py') on dev builds because you'll # be deleting all py files in symlinked folders. compileall.compile_dir(pydep_folder, force=True, legacy=True) delete_files_with_pattern(pydep_folder, "*.py") delete_files_with_pattern(pydep_folder, "__pycache__") print("Compiling with WAF") os.chdir("cocoa") print_and_do(cocoa_compile_command()) os.chdir("..") app.copy_executable("cocoa/build/moneyGuru") build_help() print("Copying resources and frameworks") resources = ["cocoa/dsa_pub.pem", "build/mg_cocoa.py", "build/help", "data/example.moneyguru"] + glob.glob( "images/*" ) app.copy_resources(*resources, use_symlinks=dev) app.copy_frameworks("build/Python", "cocoalib/Sparkle.framework") print("Creating the run.py file") tmpl = open("run_template_cocoa.py", "rt").read() run_contents = tmpl.replace("{{app_path}}", app.dest) open("run.py", "wt").write(run_contents)
def build_normal(): print("Building dupeGuru with UI qt") add_to_pythonpath('.') print("Building dupeGuru") build_pe_modules() print("Building localizations") build_localizations() print("Building Qt stuff") print_and_do("pyrcc5 {0} > {1}".format(op.join('qt', 'dg.qrc'), op.join('qt', 'dg_rc.py'))) fix_qt_resource_file(op.join('qt', 'dg_rc.py')) build_help()
def package_source_tgz(): venv.create('build/pkgenv', clear=True, with_pip=True) print_and_do('./build/pkgenv/bin/pip install -r requirements.txt') print_and_do('./build/pkgenv/bin/pip freeze > build/requirements.freeze') app_version = MoneyGuru.VERSION name = 'moneyguru-src-{}.tar'.format(app_version) dest = op.join('build', name) print_and_do('git archive -o {} HEAD'.format(dest)) print("Adding requirements.freeze and wrapping up") os.chdir('build') print_and_do('tar -rf {} requirements.freeze'.format(name)) print_and_do('gzip {}'.format(name)) os.chdir('..')
def package_windows(edition, dev): if not ISWINDOWS: print("Qt packaging only works under Windows.") return add_to_pythonpath('.') app_version = get_module_version('core_{}'.format(edition)) distdir = 'dist' if op.exists(distdir): shutil.rmtree(distdir) is64bit = platform.architecture()[0] == '64bit' # Since v4.2.3, cx_freeze started to falsely include tkinter in the package. We exclude it explicitly because of that. cmd = 'cxfreeze --base-name Win32GUI --target-dir "{0}" --target-name "{1}.exe" --icon {2} --exclude-modules tkinter run.py' target_name = { 'se': 'dupeGuru', 'me': 'dupeGuru ME', 'pe': 'dupeGuru PE' }[edition] icon_path = 'images\\dg{0}_logo.ico'.format(edition) print_and_do(cmd.format(distdir, target_name, icon_path)) if not dev: # Copy qt plugins plugin_dest = op.join(distdir, 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Compress with UPX if not is64bit: # UPX doesn't work on 64 bit libs = [ name for name in os.listdir(distdir) if op.splitext(name)[1] in ('.pyd', '.dll', '.exe') ] for lib in libs: print_and_do("upx --best \"{0}\"".format(op.join(distdir, lib))) help_path = op.join('build', 'help') print("Copying {} to dist\\help".format(help_path)) shutil.copytree(help_path, op.join(distdir, 'help')) locale_path = op.join('build', 'locale') print("Copying {} to dist\\locale".format(locale_path)) shutil.copytree(locale_path, op.join(distdir, 'locale')) # We don't install the VC redist as a prerequisite. We just bundle the appropriate dlls. shutil.copy(find_in_path('msvcr100.dll'), distdir) shutil.copy(find_in_path('msvcp100.dll'), distdir) # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change installer_file = 'installer64.aip' if is64bit else 'installer.aip' installer_path = op.join('qt', edition, installer_file) shutil.copy(installer_path, 'installer_tmp.aip') print_and_do( 'AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % app_version) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip') if op.exists('installer_tmp.back.aip'): os.remove('installer_tmp.back.aip')
def package_windows(dev): if op.exists('dist'): shutil.rmtree('dist') is64bit = platform.architecture()[0] == '64bit' cmd = 'cxfreeze --base-name Win32GUI --target-name "moneyGuru.exe" --icon images\\main_icon.ico run.py' print_and_do(cmd) if not dev: # Copy qt plugins plugin_dest = op.join('dist', 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Compress with UPX if not is64bit: # UPX doesn't work on 64 bit libs = [name for name in os.listdir('dist') if op.splitext(name)[1] in ('.pyd', '.dll', '.exe')] for lib in libs: print_and_do("upx --best \"dist\\{0}\"".format(lib)) shutil.copytree('build\\help', 'dist\\help') shutil.copytree('build\\locale', 'dist\\locale') shutil.copytree('plugin_examples', 'dist\\plugin_examples') shutil.copy(find_in_path('msvcr100.dll'), 'dist') shutil.copy(find_in_path('msvcp100.dll'), 'dist') if not dev: # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change installer_file = 'qt\\installer64.aip' if is64bit else 'qt\\installer.aip' shutil.copy(installer_file, 'installer_tmp.aip') print_and_do('AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % MoneyGuru.VERSION) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip')
def build_cocoa(dev): build_localizations() build_cocoa_proxy_module() build_cocoa_bridging_interfaces() app_version = get_module_version('core') cocoa_project_path = 'cocoa' filereplace(op.join(cocoa_project_path, 'InfoTemplate.plist'), op.join('build', 'Info.plist'), version=app_version) copy_embeddable_python_dylib('build') if not op.exists('build/PythonHeaders'): os.symlink(op.dirname(sysconfig.get_config_h_filename()), 'build/PythonHeaders') build_help() pydep_folder = op.join('build', 'py') if not op.exists(pydep_folder): os.mkdir(pydep_folder) shutil.copy(op.join(cocoa_project_path, 'dg_cocoa.py'), 'build') tocopy = [ 'dupeguru/core', 'dupeguru/hscommon', 'cocoa/inter', 'cocoalib/cocoa', 'objp', 'send2trash', 'hsaudiotag', ] copy_packages(tocopy, pydep_folder, create_links=dev) sys.path.insert(0, 'build') # ModuleFinder can't seem to correctly detect the multiprocessing dependency, so we have # to manually specify it. extra_deps = ['multiprocessing'] collect_stdlib_dependencies('build/dg_cocoa.py', pydep_folder, extra_deps=extra_deps) del sys.path[0] # Views are not referenced by python code, so they're not found by the collector. copy_all('build/inter/*.so', op.join(pydep_folder, 'inter')) if not dev: # Important: Don't ever run delete_files_with_pattern('*.py') on dev builds because you'll # be deleting all py files in symlinked folders. compileall.compile_dir(pydep_folder, force=True, legacy=True) delete_files_with_pattern(pydep_folder, '*.py') delete_files_with_pattern(pydep_folder, '__pycache__') print_and_do('xcodebuild')
def build_qt(dev): qrc_path = op.join('qt', 'mg.qrc') pyrc_path = op.join('qt', 'mg_rc.py') ret = print_and_do("pyrcc5 {} > {}".format(qrc_path, pyrc_path)) if ret != 0: raise RuntimeError("pyrcc5 call failed with code {}. Aborting build".format(ret)) build_help()
def build_qt(dev): qrc_path = op.join('qt', 'mg.qrc') pyrc_path = op.join('qt', 'mg_rc.py') ret = print_and_do("pyrcc5 {} > {}".format(qrc_path, pyrc_path)) if ret != 0: raise RuntimeError( "pyrcc5 call failed with code {}. Aborting build".format(ret)) build_help()
def build_qt(dev): qrc_path = op.join('qt', 'mg.qrc') pyrc_path = op.join('qt', 'mg_rc.py') ret = print_and_do("pyrcc5 {} > {}".format(qrc_path, pyrc_path)) if ret != 0: raise RuntimeError("pyrcc5 call failed with code {}. Aborting build".format(ret)) build_help() print("Creating the run.py file") shutil.copy('run_template_qt.py', 'run.py')
def build_help(dev): if dev: print("Generating devdocs") print_and_do('sphinx-build devdoc devdoc_html') print("Generating Help") current_platform = 'osx' if ISOSX else 'win' current_path = op.abspath('.') confpath = op.join(current_path, 'help', 'conf.tmpl') help_basepath = op.join(current_path, 'help', 'en') help_destpath = op.join(current_path, 'build', 'help') changelog_path = op.join(current_path, 'help', 'changelog') image_src = op.join(current_path, 'help', 'image_{}'.format(current_platform)) image_dst = op.join(current_path, 'help', 'en', 'image') if not op.exists(image_dst): os.symlink(image_src, image_dst) tixurl = "https://hardcoded.lighthouseapp.com/projects/31473-moneyguru/tickets/{0}" confrepl = {'platform': current_platform} sphinxgen.gen(help_basepath, help_destpath, changelog_path, tixurl, confrepl, confpath)
def package_windows(): app_version = get_module_version('core') arch = platform.architecture()[0] # Information to pass to pyinstaller and NSIS match = re.search('[0-9]+.[0-9]+.[0-9]+', app_version) version_array = match.group(0).split('.') match = re.search('[0-9]+', arch) bits = match.group(0) # include locale files if they are built otherwise exit as it will break # the localization if not op.exists('build/locale'): print("Locale files not built, exiting...") return # include help files if they are built otherwise exit as they should be included? if not op.exists('build/help'): print("Help files not built, exiting...") return # create version information file from template try: version_template = open("win_version_info.temp", "r") version_info = version_template.read() version_template.close() version_info_file = open("win_version_info.txt", "w") version_info_file.write( version_info.format(version_array[0], version_array[1], version_array[2], bits)) version_info_file.close() except Exception: print("Error creating version info file, exiting...") return # run pyinstaller via command line print_and_do( 'pyinstaller -w --name=dupeguru-win{0} --icon=images/dgse_logo.ico ' '--add-data "build/locale;locale" --add-data "build/help;help" ' '--version-file win_version_info.txt run.py'.format(bits)) # remove version info file os.remove('win_version_info.txt') # Call NSIS (TODO update to not use hardcoded path) cmd = ( '"C:\\Program Files (x86)\\NSIS\\Bin\\makensis.exe" ' '/DVERSIONMAJOR={0} /DVERSIONMINOR={1} /DVERSIONPATCH={2} /DBITS={3} setup.nsi' ) print_and_do( cmd.format(version_array[0], version_array[1], version_array[2], bits))
def package_source_tgz(edition): if not op.exists('deps'): print("Downloading PyPI dependencies") print_and_do('./download_deps.sh') print("Creating git archive") app_version = get_module_version('core_{}'.format(edition)) name = 'dupeguru-{}-src-{}.tar'.format(edition, app_version) dest = op.join('build', name) print_and_do('git archive -o {} HEAD'.format(dest)) print("Adding dependencies and wrapping up") print_and_do('tar -rf {} deps'.format(dest)) print_and_do('gzip {}'.format(dest))
def build_qt(dev): qrc_path = op.join('qt', 'mg.qrc') pyrc_path = op.join('qt', 'mg_rc.py') ret = print_and_do("pyrcc5 {} > {}".format(qrc_path, pyrc_path)) if ret != 0: raise RuntimeError( "pyrcc5 call failed with code {}. Aborting build".format(ret)) build_help() print("Creating the run.py file") shutil.copy('run_template_qt.py', 'run.py')
def package_source_tgz(): if not op.exists('deps'): print("Downloading PyPI dependencies") os.mkdir('deps') print_and_do('pip install --download=deps -r requirements.txt setuptools pip') app_version = MoneyGuru.VERSION name = 'moneyguru-src-{}.tar'.format(app_version) dest = op.join('build', name) print_and_do('git archive -o {} HEAD'.format(dest)) print("Adding dependencies and wrapping up") print_and_do('tar -rf {} deps'.format(dest)) print_and_do('gzip {}'.format(dest))
def package_windows(edition, dev): if not ISWINDOWS: print("Qt packaging only works under Windows.") return add_to_pythonpath('.') app_version = get_module_version('core_{}'.format(edition)) distdir = 'dist' if op.exists(distdir): shutil.rmtree(distdir) is64bit = platform.architecture()[0] == '64bit' # Since v4.2.3, cx_freeze started to falsely include tkinter in the package. We exclude it explicitly because of that. cmd = 'cxfreeze --base-name Win32GUI --target-dir "{0}" --target-name "{1}.exe" --icon {2} --exclude-modules tkinter run.py' target_name = {'se': 'dupeGuru', 'me': 'dupeGuru ME', 'pe': 'dupeGuru PE'}[edition] icon_path = 'images\\dg{0}_logo.ico'.format(edition) print_and_do(cmd.format(distdir, target_name, icon_path)) if not dev: # Copy qt plugins plugin_dest = op.join(distdir, 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Compress with UPX if not is64bit: # UPX doesn't work on 64 bit libs = [name for name in os.listdir(distdir) if op.splitext(name)[1] in ('.pyd', '.dll', '.exe')] for lib in libs: print_and_do("upx --best \"{0}\"".format(op.join(distdir, lib))) help_path = op.join('build', 'help') print("Copying {} to dist\\help".format(help_path)) shutil.copytree(help_path, op.join(distdir, 'help')) locale_path = op.join('build', 'locale') print("Copying {} to dist\\locale".format(locale_path)) shutil.copytree(locale_path, op.join(distdir, 'locale')) if is64bit: # In 64bit mode, we don't install the VC redist as a prerequisite. We just bundle the # appropriate dlls. shutil.copy(find_in_path('msvcr100.dll'), distdir) shutil.copy(find_in_path('msvcp100.dll'), distdir) # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change installer_file = 'installer64.aip' if is64bit else 'installer.aip' installer_path = op.join('qt', edition, installer_file) shutil.copy(installer_path, 'installer_tmp.aip') print_and_do('AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % app_version) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip') if op.exists('installer_tmp.back.aip'): os.remove('installer_tmp.back.aip')
def main(): options = parse_args() conf = json.load(open('conf.json')) edition = conf['edition'] ui = conf['ui'] dev = conf['dev'] if dev: print("Building in Dev mode") if options.clean: for path in [ 'build', op.join('cocoa', 'build'), op.join('cocoa', 'autogen') ]: if op.exists(path): shutil.rmtree(path) if not op.exists('build'): os.mkdir('build') if options.doc: build_help(edition) elif options.loc: build_localizations(ui, edition) elif options.updatepot: build_updatepot() elif options.mergepot: build_mergepot() elif options.normpo: build_normpo() elif options.cocoa_ext: build_cocoa_proxy_module() build_cocoa_bridging_interfaces(edition) elif options.cocoa_compile: os.chdir('cocoa') print_and_do(cocoa_compile_command(edition)) os.chdir('..') cocoa_app(edition).copy_executable('cocoa/build/dupeGuru') elif options.xibless: build_cocoalib_xibless() build_xibless(edition) else: build_normal(edition, ui, dev, conf)
def build_help(dev): if dev: print("Generating devdocs") print_and_do('sphinx-build devdoc devdoc_html') print("Generating Help") current_platform = 'osx' if ISOSX else 'win' current_path = op.abspath('.') confpath = op.join(current_path, 'help', 'conf.tmpl') help_basepath = op.join(current_path, 'help', 'en') help_destpath = op.join(current_path, 'build', 'help') changelog_path = op.join(current_path, 'help', 'changelog') image_src = op.join(current_path, 'help', 'image_{}'.format(current_platform)) image_dst = op.join(current_path, 'help', 'en', 'image') if not op.exists(image_dst): try: os.symlink(image_src, image_dst) except (NotImplementedError, OSError): # Windows crappy symlink support shutil.copytree(image_src, image_dst) tixurl = "https://github.com/hsoft/moneyguru/issues/{}" confrepl = {'platform': current_platform} sphinxgen.gen(help_basepath, help_destpath, changelog_path, tixurl, confrepl, confpath)
def package_windows(dev): from cx_Freeze import Freezer, Executable app_version = get_module_version('core') if op.exists('dist'): shutil.rmtree('dist') is64bit = platform.architecture()[0] == '64bit' exe = Executable( targetName='PdfMasher.exe', script='run.py', base='Win32GUI', icon='images\\main_icon.ico', ) freezer = Freezer( [exe], # Since v4.2.3, cx_freeze started to falsely include tkinter in the package. We exclude it explicitly because of that. excludes=['tkinter'], ) freezer.Freeze() # Now we have to copy pdfminder's cmap to our root dist dir (We'll set CMAP_PATH env at runtime) import pdfminer.cmap cmap_src = op.dirname(pdfminer.cmap.__file__) cmap_dest = op.join('dist', 'cmap') shutil.copytree(cmap_src, cmap_dest) if not dev: # Copy qt plugins plugin_dest = op.join('dist', 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Compress with UPX if not is64bit: # UPX doesn't work on 64 bit libs = [ name for name in os.listdir('dist') if op.splitext(name)[1] in ('.pyd', '.dll', '.exe') ] for lib in libs: print_and_do("upx --best \"dist\\{0}\"".format(lib)) help_path = 'build\\help' print("Copying {0} to dist\\help".format(help_path)) shutil.copytree(help_path, 'dist\\help') if is64bit: # In 64bit mode, we don't install the VC redist as a prerequisite. We just bundle the # appropriate dlls. shutil.copy(find_in_path('msvcr100.dll'), 'dist') shutil.copy(find_in_path('msvcp100.dll'), 'dist') if not dev: # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change installer_file = 'qt\\installer64.aip' if is64bit else 'qt\\installer.aip' shutil.copy(installer_file, 'installer_tmp.aip') print_and_do( 'AdvancedInstaller.com /edit installer_tmp.aip /SetVersion {}'. format(app_version)) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip')
def package_windows(dev): if sys.platform != "win32": print("Qt packaging only works under Windows.") return add_to_pythonpath('.') add_to_pythonpath('qt') os.chdir('qt') from app import MusicGuru if op.exists('dist'): shutil.rmtree('dist') cmd = 'cxfreeze --base-name Win32GUI --target-name musicGuru.exe --icon ..\\images\\mg_logo.ico start.py' print_and_do(cmd) if not dev: # Copy qt plugins plugin_dest = op.join('dist', 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Compress with UPX libs = [ name for name in os.listdir('dist') if op.splitext(name)[1] in ('.pyd', '.dll', '.exe') ] for lib in libs: print_and_do("upx --best \"dist\\{0}\"".format(lib)) print_and_do("xcopy /Y /S /I ..\\help\\musicguru_help dist\\help") # AdvancedInstaller.com has to be in your PATH # this copying is so we don't have to re-commit installer.aip at every version change shutil.copy('installer.aip', 'installer_tmp.aip') print_and_do( 'AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % MusicGuru.VERSION) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip') os.chdir(op.join('..', '..'))
def package_windows(): app_version = get_module_version('core') arch = platform.architecture()[0] # Information to pass to pyinstaller and NSIS match = re.search('[0-9]+.[0-9]+.[0-9]+', app_version) version_array = match.group(0).split('.') match = re.search('[0-9]+', arch) bits = match.group(0) # include locale files if they are built otherwise exit as it will break # the localization if not op.exists('build/locale'): print("Locale files not built, exiting...") return # include help files if they are built otherwise exit as they should be included? if not op.exists('build/help'): print("Help files not built, exiting...") return # create version information file from template try: version_template = open("win_version_info.temp", "r") version_info = version_template.read() version_template.close() version_info_file = open("win_version_info.txt", "w") version_info_file.write(version_info.format(version_array[0], version_array[1], version_array[2], bits)) version_info_file.close() except Exception: print("Error creating version info file, exiting...") return # run pyinstaller via command line print_and_do('pyinstaller -w --name=dupeguru-win{0} --icon=images/dgse_logo.ico ' '--add-data "build/locale;locale" --add-data "build/help;help" ' '--version-file win_version_info.txt run.py'.format(bits)) # remove version info file os.remove('win_version_info.txt') # Call NSIS (TODO update to not use hardcoded path) cmd = ('"C:\\Program Files (x86)\\NSIS\\Bin\\makensis.exe" ' '/DVERSIONMAJOR={0} /DVERSIONMINOR={1} /DVERSIONPATCH={2} /DBITS={3} setup.nsi') print_and_do(cmd.format(version_array[0], version_array[1], version_array[2], bits))
def main(): options = parse_args() conf = json.load(open('conf.json')) edition = conf['edition'] ui = conf['ui'] dev = conf['dev'] if dev: print("Building in Dev mode") if options.clean: for path in ['build', op.join('cocoa', 'build'), op.join('cocoa', 'autogen')]: if op.exists(path): shutil.rmtree(path) if not op.exists('build'): os.mkdir('build') if options.doc: build_help(edition) elif options.loc: build_localizations(ui, edition) elif options.updatepot: build_updatepot() elif options.mergepot: build_mergepot() elif options.normpo: build_normpo() elif options.cocoa_ext: build_cocoa_proxy_module() build_cocoa_bridging_interfaces(edition) elif options.cocoa_compile: os.chdir('cocoa') print_and_do('{0} waf configure --edition {1} && {0} waf'.format(sys.executable, edition)) os.chdir('..') cocoa_app(edition).copy_executable('cocoa/build/dupeGuru') elif options.xibless: build_cocoalib_xibless() build_xibless(edition) else: build_normal(edition, ui, dev, conf)
def main(): options = parse_args() ui = options.ui if ui not in ('cocoa', 'qt'): ui = 'cocoa' if ISOSX else 'qt' if options.dev: print("Building in Dev mode") if options.clean: for path in ['build', op.join('cocoa', 'build'), op.join('cocoa', 'autogen')]: if op.exists(path): shutil.rmtree(path) if not op.exists('build'): os.mkdir('build') if options.doc: build_help() elif options.loc: build_localizations(ui) elif options.updatepot: build_updatepot() elif options.mergepot: build_mergepot() elif options.normpo: build_normpo() elif options.cocoa_ext: build_cocoa_proxy_module() build_cocoa_bridging_interfaces() elif options.cocoa_compile: os.chdir('cocoa') print_and_do('{0} waf configure && {0} waf'.format(sys.executable)) os.chdir('..') cocoa_app().copy_executable('cocoa/build/dupeGuru') elif options.xibless: build_cocoalib_xibless() build_xibless() else: build_normal(ui, options.dev)
def package_windows(dev): from cx_Freeze import Freezer, Executable app_version = get_module_version('core') if op.exists('dist'): shutil.rmtree('dist') is64bit = platform.architecture()[0] == '64bit' exe = Executable( targetName = 'PdfMasher.exe', script = 'run.py', base = 'Win32GUI', icon = 'images\\main_icon.ico', ) freezer = Freezer( [exe], # Since v4.2.3, cx_freeze started to falsely include tkinter in the package. We exclude it explicitly because of that. excludes = ['tkinter'], ) freezer.Freeze() # Now we have to copy pdfminder's cmap to our root dist dir (We'll set CMAP_PATH env at runtime) import pdfminer.cmap cmap_src = op.dirname(pdfminer.cmap.__file__) cmap_dest = op.join('dist', 'cmap') shutil.copytree(cmap_src, cmap_dest) if not dev: # Copy qt plugins plugin_dest = op.join('dist', 'qt4_plugins') plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Compress with UPX if not is64bit: # UPX doesn't work on 64 bit libs = [name for name in os.listdir('dist') if op.splitext(name)[1] in ('.pyd', '.dll', '.exe')] for lib in libs: print_and_do("upx --best \"dist\\{0}\"".format(lib)) help_path = 'build\\help' print("Copying {0} to dist\\help".format(help_path)) shutil.copytree(help_path, 'dist\\help') if is64bit: # In 64bit mode, we don't install the VC redist as a prerequisite. We just bundle the # appropriate dlls. shutil.copy(find_in_path('msvcr100.dll'), 'dist') shutil.copy(find_in_path('msvcp100.dll'), 'dist') if not dev: # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change installer_file = 'qt\\installer64.aip' if is64bit else 'qt\\installer.aip' shutil.copy(installer_file, 'installer_tmp.aip') print_and_do('AdvancedInstaller.com /edit installer_tmp.aip /SetVersion {}'.format(app_version)) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip')
def package_source_tgz(): print("Creating git archive") app_version = get_module_version('core') name = 'dupeguru-src-{}.tar'.format(app_version) base_path = os.getcwd() build_path = op.join(base_path, 'build') dest = op.join(build_path, name) print_and_do('git archive -o {} HEAD'.format(dest)) # Now, we need to include submodules SUBMODULES = ['hscommon', 'qtlib'] for submodule in SUBMODULES: print("Adding submodule {} to archive".format(submodule)) os.chdir(submodule) archive_path = op.join(build_path, '{}.tar'.format(submodule)) print_and_do('git archive -o {} --prefix {}/ HEAD'.format(archive_path, submodule)) os.chdir(base_path) print_and_do('tar -A {} -f {}'.format(archive_path, dest)) print_and_do('gzip {}'.format(dest))
def package_source_tgz(): print("Creating git archive") app_version = get_module_version('core') name = 'dupeguru-src-{}.tar'.format(app_version) base_path = os.getcwd() build_path = op.join(base_path, 'build') dest = op.join(build_path, name) print_and_do('git archive -o {} HEAD'.format(dest)) # Now, we need to include submodules SUBMODULES = ['hscommon', 'qtlib', 'cocoalib'] for submodule in SUBMODULES: print("Adding submodule {} to archive".format(submodule)) os.chdir(submodule) archive_path = op.join(build_path, '{}.tar'.format(submodule)) print_and_do('git archive -o {} --prefix {}/ HEAD'.format( archive_path, submodule)) os.chdir(base_path) print_and_do('tar -A {} -f {}'.format(archive_path, dest)) print_and_do('gzip {}'.format(dest))
def package_windows(): from cx_Freeze import setup, Executable app_version = get_module_version('core') arch = platform.architecture()[0] buildpath = op.join('build', 'dupeguru-win{}'.format(arch)) # remove existing build directory if op.exists(buildpath): shutil.rmtree(buildpath) include_files = [] # include locale files if they are built otherwise exit as it will break # the localization if op.exists('build/locale'): include_files.append(('build/locale', 'locale')) else: print("Locale files not built, exiting...") return # include help files if they are built otherwise exit as they should be included? if op.exists('build/help'): include_files.append(('build/help', 'help')) else: print("Help files not built, exiting...") return # options for cx_Freeze # if zip_include packages is not used, the cx_Freeze packager will include # the whole PyQT5 directory options = { 'build_exe': { 'build_exe': buildpath, 'excludes': [], 'includes': ['atexit'], 'include_files': include_files, 'include_msvcr': True, 'zip_include_packages': ['*'], 'zip_exclude_packages': [] }, } # executables to build, uses se edition icon executables = [ Executable(script='run.py', base='Win32GUI', targetName='dupeguru.exe', icon='images/dgse_logo.ico', copyright='Copyright (C) 2017 Hardcoded Software') ] # call cx_freeze setup(name='dupeguru', version=app_version, description='Tool to find duplicate files on your computer.', options=options, executables=executables, script_args=['build']) # Information to pass to NSIS version_array = app_version.split('.') match = re.search('[0-9]+', arch) bits = match.group(0) # Call NSIS (TODO update to not use hardcoded path) cmd = ( '"C:\\Program Files (x86)\\NSIS\\Bin\\makensis.exe" ' '/DVERSIONMAJOR={0} /DVERSIONMINOR={1} /DVERSIONPATCH={2} /DBITS={3} setup.nsi' ) print_and_do( cmd.format(version_array[0], version_array[1], version_array[2], bits))
def package_source_tgz(edition): app_version = get_module_version('core_{}'.format(edition)) name = 'dupeguru-{}-src-{}.tar.gz'.format(edition, app_version) dest = op.join('build', name) print_and_do('git archive -o {} HEAD'.format(dest))
def package_windows(edition, dev): if not ISWINDOWS: print("Qt packaging only works under Windows.") return from cx_Freeze import setup, Executable from PyQt5.QtCore import QLibraryInfo add_to_pythonpath('.') app_version = get_module_version('core_{}'.format(edition)) distdir = 'dist' if op.exists(distdir): shutil.rmtree(distdir) if not dev: # Copy qt plugins plugin_dest = distdir plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Since v4.2.3, cx_freeze started to falsely include tkinter in the package. We exclude it explicitly because of that. options = { 'build_exe': { 'includes': 'atexit', 'excludes': ['tkinter'], 'bin_excludes': ['icudt51', 'icuin51.dll', 'icuuc51.dll'], 'icon': 'images\\dg{0}_logo.ico'.format(edition), 'include_msvcr': True, }, 'install_exe': { 'install_dir': 'dist', } } executables = [ Executable( 'run.py', base='Win32GUI', targetDir=distdir, targetName={'se': 'dupeGuru', 'me': 'dupeGuru ME', 'pe': 'dupeGuru PE'}[edition] + '.exe', ) ] setup( script_args=['install'], options=options, executables=executables ) print("Removing useless files") # Debug info that cx_freeze brings in. for fn in glob.glob(op.join(distdir, '*', '*.pdb')): os.remove(fn) print("Copying forgotten DLLs") qtlibpath = QLibraryInfo.location(QLibraryInfo.LibrariesPath) shutil.copy(op.join(qtlibpath, 'libEGL.dll'), distdir) shutil.copy(find_in_path('msvcp110.dll'), distdir) print("Copying the rest") help_path = op.join('build', 'help') print("Copying {} to dist\\help".format(help_path)) shutil.copytree(help_path, op.join(distdir, 'help')) locale_path = op.join('build', 'locale') print("Copying {} to dist\\locale".format(locale_path)) shutil.copytree(locale_path, op.join(distdir, 'locale')) # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change installer_file = 'installer.aip' installer_path = op.join('qt', edition, installer_file) shutil.copy(installer_path, 'installer_tmp.aip') print_and_do('AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % app_version) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip') if op.exists('installer_tmp.back.aip'): os.remove('installer_tmp.back.aip')
def package_windows(edition, dev): if not ISWINDOWS: print("Qt packaging only works under Windows.") return from cx_Freeze import setup, Executable from PyQt5.QtCore import QLibraryInfo add_to_pythonpath('.') app_version = get_module_version('core_{}'.format(edition)) distdir = 'dist' if op.exists(distdir): shutil.rmtree(distdir) if not dev: # Copy qt plugins plugin_dest = distdir plugin_names = ['accessible', 'codecs', 'iconengines', 'imageformats'] copy_qt_plugins(plugin_names, plugin_dest) # Since v4.2.3, cx_freeze started to falsely include tkinter in the package. We exclude it # explicitly because of that. options = { 'build_exe': { 'includes': 'atexit', 'excludes': ['tkinter'], 'bin_excludes': ['icudt51', 'icuin51.dll', 'icuuc51.dll'], 'icon': 'images\\dg{0}_logo.ico'.format(edition), 'include_msvcr': True, }, 'install_exe': { 'install_dir': 'dist', } } executables = [ Executable( 'run.py', base='Win32GUI', targetDir=distdir, targetName={'se': 'dupeGuru', 'me': 'dupeGuru ME', 'pe': 'dupeGuru PE'}[edition] + '.exe', ) ] setup( script_args=['install'], options=options, executables=executables ) print("Removing useless files") # Debug info that cx_freeze brings in. for fn in glob.glob(op.join(distdir, '*', '*.pdb')): os.remove(fn) print("Copying forgotten DLLs") qtlibpath = QLibraryInfo.location(QLibraryInfo.LibrariesPath) shutil.copy(op.join(qtlibpath, 'libEGL.dll'), distdir) shutil.copy(find_in_path('msvcp110.dll'), distdir) print("Copying the rest") help_path = op.join('build', 'help') print("Copying {} to dist\\help".format(help_path)) shutil.copytree(help_path, op.join(distdir, 'help')) locale_path = op.join('build', 'locale') print("Copying {} to dist\\locale".format(locale_path)) shutil.copytree(locale_path, op.join(distdir, 'locale')) # AdvancedInstaller.com has to be in your PATH # this is so we don'a have to re-commit installer.aip at every version change installer_file = 'installer.aip' installer_path = op.join('qt', edition, installer_file) shutil.copy(installer_path, 'installer_tmp.aip') print_and_do('AdvancedInstaller.com /edit installer_tmp.aip /SetVersion %s' % app_version) print_and_do('AdvancedInstaller.com /build installer_tmp.aip -force') os.remove('installer_tmp.aip') if op.exists('installer_tmp.back.aip'): os.remove('installer_tmp.back.aip')
def package_windows(): from cx_Freeze import setup, Executable app_version = get_module_version('core') arch = platform.architecture()[0] buildpath = op.join('build', 'dupeguru-win{}'.format(arch)) # remove existing build directory if op.exists(buildpath): shutil.rmtree(buildpath) include_files = [] # include locale files if they are built otherwise exit as it will break # the localization if op.exists('build/locale'): include_files.append(('build/locale', 'locale')) else: print("Locale files not built, exiting...") return # include help files if they are built otherwise exit as they should be included? if op.exists('build/help'): include_files.append(('build/help', 'help')) else: print("Help files not built, exiting...") return # options for cx_Freeze # if zip_include packages is not used, the cx_Freeze packager will include # the whole PyQT5 directory options = { 'build_exe': { 'build_exe': buildpath, 'excludes': [], 'includes': ['atexit', 'dbm.dumb'], 'include_files': include_files, 'include_msvcr': True, 'zip_include_packages': ['*'], 'zip_exclude_packages': [] }, } # executables to build, uses se edition icon executables = [ Executable( script='run.py', base='Win32GUI', targetName='dupeguru.exe', icon='images/dgse_logo.ico', copyright='Copyright (C) 2017 Hardcoded Software' ) ] # call cx_freeze setup( name='dupeguru', version=app_version, description='Tool to find duplicate files on your computer.', options=options, executables=executables, script_args=['build'] ) # Information to pass to NSIS version_array = app_version.split('.') match = re.search('[0-9]+', arch) bits = match.group(0) # Call NSIS (TODO update to not use hardcoded path) cmd = ('"C:\\Program Files (x86)\\NSIS\\Bin\\makensis.exe" ' '/DVERSIONMAJOR={0} /DVERSIONMINOR={1} /DVERSIONPATCH={2} /DBITS={3} setup.nsi') print_and_do(cmd.format(version_array[0], version_array[1], version_array[2], bits))
def build_cocoa(edition, dev): print("Creating OS X app structure") ed = lambda s: s.format(edition) app = cocoa_app(edition) app_version = get_module_version(ed('core_{}')) cocoa_project_path = ed('cocoa/{}') filereplace(op.join(cocoa_project_path, 'InfoTemplate.plist'), op.join('build', 'Info.plist'), version=app_version) app.create(op.join('build', 'Info.plist')) print("Building localizations") build_localizations('cocoa', edition) print("Building xibless UIs") build_cocoalib_xibless() build_xibless(edition) print("Building Python extensions") build_cocoa_proxy_module() build_cocoa_bridging_interfaces(edition) print("Building the cocoa layer") copy_embeddable_python_dylib('build') pydep_folder = op.join(app.resources, 'py') if not op.exists(pydep_folder): os.mkdir(pydep_folder) shutil.copy(op.join(cocoa_project_path, 'dg_cocoa.py'), 'build') appscript_pkgs = ['appscript', 'aem', 'mactypes', 'osax'] specific_packages = { 'se': ['core_se'], 'me': ['core_me'] + appscript_pkgs + ['hsaudiotag'], 'pe': ['core_pe'] + appscript_pkgs, }[edition] tocopy = ['core', 'hscommon', 'cocoa/inter', 'cocoalib/cocoa', 'jobprogress', 'objp', 'send2trash'] + specific_packages copy_packages(tocopy, pydep_folder, create_links=dev) sys.path.insert(0, 'build') extra_deps = None if edition == 'pe': # ModuleFinder can't seem to correctly detect the multiprocessing dependency, so we have # to manually specify it. extra_deps=['multiprocessing'] collect_stdlib_dependencies('build/dg_cocoa.py', pydep_folder, extra_deps=extra_deps) del sys.path[0] # Views are not referenced by python code, so they're not found by the collector. copy_all('build/inter/*.so', op.join(pydep_folder, 'inter')) copy_sysconfig_files_for_embed(pydep_folder) if not dev: # Important: Don't ever run delete_files_with_pattern('*.py') on dev builds because you'll # be deleting all py files in symlinked folders. compileall.compile_dir(pydep_folder, force=True, legacy=True) delete_files_with_pattern(pydep_folder, '*.py') delete_files_with_pattern(pydep_folder, '__pycache__') print("Compiling with WAF") os.chdir('cocoa') print_and_do(cocoa_compile_command(edition)) os.chdir('..') app.copy_executable('cocoa/build/dupeGuru') print("Copying resources and frameworks") image_path = ed('cocoa/{}/dupeguru.icns') resources = [image_path, 'cocoa/base/dsa_pub.pem', 'build/dg_cocoa.py', 'build/help'] app.copy_resources(*resources, use_symlinks=dev) app.copy_frameworks('build/Python', 'cocoalib/Sparkle.framework') print("Creating the run.py file") tmpl = open('cocoa/run_template.py', 'rt').read() run_contents = tmpl.replace('{{app_path}}', app.dest) open('run.py', 'wt').write(run_contents)