Skip to content

feat: add optional native-tls support as alternative to rustls#8037

Open
r0x0d wants to merge 3 commits intoblock:mainfrom
r0x0d:native-tls-support
Open

feat: add optional native-tls support as alternative to rustls#8037
r0x0d wants to merge 3 commits intoblock:mainfrom
r0x0d:native-tls-support

Conversation

@r0x0d
Copy link
Contributor

@r0x0d r0x0d commented Mar 20, 2026

Summary

Add a native-tls Cargo feature across all crates as an alternative to the default rustls TLS backend. This enables building goose against the platform's native TLS stack (OpenSSL on Linux, Secure Transport on macOS, SChannel on Windows), which is required for Fedora/RHEL packaging where vendoring rustls/aws-lc-rs is problematic.

Changes by crate:

goose (core):

  • Add default-tls and native-tls feature groups gating reqwest, rmcp, sqlx, jsonwebtoken, and oauth2 TLS backends
  • Set reqwest, rmcp, sqlx, oauth2 to default-features = false so TLS backend is selected purely via features
  • Switch jsonwebtoken to default-features = false with explicit use_pem; gate aws_lc_rs (default-tls) vs rust_crypto (native-tls)
  • Conditionally compile Identity::from_pem (rustls) vs Identity::from_pkcs8_pem (native-tls) in api_client.rs

goose-server:

  • Add default-tls and native-tls feature groups gating reqwest, tokio-tungstenite, axum-server, rustls, aws-lc-rs, and openssl
  • Make rustls, aws-lc-rs optional (default-tls); add openssl optional (native-tls)
  • Refactor tls.rs: extract generate_self_signed_cert() and sha256_fingerprint() helpers; use cfg-gated TlsConfig type alias (RustlsConfig vs OpenSSLConfig)
  • Cfg-gate rustls crypto provider initialization in agent.rs and lapstone.rs
  • Cfg-gate axum_server::bind_rustls vs bind_openssl in agent.rs
  • Add TLS integration tests in tests/tls_test.rs

goose-cli:

  • Add default-tls and native-tls feature groups gating reqwest and sigstore-verification TLS backends, forwarding to goose and goose-mcp

goose-mcp:

  • Add default-tls and native-tls features gating reqwest TLS backend; remove hardcoded rustls feature from reqwest dep

goose-acp:

  • Add default-tls and native-tls feature forwarding to goose dep

CI and build:

  • Remove scripts/check-no-native-tls.sh (no longer applicable)
  • Remove banned TLS crate check from ci.yml and Justfile

Usage:

Default build (rustls, unchanged behavior) cargo build

Build with native-tls (OpenSSL) cargo build --no-default-features --features native-tls,code-mode

Made-with: Cursor

Testing

Tested by running cargo test locally and verifying that native-tls was being used, both with default features and without it.

Related Issues

Relates to #ISSUE_ID
Discussion: LINK (if any)

Screenshots/Demos (for UX changes)

Before:

After:

Add a `native-tls` Cargo feature across all crates as an alternative to
the default `rustls` TLS backend. This enables building goose against
the platform's native TLS stack (OpenSSL on Linux, Secure Transport on
macOS, SChannel on Windows), which is required for Fedora/RHEL packaging
where vendoring rustls/aws-lc-rs is problematic.

Changes by crate:

goose (core):
- Add `default-tls` and `native-tls` feature groups gating reqwest,
  rmcp, sqlx, jsonwebtoken, and oauth2 TLS backends
- Set reqwest, rmcp, sqlx, oauth2 to default-features = false so TLS
  backend is selected purely via features
- Switch jsonwebtoken to default-features = false with explicit use_pem;
  gate aws_lc_rs (default-tls) vs rust_crypto (native-tls)
- Conditionally compile Identity::from_pem (rustls) vs
  Identity::from_pkcs8_pem (native-tls) in api_client.rs

goose-server:
- Add `default-tls` and `native-tls` feature groups gating reqwest,
  tokio-tungstenite, axum-server, rustls, aws-lc-rs, and openssl
- Make rustls, aws-lc-rs optional (default-tls); add openssl optional
  (native-tls)
