Skip to content

test(integration): take the suite's ports from the environment - #434

Open
freshtonic wants to merge 1 commit into
mainfrom
chore/test-ports-from-env
Open

test(integration): take the suite's ports from the environment#434
freshtonic wants to merge 1 commit into
mainfrom
chore/test-ports-from-env

Conversation

@freshtonic

@freshtonic freshtonic commented Jul 30, 2026

Copy link
Copy Markdown
Contributor

Prerequisite for the three plaintext-leak fixes stacked on top of this branch (CIP-3680, CIP-3682, CIP-3688). Small and standalone.

Why

The four ports the integration suite connects to were hardcoded (pub const PROXY: u16 = 6432), so only one copy of the suite could run at a time. Fixing three separate Proxy defects in parallel needs three Proxy instances against three databases, which needs three sets of ports.

What

PROXY, PROXY_METRICS_PORT, PG_PORT and PG_TLS_PORT become LazyLock<u16> reading CS_TEST_PROXY_PORT, CS_TEST_PROXY_METRICS_PORT, CS_TEST_PG_PORT and CS_TEST_PG_TLS_PORT, each falling back to its current value. An unconfigured run behaves exactly as before.

A malformed value panics rather than falling back to the default. Silently retargeting the whole suite at whatever else happens to be listening on 6432 is the one failure mode that looks like a pass.

Note for anyone running the suite on custom ports

mise exec overrides CS_DATABASE__PORT from the parent shell, because mise.toml sets it to 5532:

$ CS_DATABASE__PORT=5599 mise exec -- env | grep CS_DATABASE__PORT
CS_DATABASE__PORT=5532

Re-assert it inside: mise exec -- env CS_DATABASE__PORT=5541 cargo …. The CS_TEST_* variables introduced here are not set in mise.toml, so they pass through fine. Tests that run the migrate CLI in-process also need CS_SERVER__PORT set, since that CLI reads it to find Proxy.

Testing

cargo check -p cipherstash-proxy-integration --tests clean; cargo fmt clean. Behaviour with no environment variables set is unchanged by construction.

Acknowledgment

By submitting this pull request, I confirm that CipherStash can use, modify, copy, and redistribute this contribution, under the terms of CipherStash's choice.

Summary by CodeRabbit

  • New Features
    • Integration-test proxy and database ports can now be configured through environment variables, with defaults available when not specified.
  • Bug Fixes
    • Updated connection handling across integration tests to use the runtime-configured ports.
  • Tests
    • Maintained coverage for encryption, mapping, querying, multitenancy, diagnostics, and connection-resilience scenarios with the updated configuration.

The four ports the integration suite connects to were hardcoded, so only
one copy of the suite could run at a time. Several agents each working on
a different Proxy defect need their own Proxy and PostgreSQL, which means
their own ports.

Each port now reads an environment variable and falls back to the current
value, so an unconfigured run behaves exactly as before. A malformed
value panics rather than falling back: silently retargeting the whole
suite at whatever else is listening on 6432 is the one failure that looks
like a pass.
@coderabbitai

coderabbitai Bot commented Jul 30, 2026

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

Integration-test ports now resolve from environment variables with defaults, and all affected proxy/Postgres connection helpers and tests dereference the new lazy port values.

Changes

Runtime integration test port configuration

Layer / File(s) Summary
Runtime port declarations and shared helpers
packages/cipherstash-proxy-integration/src/common.rs
Proxy, metrics, Postgres, and TLS ports use environment-backed LazyLock<u16> values, with updated shared connection and database-port fallback logic.
Resilience and diagnostics connections
packages/cipherstash-proxy-integration/src/connection_resilience.rs, packages/cipherstash-proxy-integration/src/diagnostics.rs, packages/cipherstash-proxy-integration/src/disable_mapping.rs
Tests pass dereferenced proxy or metrics ports to connection helpers.
Mapping, encryption, and query tests
packages/cipherstash-proxy-integration/src/{decrypt,insert,map*}/*, packages/cipherstash-proxy-integration/src/eql_regression.rs
TLS setup uses *PROXY across mapping, encryption, EQL, insert, and index tests.
Protocol and multitenant tests
packages/cipherstash-proxy-integration/src/{migrate,multitenant,simple_protocol}/*, packages/cipherstash-proxy-integration/src/{passthrough,pipeline,schema_change,set_keyset_error}.rs, packages/cipherstash-proxy-integration/src/update/*
Migration, multitenant, protocol, passthrough, schema, keyset, and update tests use dereferenced proxy ports.
Select and JSONB tests
packages/cipherstash-proxy-integration/src/select/*
Select, JSONB, predicate, catalog, indexing, and unmappable-query tests use *PROXY for TLS connections.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Possibly related PRs

Suggested reviewers: tobyhede

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly captures the main change: integration test ports are now read from environment variables.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch chore/test-ports-from-env

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/cipherstash-proxy-integration/src/common.rs`:
- Around line 67-72: Update the environment-variable parsing match around
std::env::var in the port configuration logic to distinguish
VarError::NotPresent from VarError::NotUnicode. Return the default only for
NotPresent, and panic with a clear misconfiguration message for NotUnicode
instead of silently using the default port.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 57d425b3-424d-411d-9b31-8cd230844ffb

📥 Commits

Reviewing files that changed from the base of the PR and between 15b7f99 and bf72e2f.

📒 Files selected for processing (49)
  • packages/cipherstash-proxy-integration/src/common.rs
  • packages/cipherstash-proxy-integration/src/connection_resilience.rs
  • packages/cipherstash-proxy-integration/src/decrypt/insert_returning.rs
  • packages/cipherstash-proxy-integration/src/diagnostics.rs
  • packages/cipherstash-proxy-integration/src/disable_mapping.rs
  • packages/cipherstash-proxy-integration/src/empty_result.rs
  • packages/cipherstash-proxy-integration/src/encryption_sanity.rs
  • packages/cipherstash-proxy-integration/src/eql_regression.rs
  • packages/cipherstash-proxy-integration/src/extended_protocol_error_messages.rs
  • packages/cipherstash-proxy-integration/src/insert/insert_domain_type.rs
  • packages/cipherstash-proxy-integration/src/insert/insert_with_params.rs
  • packages/cipherstash-proxy-integration/src/map_concat.rs
  • packages/cipherstash-proxy-integration/src/map_literals.rs
  • packages/cipherstash-proxy-integration/src/map_match_index.rs
  • packages/cipherstash-proxy-integration/src/map_nulls.rs
  • packages/cipherstash-proxy-integration/src/map_ope_index_order.rs
  • packages/cipherstash-proxy-integration/src/map_ope_index_where.rs
  • packages/cipherstash-proxy-integration/src/map_ore_index_order.rs
  • packages/cipherstash-proxy-integration/src/map_ore_index_where.rs
  • packages/cipherstash-proxy-integration/src/map_params.rs
  • packages/cipherstash-proxy-integration/src/map_unique_index.rs
  • packages/cipherstash-proxy-integration/src/migrate/mod.rs
  • packages/cipherstash-proxy-integration/src/multitenant/contention.rs
  • packages/cipherstash-proxy-integration/src/multitenant/ore_order.rs
  • packages/cipherstash-proxy-integration/src/multitenant/set_keyset_id.rs
  • packages/cipherstash-proxy-integration/src/multitenant/set_keyset_name.rs
  • packages/cipherstash-proxy-integration/src/passthrough.rs
  • packages/cipherstash-proxy-integration/src/pipeline.rs
  • packages/cipherstash-proxy-integration/src/schema_change.rs
  • packages/cipherstash-proxy-integration/src/select/distinct_order_by.rs
  • packages/cipherstash-proxy-integration/src/select/indexing.rs
  • packages/cipherstash-proxy-integration/src/select/jsonb_array_elements.rs
  • packages/cipherstash-proxy-integration/src/select/jsonb_containment_index.rs
  • packages/cipherstash-proxy-integration/src/select/jsonb_fusion_gaps.rs
  • packages/cipherstash-proxy-integration/src/select/jsonb_path_query.rs
  • packages/cipherstash-proxy-integration/src/select/jsonb_selector_param_types.rs
  • packages/cipherstash-proxy-integration/src/select/operator_backed_predicates.rs
  • packages/cipherstash-proxy-integration/src/select/operator_class_shapes.rs
  • packages/cipherstash-proxy-integration/src/select/pg_catalog.rs
  • packages/cipherstash-proxy-integration/src/select/select_where_in.rs
  • packages/cipherstash-proxy-integration/src/select/select_where_jsonb.rs
  • packages/cipherstash-proxy-integration/src/select/unmappable.rs
  • packages/cipherstash-proxy-integration/src/set_keyset_error.rs
  • packages/cipherstash-proxy-integration/src/simple_protocol/error_handling.rs
  • packages/cipherstash-proxy-integration/src/simple_protocol/map_literals.rs
  • packages/cipherstash-proxy-integration/src/simple_protocol/map_nulls.rs
  • packages/cipherstash-proxy-integration/src/simple_protocol/multiple_statements.rs
  • packages/cipherstash-proxy-integration/src/update/update_domain_type.rs
  • packages/cipherstash-proxy-integration/src/update/update_with_reused_param.rs

Comment on lines +67 to +72
match std::env::var(var) {
Ok(value) => value
.parse()
.unwrap_or_else(|_| panic!("{var} must be a port number, got: {value:?}")),
Err(_) => default,
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo "== locate file =="
git ls-files | rg '(^|/)common\.rs$' || true

echo "== target file context =="
if [ -f packages/cipherstash-proxy-integration/src/common.rs ]; then
  nl -ba packages/cipherstash-proxy-integration/src/common.rs | sed -n '1,140p'
fi

echo "== env var usage in proxy integration =="
rg -n 'port_from_env|PORT|DEFAULT|LazyLock' packages/cipherstash-proxy-integration/src packages/cipherstash-proxy-integration -S || true

echo "== rust compiler availability =="
command -v rustc && rustc --version || true

Repository: cipherstash/proxy

Length of output: 324


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo "== target file context =="
cat -n packages/cipherstash-proxy-integration/src/common.rs | sed -n '1,140p'

echo "== env var usage in proxy integration =="
rg -n 'port_from_env|PORT|DEFAULT|LazyLock|std::env::var' packages/cipherstash-proxy-integration/src packages/cipherstash-proxy-integration -S || true

echo "== deterministic VarError text check from Rust std source on installed SDK if available =="
if command -v rustc >/dev/null 2>&1; then
  rustc --version
else
  echo "rustc unavailable"
fi

echo "== local source VarError matches if Rust toolchain source is reachable =="
for d in /usr/local/rustup/toolchains/*/lib/rustlib/src/rust/library/std/src/sys/unix/uw8.rs /usr/local/rustup/toolchains/*/lib/rustlib/src/rust/library/std/src/env.rs; do
  [ -d "$d" ] && { echo "FOUND $d"; find "$d" -maxdepth 2 -type f | head -20; } || true
done
rg -n 'enum VarError|VarError::NotUnicode|NotUnicode|std::env::var' /usr/local/rustup/toolchains/*/lib/rustlib/src/rust/library/std/src 2>/dev/null | head -80 || true

Repository: cipherstash/proxy

Length of output: 22363


🌐 Web query:

Rust std::env::var VarError NotUnicode documentation

💡 Result:

In Rust, std::env::VarError is an enum used to represent errors that occur when interacting with environment variables, particularly when using the std::env::var function [1][2]. The VarError::NotUnicode variant specifically indicates that while the requested environment variable was found, its value does not contain valid Unicode data [1][3]. The NotUnicode variant carries an OsString payload, which allows the program to access the original, non-Unicode data [1][4]. For scenarios where you need to handle environment variables that may contain non-Unicode data without triggering this error, the standard library provides the std::env::var_os function, which returns an Option instead of a Result<String, VarError> [5][6].

Citations:


Do not treat non-UTF-8 environment values as unset.

std::env::var returns VarError::NotUnicode(_) when the variable is present but contains invalid UTF-8, and Err(_) => default silently selects the default port. Match VarError::NotPresent separately and panic for NotUnicode so this explicit misconfiguration fails instead of connecting to the wrong instance.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/cipherstash-proxy-integration/src/common.rs` around lines 67 - 72,
Update the environment-variable parsing match around std::env::var in the port
configuration logic to distinguish VarError::NotPresent from
VarError::NotUnicode. Return the default only for NotPresent, and panic with a
clear misconfiguration message for NotUnicode instead of silently using the
default port.

@freshtonic
freshtonic requested a review from tobyhede July 30, 2026 01:14
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.

1 participant