-
Notifications
You must be signed in to change notification settings - Fork 0
feat(auth): enforce purpose-bound route authorization #34
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Draft
seonghobae
wants to merge
55
commits into
develop
Choose a base branch
from
feat/purpose-bound-authorization
base: develop
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Draft
Changes from all commits
Commits
Show all changes
55 commits
Select commit
Hold shift + click to select a range
7e46767
feat(auth): enforce purpose-bound route authorization
seonghobae 0bd9723
test(auth): verify immutable authorization evidence
seonghobae 5d9e6ec
style(auth): normalize unittest mock import
seonghobae 23813c7
fix(auth): bound command correlation evidence
seonghobae f1aa012
fix(auth): preserve bounded command correlation
seonghobae ecb2359
fix(auth): retain tenant provenance and require caller kind
seonghobae 4dfdc09
docs: track authorization gap integration status
seonghobae a778e3b
fix: bind authorization evidence to tenant scope
seonghobae c656ab9
fix(auth): reject malformed close bodies before authorization
seonghobae 4868dba
fix(auth): reject caller-constructed decisions
seonghobae 010c896
fix(auth): preserve decision provenance
seonghobae 7b7bdda
fix(auth): seal authorization decisions
seonghobae a8d6ffd
fix(auth): remove forgeable issuance marker
seonghobae 5b7bfc2
fix(auth): authorize malformed period closes
seonghobae 89ae72d
test(auth): reserve reconciliation completion authority
seonghobae 1593f2b
feat(auth): reserve reconciliation completion permission
seonghobae 9e6fa3f
test(auth): version reconciliation permission expansion
seonghobae f9814c0
fix(auth): version expanded operation policy
seonghobae 6222aac
docs(auth): version reconciliation completion authority
seonghobae 5e2f742
docs(auth): doctor reconciliation completion policy expansion
seonghobae 270bc60
docs: canonicalize reconciliation authorization references
seonghobae 1f9da05
test(auth): require request-scoped principal resolution
seonghobae 0fa27a8
ci(auth): repair request-scoped caller identity boundary
seonghobae 8c561df
ci(auth): use src-aware Python path for focused repair
seonghobae 14684f9
ci(auth): fix request-principal repair source quoting
seonghobae 545da7d
ci(auth): allow bounded helper to publish verified repair
seonghobae d882ed4
fix(auth): resolve validated principal per request
github-actions[bot] 5a985ef
docs(auth): trace request-scoped principal authority repair
seonghobae a55fff4
docs(auth): normalize doctoring whitespace
seonghobae 5f85ab9
test(auth): reject malformed principal resolver output
seonghobae 1433975
ci: run bounded malformed-principal repair
seonghobae 811aaf7
fix(auth): fail closed on malformed principal output
fa0ac22
docs(auth): separate doctoring date and scope
seonghobae 772a816
fix(auth): bound durable decision evidence
seonghobae 6ef23db
test(auth): ratchet audit evidence bounds
seonghobae 8b97fec
docs(auth): record evidence storage bound basis
seonghobae 84f4cbb
docs(auth): canonicalize identity storage references
seonghobae 0e300ad
fix(auth): align correlation storage units
seonghobae ef9ffac
test(auth): align multibyte correlation contract
seonghobae b00f016
docs(auth): align correlation evidence units
seonghobae dc1cb7b
test(auth): correct multibyte correlation boundary fixture
seonghobae f0dc028
test(auth): reserve exception-resolution permission
seonghobae 764e5d0
feat(auth): reserve exception-resolution authority
seonghobae c7f558e
test(auth): advance completion policy vocabulary
seonghobae b9fbab4
docs(adr): separate exception-resolution permission
seonghobae 71db019
docs(auth): trace exception-resolution policy v3
seonghobae 27ca180
test: reserve unique authorization ADR identity
seonghobae ad0b900
docs: assign authorization ADR 0064 proposed
seonghobae ef58aea
docs: retire colliding authorization ADR 0055
seonghobae 42e6c7d
fix: point repository contract at ADR 0064
seonghobae d6674b8
docs: point completion trace to ADR 0064
seonghobae 04488f5
docs: point request-scope trace to ADR 0064
seonghobae 1afd776
docs: point exception policy trace to ADR 0064
seonghobae 4ef1f42
test: bind authorization traceability to ADR 0064
seonghobae 9cdafb7
docs: point authorization traceability to ADR 0064
seonghobae File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
101 changes: 101 additions & 0 deletions
101
database/migrations/0015_authorization_decision_evidence.sql
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,101 @@ | ||
| BEGIN; | ||
|
|
||
| -- Purpose-bound application decisions are append-only evidence. The host identity adapter validates | ||
| -- credentials; this table retains only the opaque claims and decision needed for accounting audit. | ||
| -- Identity references are normalized CWL URNs and use the 255-octet authorization profile ceiling; | ||
| -- raw external claims remain at the trusted identity-provider boundary. Operation/purpose limits | ||
| -- mirror the executable code contract, permission is two bounded code components, and the existing | ||
| -- 512-character correlation evidence ceiling is enforced again at PostgreSQL so direct SQL cannot | ||
| -- inflate storage while multibyte command identities retain the same contract as the HTTP boundary. | ||
| CREATE TABLE accounting_integration.authorization_decision_record ( | ||
| authorization_decision_record_id uuid PRIMARY KEY DEFAULT uuidv7(), | ||
| tenant_account_id uuid NOT NULL, | ||
| principal_reference text NOT NULL | ||
| CHECK ( | ||
| btrim(principal_reference) <> '' | ||
| AND octet_length(principal_reference) <= 255 | ||
| AND principal_reference ~ '^urn:cwl:[A-Za-z0-9_:.-]+$' | ||
| ), | ||
| principal_tenant_reference text NOT NULL | ||
| CHECK ( | ||
| btrim(principal_tenant_reference) <> '' | ||
| AND octet_length(principal_tenant_reference) <= 255 | ||
| AND principal_tenant_reference ~ '^urn:cwl:[A-Za-z0-9_:.-]+$' | ||
| ), | ||
| requested_tenant_reference text NOT NULL | ||
| CHECK ( | ||
| btrim(requested_tenant_reference) <> '' | ||
| AND octet_length(requested_tenant_reference) <= 255 | ||
| AND requested_tenant_reference ~ '^urn:cwl:[A-Za-z0-9_:.-]+$' | ||
| ), | ||
| authentication_context_reference text NOT NULL | ||
| CHECK ( | ||
| btrim(authentication_context_reference) <> '' | ||
| AND octet_length(authentication_context_reference) <= 255 | ||
| AND authentication_context_reference ~ '^urn:cwl:[A-Za-z0-9_:.-]+$' | ||
| ), | ||
| credential_evidence_reference text NOT NULL | ||
| CHECK ( | ||
| btrim(credential_evidence_reference) <> '' | ||
| AND octet_length(credential_evidence_reference) <= 255 | ||
| AND credential_evidence_reference ~ '^urn:cwl:[A-Za-z0-9_:.-]+$' | ||
| ), | ||
| operation_code text NOT NULL | ||
| CHECK ( | ||
| octet_length(operation_code) <= 64 | ||
| AND operation_code ~ '^[a-z][a-z0-9_]{1,63}$' | ||
| ), | ||
| permission_code text NOT NULL | ||
| CHECK ( | ||
| octet_length(permission_code) <= 129 | ||
| AND ( | ||
| permission_code = '' | ||
| OR permission_code ~ '^[a-z][a-z0-9_]{1,63}\.[a-z][a-z0-9_]{1,63}$' | ||
| ) | ||
| ), | ||
| purpose_code text NOT NULL | ||
| CHECK ( | ||
| octet_length(purpose_code) <= 64 | ||
| AND purpose_code ~ '^[a-z][a-z0-9_]{1,63}$' | ||
| ), | ||
| policy_version text NOT NULL | ||
| CHECK (btrim(policy_version) <> '' AND octet_length(policy_version) <= 64), | ||
| decision_code text NOT NULL CHECK (decision_code IN ('allowed', 'denied')), | ||
| correlation_reference text NOT NULL | ||
| CHECK (btrim(correlation_reference) <> '' AND char_length(correlation_reference) <= 512), | ||
| recorded_at timestamptz NOT NULL DEFAULT clock_timestamp(), | ||
| FOREIGN KEY (tenant_account_id) | ||
| REFERENCES accounting_core.tenant_account (tenant_account_id), | ||
| UNIQUE (tenant_account_id, authorization_decision_record_id) | ||
| ); | ||
|
seonghobae marked this conversation as resolved.
|
||
|
|
||
| CREATE INDEX authorization_decision_scope_index | ||
| ON accounting_integration.authorization_decision_record ( | ||
| tenant_account_id, recorded_at, authorization_decision_record_id | ||
| ); | ||
|
|
||
| CREATE OR REPLACE FUNCTION accounting_core.reject_authorization_decision_mutation() | ||
| RETURNS trigger | ||
| LANGUAGE plpgsql | ||
| AS $$ | ||
| BEGIN | ||
| RAISE EXCEPTION | ||
| 'authorization decision evidence is append-only (authorization_evidence_immutable)' | ||
| USING ERRCODE = '23514'; | ||
| END; | ||
| $$; | ||
|
|
||
| CREATE TRIGGER authorization_decision_immutable_guard | ||
| BEFORE UPDATE OR DELETE ON accounting_integration.authorization_decision_record | ||
| FOR EACH ROW EXECUTE FUNCTION accounting_core.reject_authorization_decision_mutation(); | ||
|
|
||
| ALTER TABLE accounting_integration.authorization_decision_record ENABLE ROW LEVEL SECURITY; | ||
| ALTER TABLE accounting_integration.authorization_decision_record FORCE ROW LEVEL SECURITY; | ||
| CREATE POLICY authorization_decision_tenant_isolation | ||
| ON accounting_integration.authorization_decision_record | ||
| USING (tenant_account_id = accounting_core.current_tenant_account_id()) | ||
| WITH CHECK (tenant_account_id = accounting_core.current_tenant_account_id()); | ||
|
|
||
| REVOKE ALL ON accounting_integration.authorization_decision_record FROM PUBLIC; | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. |
||
|
|
||
| COMMIT; | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🔍 Malformed-close documentation contradicts runtime
The changelog says malformed close bodies never create allowed evidence.
_post_authorization_operationclassifies them as hard closes, records an allow, then returns 400.Was this helpful? React with 👍 or 👎 to provide feedback.