mirror of
				https://github.com/python/cpython.git
				synced 2025-10-31 13:41:24 +00:00 
			
		
		
		
	
		
			
				
	
	
		
			249 lines
		
	
	
	
		
			8.3 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			249 lines
		
	
	
	
		
			8.3 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
| from .constants import *
 | |
| 
 | |
| URL_BASE = "https://www.python.org/ftp/python/"
 | |
| 
 | |
| XYZ_VERSION = f"{VER_MAJOR}.{VER_MINOR}.{VER_MICRO}"
 | |
| WIN32_VERSION = f"{VER_MAJOR}.{VER_MINOR}.{VER_MICRO}.{VER_FIELD4}"
 | |
| FULL_VERSION = f"{VER_MAJOR}.{VER_MINOR}.{VER_MICRO}{VER_SUFFIX}"
 | |
| 
 | |
| 
 | |
| def _not_empty(n, key=None):
 | |
|     result = []
 | |
|     for i in n:
 | |
|         if key:
 | |
|             i_l = i[key]
 | |
|         else:
 | |
|             i_l = i
 | |
|         if not i_l:
 | |
|             continue
 | |
|         result.append(i)
 | |
|     return result
 | |
| 
 | |
| 
 | |
| def calculate_install_json(ns, *, for_embed=False, for_test=False):
 | |
|     TARGET = "python.exe"
 | |
|     TARGETW = "pythonw.exe"
 | |
| 
 | |
|     SYS_ARCH = {
 | |
|         "win32": "32bit",
 | |
|         "amd64": "64bit",
 | |
|         "arm64": "64bit", # Unfortunate, but this is how it's spec'd
 | |
|     }[ns.arch]
 | |
|     TAG_ARCH = {
 | |
|         "win32": "-32",
 | |
|         "amd64": "-64",
 | |
|         "arm64": "-arm64",
 | |
|     }[ns.arch]
 | |
| 
 | |
|     COMPANY = "PythonCore"
 | |
|     DISPLAY_NAME = "Python"
 | |
|     TAG_SUFFIX = ""
 | |
|     ALIAS_PREFIX = "python"
 | |
|     ALIAS_WPREFIX = "pythonw"
 | |
|     FILE_PREFIX = "python-"
 | |
|     FILE_SUFFIX = f"-{ns.arch}"
 | |
|     DISPLAY_TAGS = [{
 | |
|         "win32": "32-bit",
 | |
|         "amd64": "",
 | |
|         "arm64": "ARM64",
 | |
|     }[ns.arch]]
 | |
| 
 | |
|     if for_test:
 | |
|         # Packages with the test suite come under a different Company
 | |
|         COMPANY = "PythonTest"
 | |
|         DISPLAY_TAGS.append("with tests")
 | |
|         FILE_SUFFIX = f"-test-{ns.arch}"
 | |
|     if for_embed:
 | |
|         # Embeddable distro comes under a different Company
 | |
|         COMPANY = "PythonEmbed"
 | |
|         TARGETW = None
 | |
|         ALIAS_PREFIX = None
 | |
|         DISPLAY_TAGS.append("embeddable")
 | |
|         # Deliberately name the file differently from the existing distro
 | |
|         # so we can republish old versions without replacing files.
 | |
|         FILE_SUFFIX = f"-embeddable-{ns.arch}"
 | |
|     if ns.include_freethreaded:
 | |
|         # Free-threaded distro comes with a tag suffix
 | |
|         TAG_SUFFIX = "t"
 | |
|         TARGET = f"python{VER_MAJOR}.{VER_MINOR}t.exe"
 | |
|         TARGETW = f"pythonw{VER_MAJOR}.{VER_MINOR}t.exe"
 | |
|         DISPLAY_TAGS.append("freethreaded")
 | |
|         FILE_SUFFIX = f"t-{ns.arch}"
 | |
| 
 | |
|     FULL_TAG = f"{VER_MAJOR}.{VER_MINOR}.{VER_MICRO}{VER_SUFFIX}{TAG_SUFFIX}"
 | |
|     FULL_ARCH_TAG = f"{FULL_TAG}{TAG_ARCH}"
 | |
|     XY_TAG = f"{VER_MAJOR}.{VER_MINOR}{TAG_SUFFIX}"
 | |
|     XY_ARCH_TAG = f"{XY_TAG}{TAG_ARCH}"
 | |
|     X_TAG = f"{VER_MAJOR}{TAG_SUFFIX}"
 | |
|     X_ARCH_TAG = f"{X_TAG}{TAG_ARCH}"
 | |
| 
 | |
|     # Tag used in runtime ID (for side-by-side install/updates)
 | |
|     ID_TAG = XY_ARCH_TAG
 | |
|     # Tag shown in 'py list' output
 | |
|     DISPLAY_TAG = f"{XY_TAG}-dev{TAG_ARCH}" if VER_SUFFIX else XY_ARCH_TAG
 | |
| 
 | |
|     DISPLAY_SUFFIX = ", ".join(i for i in DISPLAY_TAGS if i)
 | |
|     if DISPLAY_SUFFIX:
 | |
|         DISPLAY_SUFFIX = f" ({DISPLAY_SUFFIX})"
 | |
|     DISPLAY_VERSION = f"{XYZ_VERSION}{VER_SUFFIX}{DISPLAY_SUFFIX}"
 | |
| 
 | |
|     STD_RUN_FOR = []
 | |
|     STD_ALIAS = []
 | |
|     STD_PEP514 = []
 | |
|     STD_START = []
 | |
|     STD_UNINSTALL = []
 | |
| 
 | |
|     # The list of 'py install <TAG>' tags that will match this runtime.
 | |
|     # Architecture should always be included here because PyManager will add it.
 | |
|     INSTALL_TAGS = [
 | |
|         FULL_ARCH_TAG,
 | |
|         XY_ARCH_TAG,
 | |
|         X_ARCH_TAG,
 | |
|         # X_TAG and XY_TAG doesn't include VER_SUFFIX, so create -dev versions
 | |
|         f"{XY_TAG}-dev{TAG_ARCH}" if XY_TAG and VER_SUFFIX else "",
 | |
|         f"{X_TAG}-dev{TAG_ARCH}" if X_TAG and VER_SUFFIX else "",
 | |
|     ]
 | |
| 
 | |
|     # Generate run-for entries for each target.
 | |
|     # Again, include architecture because PyManager will add it.
 | |
|     for base in [
 | |
|         {"target": TARGET},
 | |
|         {"target": TARGETW, "windowed": 1},
 | |
|     ]:
 | |
|         if not base["target"]:
 | |
|             continue
 | |
|         STD_RUN_FOR.append({**base, "tag": FULL_ARCH_TAG})
 | |
|         if XY_TAG:
 | |
|             STD_RUN_FOR.append({**base, "tag": XY_ARCH_TAG})
 | |
|         if X_TAG:
 | |
|             STD_RUN_FOR.append({**base, "tag": X_ARCH_TAG})
 | |
|         if VER_SUFFIX:
 | |
|             STD_RUN_FOR.extend([
 | |
|                 {**base, "tag": f"{XY_TAG}-dev{TAG_ARCH}" if XY_TAG else ""},
 | |
|                 {**base, "tag": f"{X_TAG}-dev{TAG_ARCH}" if X_TAG else ""},
 | |
|             ])
 | |
| 
 | |
|     # Generate alias entries for each target. We need both arch and non-arch
 | |
|     # versions as well as windowed/non-windowed versions to make sure that all
 | |
|     # necessary aliases are created.
 | |
|     if ALIAS_PREFIX:
 | |
|         for prefix, base in [
 | |
|             (ALIAS_PREFIX, {"target": TARGET}),
 | |
|             (f"{ALIAS_PREFIX}w", {"target": TARGETW, "windowed": 1}),
 | |
|         ]:
 | |
|             if not base["target"]:
 | |
|                 continue
 | |
|             if XY_TAG:
 | |
|                 STD_ALIAS.extend([
 | |
|                     {**base, "name": f"{prefix}{XY_TAG}.exe"},
 | |
|                     {**base, "name": f"{prefix}{XY_ARCH_TAG}.exe"},
 | |
|                 ])
 | |
|             if X_TAG:
 | |
|                 STD_ALIAS.extend([
 | |
|                     {**base, "name": f"{prefix}{X_TAG}.exe"},
 | |
|                     {**base, "name": f"{prefix}{X_ARCH_TAG}.exe"},
 | |
|                 ])
 | |
| 
 | |
|     STD_PEP514.append({
 | |
|         "kind": "pep514",
 | |
|         "Key": rf"{COMPANY}\{ID_TAG}",
 | |
|         "DisplayName": f"{DISPLAY_NAME} {DISPLAY_VERSION}",
 | |
|         "SupportUrl": "https://www.python.org/",
 | |
|         "SysArchitecture": SYS_ARCH,
 | |
|         "SysVersion": VER_DOT,
 | |
|         "Version": FULL_VERSION,
 | |
|         "InstallPath": {
 | |
|             "_": "%PREFIX%",
 | |
|             "ExecutablePath": f"%PREFIX%{TARGET}",
 | |
|             # WindowedExecutablePath is added below
 | |
|         },
 | |
|         "Help": {
 | |
|             "Online Python Documentation": {
 | |
|                 "_": f"https://docs.python.org/{VER_DOT}/"
 | |
|             },
 | |
|         },
 | |
|     })
 | |
| 
 | |