- Refactor tls.rs: extract generate_self_signed_cert() and
  sha256_fingerprint() helpers; use cfg-gated TlsConfig type alias
  (RustlsConfig vs OpenSSLConfig)
- Cfg-gate rustls crypto provider initialization in agent.rs and
  lapstone.rs
- Cfg-gate axum_server::bind_rustls vs bind_openssl in agent.rs
- Add TLS integration tests in tests/tls_test.rs

goose-cli:
- Add `default-tls` and `native-tls` feature groups gating reqwest and
  sigstore-verification TLS backends, forwarding to goose and goose-mcp

goose-mcp:
- Add `default-tls` and `native-tls` features gating reqwest TLS
  backend; remove hardcoded rustls feature from reqwest dep

goose-acp:
- Add `default-tls` and `native-tls` feature forwarding to goose dep

CI and build:
- Remove scripts/check-no-native-tls.sh (no longer applicable)
- Remove banned TLS crate check from ci.yml and Justfile

Usage:
  # Default build (rustls, unchanged behavior)
  cargo build

  # Build with native-tls (OpenSSL)
  cargo build --no-default-features --features native-tls,code-mode

Co-authored-by: Claude <noreply@anthropic.com>
Signed-off-by: Rodolfo Olivieri <rolivier@redhat.com>
Made-with: Cursor
Copy link

@chatgpt-codex-connector chatgpt-codex-connector bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: ad16ab9720

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Propagate TLS feature selection from goose-acp to goose-mcp so standalone
goose-acp-server builds retain HTTPS support for builtin extensions.

Use openssl to convert any PEM key format (PKCS#1, SEC1, PKCS#8) to PKCS#8
in the native-tls path, so existing mTLS setups with traditional RSA or EC
keys continue to work.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Signed-off-by: Rodolfo Olivieri <rolivier@redhat.com>
Copy link

@chatgpt-codex-connector chatgpt-codex-connector bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 59bc733759

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

…itation

Change all rustls cfg guards from `not(feature = "native-tls")` to
`feature = "default-tls"` so the rustls path does not compile when
neither TLS backend is enabled (e.g. --no-default-features). Gate the
tls module and its consumers on having at least one TLS backend, and
return a clear error if TLS is requested at runtime without one.

Add module-level documentation to tls.rs explaining that the native-tls
feature uses OpenSSL for the server listener via axum-server.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Signed-off-by: Rodolfo Olivieri <rolivier@redhat.com>
Copy link

@chatgpt-codex-connector chatgpt-codex-connector bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 3049f47a47

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Comment on lines +17 to +21
#[cfg(feature = "default-tls")]
pub type TlsConfig = axum_server::tls_rustls::RustlsConfig;

#[cfg(feature = "native-tls")]
pub type TlsConfig = axum_server::tls_openssl::OpenSSLConfig;

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Make native-tls mutually exclusive with default-tls

Cargo features are additive, and crates/goose-server/Cargo.toml still keeps default-tls in the package defaults. As a result, the natural cargo build -p goose-server --features native-tls invocation enables both backends at once; in this file that means two TlsConfig aliases and two config bindings are compiled, and crates/goose-server/src/commands/agent.rs also pulls in both listener branches. The new backend therefore does not build unless callers know to add --no-default-features, which defeats the advertised “alternative to rustls” workflow for packagers and scripts.

Useful? React with 👍 / 👎.

Comment on lines +105 to +109
#[cfg(not(any(feature = "default-tls", feature = "native-tls")))]
{
anyhow::bail!(
"TLS was requested but no TLS backend is enabled. \
Enable the `default-tls` or `native-tls` feature."

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Default no-TLS builds to HTTP instead of bailing at startup

This new runtime guard makes the --no-default-features --features code-mode build fail on every ordinary launch, because crates/goose-server/src/configuration.rs:80-81 still defaults tls to true. In that configuration the binary now exits here unless the operator already knows to set GOOSE_SERVER__TLS=false, so the newly compilable HTTP-only build is unusable out of the box and will break smoke tests or packaging checks that simply start goosed with defaults.

Useful? React with 👍 / 👎.

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