Skip to content

Build cryptography with an embedded OpenSSL for legacy-cipher parity - #7938

Draft
smatula wants to merge 1 commit into
calungaproject:mainfrom
smatula:cryptography-static-openssl
Draft

smatula wants to merge 1 commit into
calungaproject:mainfrom
smatula:cryptography-static-openssl

Conversation

@smatula

@smatula smatula commented Sep 11, 2026

Copy link
Copy Markdown
Contributor

Our cryptography wheel silently loses six ciphers that the official PyPI wheel supports. Point the build at the builder's static OpenSSL so the wheel comes out the same shape upstream ships.

OpenSSL dlopens its providers, and auditwheel only follows DT_NEEDED, so ossl-modules/legacy.so never makes it into the wheel. The libcrypto that does get bundled has MODULESDIR compiled to builder paths that do not exist wherever the wheel is installed, so OSSL_PROVIDER_load(NULL, "legacy") fails at import and Blowfish, CAST5, IDEA, SEED, ARC4 and RC2 all raise UnsupportedAlgorithm. Since 50.x that load failure is only a warning rather than an error, so the import succeeds and wheel-check passes on a wheel with six dead ciphers.

cryptography is not on the index at the moment. 1dcf826 (2026-08-31) removed it along with pillow, pyarrow, numpy, lxml, cffi and freeze-core and denylisted all seven against re-publication as transitive dependencies, "due to incompatible native library bundling". For cryptography, this is that incompatible bundling. So this file is a precondition for putting the package back, not a repair to something users are pulling today.

Upstream sidesteps the whole problem by embedding OpenSSL in _rust.abi3.so. OPENSSL_DIR and OPENSSL_STATIC make openssl-sys do the same against the static, no-module OpenSSL the builder now provides.

Measured on cryptography 50.0.1, built from sdist in the builder image, repaired with auditwheel, exercised on python:3.12-slim:

                _rust.abi3.so   bundled libs        legacy ciphers
today            6.32 MB        libcrypto, libssl   1 of 7
with this       13.66 MB        none                7 of 7
PyPI wheel      14.39 MB        none                7 of 7

the 1 that works today is TripleDES, which lives in the default
provider. DT_NEEDED on the extension module is identical to PyPI's.

Requires the builder image to provide /opt/_internal/static-openssl. That prefix is deliberately off PKG_CONFIG_PATH and out of ldconfig, so this file is the only thing that reaches it and no other package is affected. The path is a version-independent symlink.

Like overrides/settings/pillow.yaml, this does not itself trigger a rebuild -- identify-packages only diffs onboarded_packages -- so it takes effect on cryptography's next version bump.

Assisted-by: Claude Opus 5 noreply@anthropic.com

Summary by Sourcery

Configure cryptography to statically embed OpenSSL so redistributed wheels retain full legacy-cipher support.

Bug Fixes:

  • Build cryptography wheels with all legacy-provider ciphers available, matching the official PyPI wheel behavior.

Enhancements:

  • Configure cryptography to embed the builder-provided static OpenSSL rather than dynamically bundling OpenSSL libraries and providers.

Build:

  • Add cryptography build settings that use the version-independent static OpenSSL installation.

Our cryptography wheel silently loses six ciphers that the official PyPI
wheel supports. Point the build at the builder's static OpenSSL so the
wheel comes out the same shape upstream ships.

OpenSSL dlopens its providers, and auditwheel only follows DT_NEEDED, so
ossl-modules/legacy.so never makes it into the wheel. The libcrypto that
does get bundled has MODULESDIR compiled to builder paths that do not
exist wherever the wheel is installed, so OSSL_PROVIDER_load(NULL,
"legacy") fails at import and Blowfish, CAST5, IDEA, SEED, ARC4 and RC2
all raise UnsupportedAlgorithm. Since 50.x that load failure is only a
warning rather than an error, so the import succeeds and wheel-check
passes on a wheel with six dead ciphers.

