diff --git a/tests/unit/forklift/test_legacy.py b/tests/unit/forklift/test_legacy.py index 8ce484b10952..eda0ed3c5ac4 100644 --- a/tests/unit/forklift/test_legacy.py +++ b/tests/unit/forklift/test_legacy.py @@ -2734,6 +2734,16 @@ def test_upload_attestation_fails_without_oidc_publisher( "macosx_11_0_x86_64", "macosx_10_15_arm64", "macosx_11_10_universal2", + "ios_13_0_arm64_iphoneos", + "ios_13_0_arm64_iphonesimulator", + "ios_13_0_x86_64_iphonesimulator", + "ios_15_4_arm64_iphoneos", + "ios_15_4_arm64_iphonesimulator", + "ios_15_4_x86_64_iphonesimulator", + "android_27_armeabi_v7a", + "android_27_arm64_v8a", + "android_27_x86", + "android_27_x86_64", # A real tag used by e.g. some numpy wheels ( "macosx_10_6_intel.macosx_10_9_intel.macosx_10_9_x86_64." diff --git a/tests/unit/utils/test_wheel.py b/tests/unit/utils/test_wheel.py index 72424737b92b..b575c814d84b 100644 --- a/tests/unit/utils/test_wheel.py +++ b/tests/unit/utils/test_wheel.py @@ -57,6 +57,46 @@ "cryptography-42.0.5-cp37-abi3-macosx_10_12_universal2.whl", ["CPython 3.7+", "macOS 10.12+ universal2 (ARM64, x86-64)"], ), + ( + "cryptography-42.0.5-cp313-cp313-android_27_armeabi_v7a.whl", + ["Android API level 27+ ARM EABI v7a", "CPython 3.13"], + ), + ( + "cryptography-42.0.5-cp313-cp313-android_27_arm64_v8a.whl", + ["Android API level 27+ ARM64 v8a", "CPython 3.13"], + ), + ( + "cryptography-42.0.5-cp313-cp313-android_27_x86.whl", + ["Android API level 27+ x86", "CPython 3.13"], + ), + ( + "cryptography-42.0.5-cp313-cp313-android_27_x86_64.whl", + ["Android API level 27+ x86-64", "CPython 3.13"], + ), + ( + "cryptography-42.0.5-cp313-abi3-android_16_armeabi_v7a.whl", + ["Android API level 16+ ARM EABI v7a", "CPython 3.13+"], + ), + ( + "cryptography-42.0.5-cp313-cp313-iOS_15_6_arm64_iphoneos.whl", + ["CPython 3.13", "iOS 15.6+ ARM64 Device"], + ), + ( + "cryptography-42.0.5-cp313-cp313-iOS_15_6_arm64_iphonesimulator.whl", + ["CPython 3.13", "iOS 15.6+ ARM64 Simulator"], + ), + ( + "cryptography-42.0.5-cp313-cp313-iOS_15_6_x86_64_iphonesimulator.whl", + ["CPython 3.13", "iOS 15.6+ x86-64 Simulator"], + ), + ( + "cryptography-42.0.5-cp313-abi3-iOS_13_0_arm64_iphoneos.whl", + ["CPython 3.13+", "iOS 13.0+ ARM64 Device"], + ), + ( + "cryptography-42.0.5-cp313-abi3-iOS_13_0_arm64_iphonesimulator.whl", + ["CPython 3.13+", "iOS 13.0+ ARM64 Simulator"], + ), ( "pgf-1.0-pp27-pypy_73-manylinux2010_x86_64.whl", ["PyPy", "manylinux: glibc 2.12+ x86-64"], diff --git a/warehouse/forklift/legacy.py b/warehouse/forklift/legacy.py index 342fc0ec74db..fc41676ed38d 100644 --- a/warehouse/forklift/legacy.py +++ b/warehouse/forklift/legacy.py @@ -154,6 +154,22 @@ "15", } +_ios_platform_re = re.compile( + r"ios_(\d+)_(\d+)_(?P.*)_(iphoneos|iphonesimulator)" +) +_ios_arches = { + "arm64", + "x86_64", +} + +_android_platform_re = re.compile(r"android_(\d+)_(?P.*)") +_android_arches = { + "armeabi_v7a", + "arm64_v8a", + "x86", + "x86_64", +} + # manylinux pep600 and musllinux pep656 are a little more complicated: _linux_platform_re = re.compile(r"(?P(many|musl))linux_(\d+)_(\d+)_(?P.*)") _jointlinux_arches = { @@ -184,6 +200,12 @@ def _valid_platform_tag(platform_tag): return m.group("arch") in _musllinux_arches if m and m.group("libc") == "many": return m.group("arch") in _manylinux_arches + m = _ios_platform_re.match(platform_tag) + if m and m.group("arch") in _ios_arches: + return True + m = _android_platform_re.match(platform_tag) + if m and m.group("arch") in _android_arches: + return True return False diff --git a/warehouse/utils/wheel.py b/warehouse/utils/wheel.py index fa0e8e216500..ef699641e205 100644 --- a/warehouse/utils/wheel.py +++ b/warehouse/utils/wheel.py @@ -40,11 +40,25 @@ re.compile(r"^macosx_(\d+)_(\d+)_(.*?)$"), lambda m: f"macOS {m.group(1)}.{m.group(2)}+ {_normalize_arch(m.group(3))}", ), + ( + re.compile(r"^android_(\d+)_(.*?)$"), + lambda m: f"Android API level {m.group(1)}+ {_normalize_arch(m.group(2))}", + ), + ( + re.compile(r"^ios_(\d+)_(\d+)_(.*?)_iphoneos$"), + lambda m: f"iOS {m.group(1)}.{m.group(2)}+ {_normalize_arch(m.group(3))} Device", # noqa: E501 + ), + ( + re.compile(r"^ios_(\d+)_(\d+)_(.*?)_iphonesimulator$"), + lambda m: f"iOS {m.group(1)}.{m.group(2)}+ {_normalize_arch(m.group(3))} Simulator", # noqa: E501 + ), ] _ARCHS = { "amd64": "x86-64", "aarch64": "ARM64", + "armeabi_v7a": "ARM EABI v7a", + "arm64_v8a": "ARM64 v8a", "x86_64": "x86-64", "intel": "Intel (x86-64, i386)", "fat": "fat (i386, PPC)",