1-SEC contributors · Reviewed · Module: auth_fortress

Agent OAuth Consent: Scope Accumulation and Grant-Rate Signals

Auth Fortress accumulates reported scope strings and grant counts for each application ID.

What 1-SEC checks

Auth Fortress accumulates reported scope strings and grant counts for each application ID. A consent-phishing signal requires at least three recognized dangerous scopes, at least three grants and an application profile less than one hour old. Excessive-scope signals use four recognized dangerous scopes or eight accumulated distinct scopes. A separate rapid-grant condition uses more than twenty grants to more than ten reported users within thirty minutes. The handler turns these observations into alerts.

Read the implementation: handleOAuthEvent

Required telemetry and context

Relevant input events: oauth_grant, oauth_consent, oauth_token. Use a trusted producer at the real application boundary.

  • app_id
  • app_name
  • scopes (space-separated string)
  • username
  • grant_type
  • redirect_uri
  • source_ip (event envelope)

Field names above describe relevant context, not a complete API request. Consult the current event contract for envelope and detail requirements. Preserve booleans, numbers, and strings as the receiving handler expects them. Agent-provided text cannot independently verify identity or authorization.

Deployment, prevention, and response

Emit app, user, redirect and scope information from a trusted authorization integration. Bind the reported app ID to the actual client before grouping events. Review granted permissions and the real consent transaction rather than treating a scope-count alert as a fraud verdict. Enforce publisher approval, least privilege and revocation at the identity provider and resource server, then verify that those systems actually refuse an unapproved operation.

Record the source event, affected agent/host, actual target, policy decision, and response result. Review enforcement configuration separately from detection. A recommendation, selected action, dry-run record, and completed action are different outcomes.

Reproduce the source fixtures

From a checkout of the linked 1-SEC source revision, run the selected fixtures with the repository's Go toolchain. These commands run tests; they do not execute a real attack against your systems.

go test ./internal/modules/auth -run '^(TestOAuthMonitor_ConsentPhishing|TestOAuthMonitor_ExcessiveScopes|TestOAuthMonitor_ExcessiveScopes_TotalCount|TestOAuthMonitor_TokenAbuse)$' -count=1

Synthetic helper fixtures cover repeated dangerous-scope grants, total distinct scopes and rapid-grant signals. They do not authenticate a provider, operate a real consent screen or demonstrate complete agent impersonation prevention.

TestOAuthMonitor_ConsentPhishing

Full fixture and assertions — run in its original package with its helpers.

func TestOAuthMonitor_ConsentPhishing(t *testing.T) {
	om := NewOAuthMonitor()

	// 3+ dangerous scopes + 3+ grants in 1 hour
	scopes := "mail.read mail.send files.readwrite.all"
	for i := 0; i < 3; i++ {
		om.Analyze("10.0.0.1", "app-evil", "EvilApp", scopes, fmt.Sprintf("user%d", i), "authorization_code", "https://evil.com/callback")
	}
	result := om.Analyze("10.0.0.1", "app-evil", "EvilApp", scopes, "userd", "authorization_code", "https://evil.com/callback")

	if !result.ConsentPhishing {
		t.Error("expected ConsentPhishing with 3+ dangerous scopes and 3+ grants")
	}
}
TestOAuthMonitor_ExcessiveScopes

Full fixture and assertions — run in its original package with its helpers.

func TestOAuthMonitor_ExcessiveScopes(t *testing.T) {
	om := NewOAuthMonitor()

	// 4+ dangerous scopes
	scopes := "mail.read mail.send mail.readwrite files.readwrite.all"
	result := om.Analyze("10.0.0.1", "app-greedy", "GreedyApp", scopes, "alice", "authorization_code", "https://app.com/cb")

	if !result.ExcessiveScopes {
		t.Error("expected ExcessiveScopes with 4+ dangerous scopes")
	}
}
TestOAuthMonitor_ExcessiveScopes_TotalCount

Full fixture and assertions — run in its original package with its helpers.

func TestOAuthMonitor_ExcessiveScopes_TotalCount(t *testing.T) {
	om := NewOAuthMonitor()

	// 8+ total scopes (even if not all dangerous)
	scopes := "scope1 scope2 scope3 scope4 scope5 scope6 scope7 scope8"
	result := om.Analyze("10.0.0.1", "app-many", "ManyScopes", scopes, "alice", "authorization_code", "https://app.com/cb")

	if !result.ExcessiveScopes {
		t.Error("expected ExcessiveScopes with 8+ total scopes")
	}
}
TestOAuthMonitor_TokenAbuse

Full fixture and assertions — run in its original package with its helpers.

func TestOAuthMonitor_TokenAbuse(t *testing.T) {
	om := NewOAuthMonitor()

	// Rapid grants to many users: >20 grants, >10 unique users
	for i := 0; i < 25; i++ {
		om.Analyze("10.0.0.1", "app-abuse", "AbuseApp", "mail.read", fmt.Sprintf("user%d", i), "authorization_code", "https://app.com/cb")
	}
	result := om.Analyze("10.0.0.1", "app-abuse", "AbuseApp", "mail.read", "userZ", "authorization_code", "https://app.com/cb")

	if !result.TokenAbuse {
		t.Error("expected TokenAbuse with rapid grants to many users")
	}
}

Tuning, evaluation, and coverage limits

These are fixed heuristics over reported OAuth events, not a provider consent screen, verified publisher assessment or automatic refusal of a grant. A legitimate new application can match, and a malicious application can remain below thresholds or use different scopes. Scope history is accumulated per app ID rather than independently approving each request. The cited fixtures exercise the monitor helper, not a live identity provider or phishing simulation. The optional Token Vault broad-scope check is a different path; enabling it does not prove every consent flow is protected.

Evaluate this behavior with representative authorized activity and a controlled known-positive case. Investigate the exact rule, inputs, and state before suppressing an alert. Do not assume a hard-coded heuristic is a configurable setting. Measure your own deployment; the source fixtures do not establish a benchmark, detection rate, compliance certification, or incident-prevention claim.

Protocol and format references

These references describe the underlying format or protocol. The implementation and fixtures above define the subset 1-SEC actually checks.

Related implemented controls

Implementation reviewed at source revision 4803febcb2bfe646bb74d1bf0f8f4e7fe8a880a6. Recheck the actual release and integration before deployment. Sources and corrections policy.