## Summary
No distinct bypass or validated alternate trigger was found for CVE-2026-59826. The parent vulnerability was specific to the Enterprise database-routing destination creation endpoint persisting attacker-controlled H2 connection details without the usual H2 validation. The fixed v1.61.2 code calls `driver/validate-db-details!` on that destination path before insertion, and bounded variant checks did not identify another remote API path in the tested product images that both persists unsafe H2 details and remains reachable on the fixed version.

## Fix Coverage / Assumptions
The original fix relies on the invariant that every code path that persists H2 connection details without testing reachability must still run a validation-only safety check before storing those details. The fixed commit is `74032e5e0a5a70dc45a6a744d37b9ba24eee8d01`.

The fix explicitly covers the vulnerable database-routing path:

- `enterprise/backend/src/metabase_enterprise/database_routing/api.clj`, `POST /api/ee/database-routing/destination-database`: the fixed path iterates over each submitted destination, calls `driver/validate-db-details!` with the router database engine and submitted destination details, and returns HTTP 400 for any thrown validation error before `t2/insert-returning-instances! :model/Database` persists the destination.
- `src/metabase/driver/h2.clj`: the H2 driver's existing safety checks were moved into `driver/validate-db-details! :h2`. This method rejects H2 as a data warehouse when `*allow-testing-h2-connections*` is false, rejects parsed `INIT` properties, and rejects malicious property values containing semicolons or scripting-language markers. `driver/can-connect? :h2` now delegates to the same validation method.

Important non-destination paths were inspected and/or tested:

- Normal database creation/update (`POST /api/database`, `PUT /api/database/:id`) already calls `test-connection-details` / `test-database-connection`, which reaches `driver/can-connect? :h2` and therefore the same H2 validation. Runtime checks confirmed both vulnerable v1.61.1 and fixed v1.61.2 reject unsafe H2 creation with `H2 is not supported as a data warehouse`.
- Serialization import has a dedicated `assert-not-h2!` guard in `src/metabase/warehouses/models/database.clj`, rejecting imported `Database` entities whose engine is H2 before the generic serdes load path can persist them. Runtime API probing did not reach a successful import path in either tested image; source inspection shows the H2-specific guard exists in both v1.61.1 and v1.61.2.
- Runtime `/api/ee/advanced-config` upload was not available in the tested v1.61.1/v1.61.2 product images. Boot/config-file import source code also calls `driver.u/can-connect-with-details?` before creating or updating non-deletion database entries, which would hit H2 validation.

The fix does not add a global database-model before-insert hook for `validate-db-details!`; instead it patches the known unsafe destination-database endpoint and relies on other entry points' existing validation/guard logic. The variant search therefore focused on other remote/admin entry points that can write `:model/Database :details`.

## Variant / Alternate Trigger
No confirmed variant/bypass was found. The tested candidate entry points were:

1. `POST /api/database` with an H2 `details.db` value containing the same escaped-semicolon SQL primitive used in the parent reproduction. Both v1.61.1 and v1.61.2 returned HTTP 400 with `H2 is not supported as a data warehouse`; no database row was created and no marker file was written.
2. `POST /api/ee/serialization/import` with a crafted serialization archive containing a `Database` YAML entity with `engine: h2` and the same malicious `details.db` value. The HTTP import request failed in both tested images before importing the database. Source review of the exact fixed tag and vulnerable tag shows `serdes/load-one! "Database"` calls `assert-not-h2!`, which rejects H2 database entities during import.
3. Probe for `POST /api/ee/advanced-config/` runtime upload. The endpoint returned HTTP 404 in both tested v1.61.1 and v1.61.2 images. Source review of the config-file database loader also shows it tests connectivity before database creation/update.

Relevant code paths and anchors:

- Parent fixed sink coverage: `enterprise/backend/src/metabase_enterprise/database_routing/api.clj`, destination validation and insertion logic around lines 38-63 in the fixed tag.
- H2 validation sink: `src/metabase/driver/h2.clj`, `driver/validate-db-details! :h2` and `driver/can-connect? :h2` around lines 118-140 in the fixed tag.
- Normal database API: `src/metabase/warehouses/api.clj`, `POST /api/database` and `PUT /api/database/:id` call connection testing around lines 864-898 and 967-1011 in the fixed tag.
- Config-file database loader: `enterprise/backend/src/metabase_enterprise/advanced_config/file/databases.clj`, `driver.u/can-connect-with-details?` before insert/update around lines 79-89 in the fixed tag.
- Serialization import guard: `src/metabase/warehouses/models/database.clj`, `assert-not-h2!` and `serdes/load-one! "Database"` around lines 573-586 in the fixed tag.

## Impact
- Package/component affected by the parent issue: Metabase Enterprise database routing and H2 database connection-detail validation.
- Tested versions: vulnerable image `metabase/metabase-enterprise:v1.61.1` and fixed image `metabase/metabase-enterprise:v1.61.2`.
- Variant-stage outcome: no additional exploitable component was confirmed. The parent impact remains critical for vulnerable database-routing builds, but no separate fixed-version bypass impact was reproduced.

## Impact Parity
- Disclosed/claimed maximum impact for the parent: arbitrary code execution / arbitrary Java code execution on the Metabase server by an authenticated administrator through unsafe H2 connection properties.
- Reproduced impact from this variant run: none for a distinct variant. The variant script executed bounded alternate-entrypoint checks and observed rejection/unavailability rather than server-side marker creation.
- Parity: `none` for a distinct variant/bypass.
- Not demonstrated: no fixed-version code execution, file write, or persisted unsafe H2 database through an alternate route was demonstrated.

## Root Cause
The parent root cause was not a flaw in H2 parsing alone; it was a Metabase trust-boundary problem where an authenticated administrator could send H2 details over a remote API path that persisted them without invoking the existing safety gate. When the persisted destination database was later opened through `/api/dataset`, H2 interpreted an escaped semicolon in a non-`INIT` property value and executed attacker-controlled SQL.

The fixed commit `74032e5e0a5a70dc45a6a744d37b9ba24eee8d01` closes the specific missing-validation path by introducing/using `driver/validate-db-details!` and invoking it in `POST /api/ee/database-routing/destination-database`. The variant search attempted to find another remote/admin entry point that persisted the same unsafe details without validation. The candidate paths either already funneled into `driver/can-connect? :h2`/`validate-db-details!`, had an independent H2 rejection guard, or were unavailable in the tested fixed product.

## Reproduction Steps
1. Run `bundle/vuln_variant/reproduction_steps.sh` from the bundle root, or set `PRUVA_ROOT` to the bundle directory and run the script from any directory.
2. The script starts real Metabase Enterprise Docker images `v1.61.1` and `v1.61.2`, initializes an admin account, and performs side-by-side candidate checks against both versions:
   - `POST /api/database` with the malicious H2 escaped-semicolon connection string.
   - `POST /api/ee/serialization/import` with a crafted H2 `Database` serialization archive.
   - `POST /api/ee/advanced-config/` endpoint availability probe.
3. Expected evidence for this negative result: the script completes without crashing and exits `1`. Logs show both normal database creation requests are rejected, serialization import does not create a marker, and the advanced-config endpoint is unavailable in both tested images.

## Evidence
Primary evidence locations:

- `bundle/logs/vuln_variant/reproduction_steps.log` — full runtime log for the last variant run.
- `bundle/vuln_variant/runtime_manifest.json` — structured runtime manifest for the variant checks.
- `bundle/logs/vuln_variant/source_versions.txt` — source/image identity for the tested vulnerable and fixed targets.
- `bundle/logs/vuln_variant/fixed_tag_variant_code_anchors.log` — source anchor excerpts for fix coverage and candidate guards.
- Candidate request/response logs:
  - `bundle/logs/vuln_variant/vuln_database_create.request.json`
  - `bundle/logs/vuln_variant/vuln_database_create.response.json`
  - `bundle/logs/vuln_variant/fixed_database_create.request.json`
  - `bundle/logs/vuln_variant/fixed_database_create.response.json`
  - `bundle/logs/vuln_variant/vuln_serialization_import.response.txt`
  - `bundle/logs/vuln_variant/fixed_serialization_import.response.txt`
  - `bundle/logs/vuln_variant/vuln_advanced_config_probe.response.txt`
  - `bundle/logs/vuln_variant/fixed_advanced_config_probe.response.txt`

Key runtime excerpts from the verified script runs:

```text
vuln candidate 1 status=400 body={"message":"H2 is not supported as a data warehouse"}
fixed candidate 1 status=400 body={"message":"H2 is not supported as a data warehouse"}
vuln candidate 2 status=500 body={"via":[{"type":"java.lang.ClassCastException", ...
fixed candidate 2 status=500 body={"via":[{"type":"java.lang.ClassCastException", ...
vuln advanced-config probe status=404 body="API endpoint does not exist."
fixed advanced-config probe status=404 body="API endpoint does not exist."
No variant bypass confirmed. Candidate entry points were blocked or unavailable on the fixed product.
```

Source identity from `source_versions.txt`:

```text
vulnerable_image=metabase/metabase-enterprise:v1.61.1
vulnerable_tag_commit=770276bdddee78aed8ee0f75cdddd61a744664d4
fixed_image=metabase/metabase-enterprise:v1.61.2
fixed_tag_commit=74032e5e0a5a70dc45a6a744d37b9ba24eee8d01
patch_commit=74032e5e0a5a70dc45a6a744d37b9ba24eee8d01
```

Environment details: Docker was used to run vendor Metabase Enterprise images. As in the parent reproduction, the script starts Metabase through a small wrapper that stubs premium token validation only so Enterprise routes can be exercised in the isolated environment; product API handlers, H2 driver code, and connection validation remain from the vendor images.

## Recommendations / Next Steps
- Keep the current destination-database fix, because it correctly adds validation to the previously missing persistence path.
- For defense in depth, consider adding a model-level or centralized persistence guard for database details, e.g. invoking `driver/validate-db-details!` in a safe before-insert/before-update path for `:model/Database` whenever details originate from a user/admin-controlled API or import surface. Internal/sample-database flows that legitimately need H2 can explicitly bind the existing H2 testing allow flag.
- Add regression tests covering every `:model/Database` write surface that accepts external/admin input: database-routing destinations, normal database create/update, config-file database initialization, and serialization import.
- Ensure serialization import failures surface the intended H2-specific rejection rather than unrelated logging failures in the tested environment, so future security regression checks can verify `assert-not-h2!` directly through the API.

## Additional Notes
- The variant reproduction script was run twice successfully. Both runs completed without crashing and exited `1`, which is the expected negative-result code for this stage.
- Fewer than three runtime-confirmed candidates were available because the normal database API and serialization import were the only distinct remote/admin database-detail entry points present in the tested images besides the parent database-routing path; the runtime advanced-config upload endpoint referenced by later source code was not present in v1.61.1/v1.61.2 images.
- This report does not claim a new vulnerability. It documents bounded testing and source review showing no fixed-version bypass was confirmed.
