Skip to content

[Question] Modernize OAuth 2.0 flows: Remove Implicit/Password, Add Device Code/PKCE #1234

@darrelmiller

Description

@darrelmiller

Question

Should we modernize the OAuth 2.0 flow support by:

  1. Removing Implicit flow (deprecated/insecure)
  2. Removing Password flow (deprecated/insecure)
  3. Adding Device Code flow (modern, user-friendly)
  4. Adding PKCE support to Authorization Code flow

Current State

OAuthFlows Definition (specification/grpc/a2a.proto, lines 608-619):

message OAuthFlows {
  oneof flow {
    AuthorizationCodeOAuthFlow authorization_code = 1;
    ClientCredentialsOAuthFlow client_credentials = 2;
    ImplicitOAuthFlow implicit = 3;           // ⚠️ Deprecated by OAuth 2.0 Security BCP
    PasswordOAuthFlow password = 4;            // ⚠️ Deprecated by OAuth 2.0 Security BCP
  }
}

Problems with Current Flows

1. Implicit Flow (Should Remove)

Why it's problematic:

  • Deprecated by OAuth 2.0 Security Best Current Practice (RFC 8252, RFC 6749)
  • Tokens exposed in URL fragments (browser history, referrer headers)
  • No refresh token support
  • Vulnerable to token leakage
  • Modern recommendation: Use Authorization Code flow with PKCE instead

OAuth 2.0 BCP states:

"The Implicit flow (response_type=token) should not be used"

2. Resource Owner Password Flow (Should Remove)

Why it's problematic:

  • Deprecated for public clients and strongly discouraged for all use cases
  • Requires sharing user credentials with the client application
  • Defeats the purpose of OAuth (delegated authorization without credential sharing)
  • Anti-pattern for modern authentication
  • No MFA support without hacks
  • Modern recommendation: Use Authorization Code flow with PKCE

OAuth 2.0 BCP states:

"The resource owner password credentials grant must not be used"

Proposed Additions

3. Device Code Flow (Should Add)

Why we need it:

message DeviceCodeOAuthFlow {
  // The device authorization endpoint URL
  string device_authorization_url = 1 [(google.api.field_behavior) = REQUIRED];
  // The token URL to be used for this flow
  string token_url = 2 [(google.api.field_behavior) = REQUIRED];
  // The URL to be used for obtaining refresh tokens
  string refresh_url = 3;
  // The available scopes for the OAuth2 security scheme
  map<string, string> scopes = 4 [(google.api.field_behavior) = REQUIRED];
}

Benefits:

  • Designed for input-constrained devices (IoT, TVs, CLI tools)
  • User authenticates on a separate device (phone/computer)
  • Secure and user-friendly for scenarios where keyboard input is difficult
  • Native support in modern OAuth providers (Microsoft, Google, GitHub, Auth0)
  • Specified in RFC 8628

Use cases for A2A:

  • CLI-based agent interactions
  • IoT agents
  • Smart home/device agents
  • Terminal-based agent clients

4. PKCE Support (Should Add)

Extend AuthorizationCodeOAuthFlow:

message AuthorizationCodeOAuthFlow {
  string authorization_url = 1 [(google.api.field_behavior) = REQUIRED];
  string token_url = 2 [(google.api.field_behavior) = REQUIRED];
  string refresh_url = 3;
  map<string, string> scopes = 4 [(google.api.field_behavior) = REQUIRED];
  
  // NEW: Indicates if PKCE is required for this flow
  bool pkce_required = 5;
}

Benefits:

  • Required for public clients (SPAs, mobile apps, native apps) per OAuth 2.0 BCP
  • Prevents authorization code interception attacks
  • Recommended even for confidential clients as defense-in-depth
  • Specified in RFC 7636
  • No downside to requiring it

Proposed Changes

Remove (Breaking Changes)

message OAuthFlows {
  oneof flow {
    AuthorizationCodeOAuthFlow authorization_code = 1;
    ClientCredentialsOAuthFlow client_credentials = 2;
    // REMOVED: ImplicitOAuthFlow implicit = 3;
    // REMOVED: PasswordOAuthFlow password = 4;
    DeviceCodeOAuthFlow device_code = 5;  // NEW
  }
}

Enhance Authorization Code Flow

message AuthorizationCodeOAuthFlow {
  string authorization_url = 1 [(google.api.field_behavior) = REQUIRED];
  string token_url = 2 [(google.api.field_behavior) = REQUIRED];
  string refresh_url = 3;
  map<string, string> scopes = 4 [(google.api.field_behavior) = REQUIRED];
  // Indicates if PKCE (RFC 7636) is required for this flow
  bool pkce_required = 5;
}

Standards References

Questions for Discussion

  1. Breaking change timing: v1.0 is the right time to make these changes, agree?

  2. Implicit flow removal: Any use cases that require implicit flow that can't be migrated to Authorization Code + PKCE?

  3. Password flow removal: Any legitimate use cases where password flow is the only option?

  4. Device code flow: Should this be required for agents targeting CLI/device scenarios?

  5. PKCE requirement: Should we:

    • Make pkce_required always true (enforce security best practice)?
    • Keep it optional for backwards compatibility with legacy providers?
    • Remove the field and document that PKCE should always be used?
  6. Migration path: Should we:

    • Deprecate first, remove later (but v1.0 is a major version)?
    • Remove immediately since we're pre-v1.0?
    • Provide migration guidance in changelog?

Recommendation

Remove both Implicit and Password flows from v1.0:

  • Both are deprecated by OAuth 2.0 Security BCP
  • Security anti-patterns that shouldn't be encouraged
  • Removal aligns A2A with modern security best practices

Add Device Code flow:

  • Essential for modern device/CLI scenarios
  • Well-established standard (RFC 8628)
  • Widely supported by providers

Add PKCE support:

  • Make pkce_required field on Authorization Code flow
  • Document that PKCE SHOULD always be used
  • Consider making it required by default in future versions

Related Issues

Metadata

Metadata

Labels

P1Priority for TSC ReviewTSC ReviewTo be reviewed by the Technical Steering Committee

Type

Projects

Status

Done

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions