TenantAtlas/specs/237-provider-boundary-hardening/quickstart.md
ahmido bd26e209de
Some checks failed
Main Confidence / confidence (push) Failing after 57s
feat: harden provider boundaries (#273)
## Summary
- add the provider boundary catalog, boundary support types, and guardrails for platform-core versus provider-owned seams
- harden provider gateway, identity resolution, operation registry, and start-gate behavior to require explicit provider bindings
- add unit and feature coverage for boundary classification, runtime preservation, unsupported paths, and platform-core leakage guards
- add the full Spec Kit artifact set for spec 237 and update roadmap/spec-candidate tracking

## Validation
- `cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Unit/Providers/ProviderBoundaryClassificationTest.php tests/Unit/Providers/ProviderBoundaryGuardrailTest.php tests/Feature/Providers/ProviderBoundaryHardeningTest.php tests/Feature/Providers/UnsupportedProviderBoundaryPathTest.php tests/Feature/Guards/ProviderBoundaryPlatformCoreGuardTest.php`
- `cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Unit/Providers/ProviderGatewayTest.php tests/Unit/Providers/ProviderIdentityResolverTest.php tests/Unit/Providers/ProviderOperationStartGateTest.php`
- `cd apps/platform && ./vendor/bin/sail bin pint --dirty --format agent`
- browser smoke: `http://localhost/admin/provider-connections?tenant_id=18000000-0000-4000-8000-000000000180` loaded with the local smoke user, the empty-state CTA reached the canonical create route, and cancel returned to the scoped list

Co-authored-by: Ahmed Darrazi <ahmed.darrazi@live.de>
Reviewed-on: #273
2026-04-24 21:05:37 +00:00

85 lines
4.6 KiB
Markdown

# Quickstart: Provider Boundary Hardening
## Goal
Implement the first provider-boundary hardening slice without introducing a second-provider runtime, schema churn, or new operator-facing UI.
## Implementation Sequence
1. Done: added the config-backed seam ownership catalog and the small boundary helper layer.
2. Done: removed Graph request-option shaping from `ProviderIdentityResolution` and kept it inside provider-owned gateway/options resolver seams.
3. Done: split shared operation definitions from provider bindings in `ProviderOperationRegistry` and made `ProviderOperationStartGate` consume explicit bindings.
4. Done: kept remaining Microsoft-first identity details documented as explicit current-release exceptions instead of widening into schema and UI neutrality.
5. Done: added focused unit and feature coverage proving current Microsoft behavior still works and unsupported shared-boundary paths fail explicitly.
## Suggested Code Areas
```text
apps/platform/app/Support/Providers/Boundary/
apps/platform/config/provider_boundaries.php
apps/platform/app/Services/Providers/
apps/platform/app/Services/Graph/
apps/platform/app/Models/ProviderConnection.php
apps/platform/tests/Unit/Providers/
apps/platform/tests/Feature/Providers/
```
## Authoritative Seam Inventory
- `provider.gateway_runtime`
- `provider.identity_resolution`
- `provider.connection_resolution`
- `provider.operation_registry`
- `provider.operation_start_gate`
## Verification Commands
Run the narrowest proving lane first:
```bash
cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Unit/Providers/ProviderBoundaryClassificationTest.php tests/Unit/Providers/ProviderBoundaryGuardrailTest.php
```
Then run the bounded runtime and unsupported-path proof:
```bash
cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Feature/Providers/ProviderBoundaryHardeningTest.php tests/Feature/Providers/UnsupportedProviderBoundaryPathTest.php
```
Then run the feature-guard proof that blocks provider leakage in platform-core seams:
```bash
cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Feature/Guards/ProviderBoundaryPlatformCoreGuardTest.php
```
If PHP files were added or changed, finish with formatting:
```bash
cd apps/platform && ./vendor/bin/sail bin pint --dirty --format agent
```
## Review Focus
- Confirm `ProviderIdentityResolution` no longer emits Graph-shaped request options directly.
- Confirm `ProviderGateway` and `MicrosoftGraphOptionsResolver` are the provider-owned seams that now assemble Graph request options.
- Confirm `ProviderOperationRegistry` keeps platform-core operation definition separate from provider binding.
- Confirm unsupported touched seams fail explicitly instead of inheriting Microsoft default behavior.
- Confirm `entra_tenant_id` and platform app identity remain explicit current-release exceptions, not silent platform-core truth.
- Confirm no second-provider runtime, schema rewrite, or UI surface slipped into the slice.
## Guardrail Close-Out
- Validation completed before final handoff:
- `cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Unit/Providers/ProviderBoundaryClassificationTest.php tests/Unit/Providers/ProviderBoundaryGuardrailTest.php tests/Feature/Providers/ProviderBoundaryHardeningTest.php tests/Feature/Providers/UnsupportedProviderBoundaryPathTest.php tests/Feature/Guards/ProviderBoundaryPlatformCoreGuardTest.php`
- `cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Unit/Providers/ProviderGatewayTest.php tests/Unit/Providers/ProviderIdentityResolverTest.php tests/Unit/Providers/ProviderOperationStartGateTest.php`
- `cd apps/platform && ./vendor/bin/sail bin pint --dirty --format agent`
- Guardrails checked:
- No new Graph contract path.
- No new provider runtime or marketplace abstraction.
- `ProviderIdentityResolution` no longer exposes `graphOptions()` or `client_request_id`.
- `ProviderOperationRegistry` keeps platform-core definitions separate from explicit provider bindings.
- `ProviderOperationStartGate` blocks unsupported provider bindings with `provider_binding_unsupported` instead of falling back to Microsoft.
- No undocumented provider-shaped exception on touched platform-core seams.
- Close-out decision: `document-in-feature`. The remaining Microsoft-first identity and target-scope details are bounded in `provider_boundaries.php`, covered by guardrails, and intentionally left for the next provider identity/target-scope neutrality spec.
- Bounded follow-up: deeper provider identity and target-scope neutrality remains a separate next spec; no schema rewrite, UI vocabulary rewrite, or second-provider runtime is included here.