cryptography is not on the index at the moment. 1dcf826 (2026-08-31)
removed it along with pillow, pyarrow, numpy, lxml, cffi and freeze-core
and denylisted all seven against re-publication as transitive
dependencies, "due to incompatible native library bundling". For
cryptography, this is that incompatible bundling. So this file is a
precondition for putting the package back, not a repair to something
users are pulling today.

Upstream sidesteps the whole problem by embedding OpenSSL in
_rust.abi3.so. OPENSSL_DIR and OPENSSL_STATIC make openssl-sys do the
same against the static, no-module OpenSSL the builder now provides.

Measured on cryptography 50.0.1, built from sdist in the builder image,
repaired with auditwheel, exercised on python:3.12-slim:

                    _rust.abi3.so   bundled libs        legacy ciphers
    today            6.32 MB        libcrypto, libssl   1 of 7
    with this       13.66 MB        none                7 of 7
    PyPI wheel      14.39 MB        none                7 of 7

  the 1 that works today is TripleDES, which lives in the default
  provider. DT_NEEDED on the extension module is identical to PyPI's.

Requires the builder image to provide /opt/_internal/static-openssl. That
prefix is deliberately off PKG_CONFIG_PATH and out of ldconfig, so this
file is the only thing that reaches it and no other package is affected.
The path is a version-independent symlink.

Like overrides/settings/pillow.yaml, this does not itself trigger a
rebuild -- identify-packages only diffs onboarded_packages -- so it takes
effect on cryptography's next version bump.

Assisted-by: Claude Opus 5 <noreply@anthropic.com>
@sourcery-ai

sourcery-ai Bot commented Sep 11, 2026

Copy link
Copy Markdown

Reviewer's Guide

Adds cryptography build settings that embed the builder’s static, no-module OpenSSL into _rust.abi3.so instead of bundling dynamic OpenSSL libraries, preserving all legacy ciphers and avoiding broken provider paths in repaired wheels.

File-Level Changes

Change Details Files
Configure cryptography’s Rust/OpenSSL build to statically embed the builder-provided OpenSSL, matching upstream wheel linkage and avoiding provider-discovery failures.
  • Set OPENSSL_DIR to the version-independent static OpenSSL prefix.
  • Enable static OpenSSL selection with OPENSSL_STATIC.
  • Document the legacy-provider, auditwheel, builder-image, and re-onboarding prerequisites.
overrides/settings/cryptography.yaml

Tips and commands

Interacting with Sourcery

  • Trigger a new review: Comment @sourcery-ai review on the pull request.
  • Continue discussions: Reply directly to Sourcery's review comments.
  • Generate a GitHub issue from a review comment: Ask Sourcery to create an
    issue from a review comment by replying to it. You can also reply to a
    review comment with @sourcery-ai issue to create an issue from it.
  • Generate a pull request title: Write @sourcery-ai anywhere in the pull
    request title to generate a title at any time. You can also comment
    @sourcery-ai title on the pull request to (re-)generate the title at any time.
  • Generate a pull request summary: Write @sourcery-ai summary anywhere in
    the pull request body to generate a PR summary at any time exactly where you
    want it. You can also comment @sourcery-ai summary on the pull request to
    (re-)generate the summary at any time.
  • Generate reviewer's guide: Comment @sourcery-ai guide on the pull
    request to (re-)generate the reviewer's guide at any time.
  • Resolve all Sourcery comments: Comment @sourcery-ai resolve on the
    pull request to resolve all Sourcery comments. Useful if you've already
    addressed all the comments and don't want to see them anymore.
  • Dismiss all Sourcery reviews: Comment @sourcery-ai dismiss on the pull
    request to dismiss all existing Sourcery reviews. Especially useful if you
    want to start fresh with a new review - don't forget to comment
    @sourcery-ai review to trigger a new review!

Customizing Your Experience

Access your dashboard to:

  • Enable or disable review features such as the Sourcery-generated pull request
    summary, the reviewer's guide, and others.
  • Change the review language.
  • Add, remove or edit custom review instructions.
  • Adjust other review settings.

Getting Help

@jvulgan

jvulgan commented Sep 14, 2026

Copy link
Copy Markdown
Contributor

LGTM

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants