feat(detectors): add Stream.io detector with JWT verification#5062
feat(detectors): add Stream.io detector with JWT verification#5062deerajcm wants to merge 3 commits into
Conversation
Add detector for HTTP Basic Authentication tokens (BSCAU002). Detects Authorization: Basic <base64> patterns and decodes them to extract username:password credentials. Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
feat(detectors): add BasicAuth detector
Add detector for Stream.io (GetStream.io) API credentials with full verification support using JWT token authentication. Features: - Detects Stream.io API keys and secrets in various formats (stream_api_key, getstream_key, environment variables, JSON configs) - Optional app_id detection (not required for verification) - Full credential verification using JWT tokens signed with HMAC-SHA256 - Multi-region support (us-east, eu-west, singapore, sydney, tokyo) - Comprehensive test coverage including real credential verification Technical implementation: - Generates JWT tokens with resource-specific claims for feed access - Uses Stream.io feed API endpoint for verification - Handles 400 status as successful auth (feed doesn't exist but auth passed) - Returns 401/403 for invalid credentials Test results: - ✅ Detection tests pass - ✅ Pattern matching tests pass - ✅ Real credential verification: Verified=true - ✅ All integration tests pass Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
|
Deeraj CM seems not to be a GitHub user. You need a GitHub account to be able to sign the CLA. If you have already a GitHub account, please add the email address used for this commit to your account. You have signed the CLA already but the status is still pending? Let us recheck it. |
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes and found 3 potential issues.
Reviewed by Cursor Bugbot for commit 3966ab6. Configure here.
| // REPLACE THESE WITH YOUR REAL STREAM.IO CREDENTIALS FROM DASHBOARD | ||
| realAppId := "1644228" // Numeric ID from dashboard | ||
| realApiKey := "4u3ncebvw27r" | ||
| realApiSecret := "as57ayreare6wqz2vj2uvsgcmpgbjejcchkdd9723gku26dqvwezgpbwnbpwmsn7" |
There was a problem hiding this comment.
Real API credentials committed in integration test
High Severity
Real Stream.io credentials (realAppId, realApiKey, realApiSecret) are hardcoded in the test file instead of placeholder values. The skip guard on line 24 checks realAppId == "your_app_id_here", but the actual value is "1644228", so the guard never triggers and these credentials are permanently exposed in the repository. Ironic for a secret-detection tool to ship with leaked secrets.
Additional Locations (1)
Reviewed by Cursor Bugbot for commit 3966ab6. Configure here.
| &azuresearchquerykey.Scanner{}, | ||
| &azure_storage.Scanner{}, | ||
| &azurerepositorykey.Scanner{}, | ||
| &basicauth.Scanner{}, |
There was a problem hiding this comment.
StreamIO detector not registered in engine defaults
High Severity
The streamio package is implemented but never imported or registered in defaults.go. Only the basicauth detector was added. Without registration, the StreamIO detector will never run during scans, making the entire feature dead code.
Reviewed by Cursor Bugbot for commit 3966ab6. Configure here.
| // Check if all regions give same error - if yes, credentials are definitely invalid | ||
| bodyStr := string(bodyBytes) | ||
| lastErr = fmt.Errorf("auth failed (status %d): %s", res.StatusCode, bodyStr) | ||
| continue |
There was a problem hiding this comment.
Verification returns error on definitive auth failure
Medium Severity
When verifyStreamIO receives a 401/403 response, it returns (false, lastErr) with a non-nil error. The established convention (e.g., in abstract.go) is to return (false, nil) for definitively invalid credentials. Returning an error causes SetVerificationError to treat the result as "verification inconclusive" rather than "credentials invalid," misrepresenting the outcome. Additionally, the loop continues trying other regions after a 401, making unnecessary API calls since authentication is not region-dependent.
Additional Locations (1)
Reviewed by Cursor Bugbot for commit 3966ab6. Configure here.


Summary
Add detector for Stream.io (GetStream.io) API credentials with full verification support using JWT token authentication.
Features
stream_api_key,getstream_keySTREAM_API_KEY,GETSTREAM_SECRET)Technical Implementation
Authentication Challenge
Stream.io requires JWT tokens signed with HMAC-SHA256 for API authentication, not raw credentials. The detector:
Verification Logic
Why 400 = Valid?
When the API returns 400 "feed group does not exist":
This confirms credentials are valid without needing actual feed configurations.
Note
Medium Risk
New credential detectors increase scan surface and false positives; Stream verification performs outbound API calls with leaked secrets, and committed real-looking Stream credentials in tests are a serious leak risk if those keys are valid.
Overview
This PR introduces two new secret detectors and registers new
DetectorTypevalues (BasicAuth= 1057,StreamIO= 1058) inproto/detector_type.protoand the generated Go enums.HTTP Basic Auth matches
Authorization/authheaders with aBasicbase64 payload, decodes and validatesusername:password, and emitsSecretParts(username,password,encoded). Findings are always unverified (no target URL to probe). The scanner is wired intodefaultsvia&basicauth.Scanner{}.Stream.io (GetStream) finds optional
app_idplusapi_key/api_secretusing prefixed regexes, pairs keys with secrets (and app IDs when present), and when verification is enabled signs an HS256 JWT from the secret and probes regional feed API endpoints—treating 200 and 400 as successful auth. Unit and integration tests cover detection patterns and optional live verification.Note for reviewers:
StreamIOis defined in proto butstreamio.Scanneris not added topkg/engine/defaults/defaults.go, so it will not run in the default engine until registered. The integration test file also embeds what look like real API credentials, which is a security concern if merged as-is.Reviewed by Cursor Bugbot for commit 3966ab6. Bugbot is set up for automated code reviews on this repo. Configure here.