|     STD_START.append({
 | |
|         "kind": "start",
 | |
|         "Name": f"{DISPLAY_NAME} {VER_DOT}{DISPLAY_SUFFIX}",
 | |
|         "Items": [
 | |
|             {
 | |
|                 "Name": f"{DISPLAY_NAME} {VER_DOT}{DISPLAY_SUFFIX}",
 | |
|                 "Target": f"%PREFIX%{TARGET}",
 | |
|                 "Icon": f"%PREFIX%{TARGET}",
 | |
|             },
 | |
|             {
 | |
|                 "Name": f"{DISPLAY_NAME} {VER_DOT} Online Documentation",
 | |
|                 "Icon": r"%SystemRoot%\System32\SHELL32.dll",
 | |
|                 "IconIndex": 13,
 | |
|                 "Target": f"https://docs.python.org/{VER_DOT}/",
 | |
|             },
 | |
|             # IDLE and local documentation items are added below
 | |
|         ],
 | |
|     })
 | |
| 
 | |
|     if TARGETW:
 | |
|         STD_PEP514[0]["InstallPath"]["WindowedExecutablePath"] = f"%PREFIX%{TARGETW}"
 | |
| 
 | |
|     if ns.include_idle:
 | |
|         STD_START[0]["Items"].append({
 | |
|             "Name": f"IDLE (Python {VER_DOT}{DISPLAY_SUFFIX})",
 | |
|             "Target": f"%PREFIX%{TARGETW or TARGET}",
 | |
|             "Arguments": r'"%PREFIX%Lib\idlelib\idle.pyw"',
 | |
|             "Icon": r"%PREFIX%Lib\idlelib\Icons\idle.ico",
 | |
|             "IconIndex": 0,
 | |
|         })
 | |
|         STD_START[0]["Items"].append({
 | |
|             "Name": f"PyDoc (Python {VER_DOT}{DISPLAY_SUFFIX})",
 | |
|             "Target": f"%PREFIX%{TARGET}",
 | |
|             "Arguments": "-m pydoc -b",
 | |
|             "Icon": r"%PREFIX%Lib\idlelib\Icons\idle.ico",
 | |
|             "IconIndex": 0,
 | |
|         })
 | |
| 
 | |
|     if ns.include_html_doc:
 | |
|         STD_PEP514[0]["Help"]["Main Python Documentation"] = {
 | |
|             "_": rf"%PREFIX%Doc\html\index.html",
 | |
|         }
 | |
|         STD_START[0]["Items"].append({
 | |
|             "Name": f"{DISPLAY_NAME} {VER_DOT} Manuals{DISPLAY_SUFFIX}",
 | |
|             "Target": r"%PREFIX%Doc\html\index.html",
 | |
|         })
 | |
|     elif ns.include_chm:
 | |
|         STD_PEP514[0]["Help"]["Main Python Documentation"] = {
 | |
|             "_": rf"%PREFIX%Doc\{PYTHON_CHM_NAME}",
 | |
|         }
 | |
|         STD_START[0]["Items"].append({
 | |
|             "Name": f"{DISPLAY_NAME} {VER_DOT} Manuals{DISPLAY_SUFFIX}",
 | |
|             "Target": "%WINDIR%hhc.exe",
 | |
|             "Arguments": rf"%PREFIX%Doc\{PYTHON_CHM_NAME}",
 | |
|         })
 | |
| 
 | |
|     STD_UNINSTALL.append({
 | |
|         "kind": "uninstall",
 | |
|         # Other settings will pick up sensible defaults
 | |
|         "Publisher": "Python Software Foundation",
 | |
|         "HelpLink": f"https://docs.python.org/{VER_DOT}/",
 | |
|     })
 | |
| 
 | |
|     data = {
 | |
|         "schema": 1,
 | |
|         "id": f"{COMPANY.lower()}-{ID_TAG}",
 | |
|         "sort-version": FULL_VERSION,
 | |
|         "company": COMPANY,
 | |
|         "tag": DISPLAY_TAG,
 | |
|         "install-for": _not_empty(INSTALL_TAGS),
 | |
|         "run-for": _not_empty(STD_RUN_FOR, "tag"),
 | |
|         "alias": _not_empty(STD_ALIAS, "name"),
 | |
|         "shortcuts": [
 | |
|             *STD_PEP514,
 | |
|             *STD_START,
 | |
|             *STD_UNINSTALL,
 | |
|         ],
 | |
|         "display-name": f"{DISPLAY_NAME} {DISPLAY_VERSION}",
 | |
|         "executable": rf".\{TARGET}",
 | |
|         "url": f"{URL_BASE}{XYZ_VERSION}/{FILE_PREFIX}{FULL_VERSION}{FILE_SUFFIX}.zip"
 | |
|     }
 | |
| 
 | |
|     return data
 | 
