Files
skybridge/TOKEN_LOOKUP_ANALYSIS.md
2025-08-26 13:51:15 -04:00

5.2 KiB

Token Verification: App ID From Token vs Separate Parameter

Current Implementation Analysis

Current Flow (Requires app_id parameter):

1. Client: POST /api/verify {"token": "TESTT-abc123", "app_id": "test.example.com"}
2. System: Get app by app_id → Validate token against app's stored hashes
3. Result: Token validated within specific application scope

Proposed Alternative (Extract app_id from token):

1. Client: POST /api/verify {"token": "TESTT-abc123"}
2. System: Extract prefix "TEST" → Find app by token_prefix → Validate token
3. Result: Token validated without requiring app_id parameter

Security Analysis

Advantages of Token-Only Verification:

1. Simpler API Usage

// Current (requires app knowledge)
await verify({token: "TESTT-abc123", app_id: "test.example.com"});

// Proposed (token-only)  
await verify({token: "TESTT-abc123"});

2. Prevents App ID Mismatches

  • Current: Client could provide wrong app_id (though validation would fail)
  • Proposed: App is determined directly from token - no mismatch possible

3. Better Token Portability

  • Tokens are self-describing and don't require external context
  • Useful for tokens shared across different applications/services

Security Risks of Token-Only Verification:

1. Information Disclosure Through Enumeration

# Attacker can discover applications by trying token prefixes
curl -X POST /api/verify -d '{"token": "TESTX-fakehash"}'
# Response reveals if "TEST" application exists

curl -X POST /api/verify -d '{"token": "PRODX-fakehash"}'  
# Response reveals if "PROD" application exists

2. Reduced Access Control Granularity

Current: Client must know both token AND which app it belongs to
Proposed: Client only needs token - loses "need to know" app context

3. Prefix Collision Risk

-- Multiple apps could theoretically have same prefix
INSERT INTO applications (app_id, token_prefix) VALUES 
  ('app1.com', 'TEST'),
  ('app2.com', 'TEST');  -- Collision!

4. Weaker Defense Against Token Leakage

  • Current: Leaked token + need app_id knowledge = double barrier
  • Proposed: Leaked token alone is sufficient = single barrier

Implementation Feasibility

Required Changes for Token-Only Verification:

// 1. Add repository method
func (r *ApplicationRepository) GetByTokenPrefix(ctx context.Context, prefix string) (*domain.Application, error)

// 2. Extract prefix from token
func extractTokenPrefix(token string) string {
    dashIndex := strings.Index(token, "-")
    if dashIndex >= 3 && dashIndex <= 6 {
        return token[:dashIndex-1] // Remove "T" or "UT" part
    }
    return ""
}

// 3. Modified verification flow
func (s *tokenService) VerifyTokenOnly(ctx context.Context, token string) (*domain.VerifyResponse, error) {
    prefix := extractTokenPrefix(token)
    app, err := s.appRepo.GetByTokenPrefix(ctx, prefix)
    if err != nil {
        return &domain.VerifyResponse{Valid: false, Error: "Invalid token"}, nil
    }
    // Continue with existing verification logic...
}

Database Schema Considerations:

-- Ensure unique prefixes (recommended)
ALTER TABLE applications ADD CONSTRAINT unique_token_prefix 
    UNIQUE (token_prefix) WHERE token_prefix != '';

-- Index already exists from migration 003
-- CREATE INDEX idx_applications_token_prefix ON applications(token_prefix);

Recommendation: Keep Current Implementation (Require app_id)

Reasoning:

Security-First Approach 🛡️

  1. Prevents enumeration attacks - attackers can't discover apps by probing prefixes
  2. Maintains access control granularity - clients must know token + app context
  3. Defense in depth - two required pieces of information instead of one
  4. Clear audit trails - logs show which app context was used for verification

Architectural Benefits 🏗️

  1. Explicit application scoping - makes it clear which app owns the token
  2. Better error handling - can distinguish between "invalid app" vs "invalid token"
  3. Supports multi-tenancy - different apps can have isolated token validation
  4. Future extensibility - can add per-app validation rules without breaking changes

Operational Benefits 🔧

  1. Clear API contracts - consumers explicitly specify their context
  2. Better monitoring - can track usage per application
  3. Simpler debugging - logs clearly show app context for each verification

Optional: Provide Both Endpoints

// Existing secure endpoint (recommended for production)
POST /api/verify
{
    "token": "TESTT-abc123",
    "app_id": "test.example.com"
}

// Optional convenience endpoint (for development/testing)
POST /api/verify/token-only  
{
    "token": "TESTT-abc123"
}

Final Answer

Keep the current implementation requiring app_id for security and architectural reasons. The slight inconvenience of requiring the app_id parameter provides significant security benefits and maintains better system architecture.

The token prefix provides tampering protection (which is working correctly), but requiring separate app_id provides additional security layers that outweigh the convenience of token-only verification.