Add signal contracts for reachability, exploitability, trust, and unknown symbols
Some checks failed
Docs CI / lint-and-preview (push) Has been cancelled
Signals DSSE Sign & Evidence Locker / sign-signals-artifacts (push) Has been cancelled
Signals DSSE Sign & Evidence Locker / verify-signatures (push) Has been cancelled

- Introduced `ReachabilityState`, `RuntimeHit`, `ExploitabilitySignal`, `ReachabilitySignal`, `SignalEnvelope`, `SignalType`, `TrustSignal`, and `UnknownSymbolSignal` records to define various signal types and their properties.
- Implemented JSON serialization attributes for proper data interchange.
- Created project files for the new signal contracts library and corresponding test projects.
- Added deterministic test fixtures for micro-interaction testing.
- Included cryptographic keys for secure operations with cosign.
This commit is contained in:
StellaOps Bot
2025-12-05 00:27:00 +02:00
parent b018949a8d
commit 8768c27f30
192 changed files with 27569 additions and 2552 deletions

View File

@@ -0,0 +1,322 @@
# Competitor Ingest Error Taxonomy (CM10)
Status: Draft · Date: 2025-12-04
Scope: Standardize retry/backoff/error taxonomy for the competitor ingest pipeline with deterministic diagnostics.
## Objectives
- Define comprehensive error taxonomy for ingest failures.
- Specify retry behavior for transient errors.
- Enable deterministic error diagnostics.
- Support offline error handling.
## Error Categories
### Retryable Errors
| Code | Category | Description | Max Retries | Backoff |
|------|----------|-------------|-------------|---------|
| `E1001` | `network_error` | Network connectivity failure | 3 | Exponential |
| `E1002` | `network_timeout` | Connection/read timeout | 3 | Exponential |
| `E1003` | `rate_limit` | Rate limit exceeded (429) | 5 | Linear |
| `E1004` | `service_unavailable` | Service temporarily unavailable (503) | 3 | Exponential |
| `E1005` | `transient_io` | Temporary I/O error | 2 | Fixed |
| `E1006` | `lock_contention` | Resource lock conflict | 3 | Exponential |
### Non-Retryable Errors
| Code | Category | Description | Action |
|------|----------|-------------|--------|
| `E2001` | `signature_invalid` | Signature verification failed | Reject |
| `E2002` | `signature_expired` | Signature validity exceeded | Reject |
| `E2003` | `key_unknown` | Signing key not found | Reject |
| `E2004` | `key_expired` | Signing key validity exceeded | Reject |
| `E2005` | `key_revoked` | Signing key revoked | Reject |
| `E2006` | `alg_unsupported` | Unsupported algorithm | Reject |
| `E2007` | `hash_mismatch` | Content hash mismatch | Reject |
| `E2008` | `schema_invalid` | Input doesn't match schema | Reject |
| `E2009` | `version_unsupported` | Tool version not supported | Reject |
| `E2010` | `no_evidence` | No acceptable evidence found | Reject |
### Warning Conditions
| Code | Category | Description | Action |
|------|----------|-------------|--------|
| `W3001` | `provenance_unknown` | Provenance not verifiable | Accept with warning |
| `W3002` | `degraded_confidence` | Low confidence result | Accept with warning |
| `W3003` | `stale_data` | Data exceeds freshness threshold | Accept with warning |
| `W3004` | `partial_mapping` | Some fields couldn't be mapped | Accept with warning |
| `W3005` | `deprecated_format` | Using deprecated format | Accept with warning |
## Error Format
### Standard Error Response
```json
{
"error": {
"code": "E2001",
"category": "signature_invalid",
"message": "DSSE signature verification failed",
"details": {
"reason": "Key ID not found in trusted keyring",
"keyId": "unknown-key-12345",
"algorithm": "ecdsa-p256"
},
"retryable": false,
"diagnostics": {
"timestamp": "2025-12-04T12:00:00Z",
"traceId": "abc123...",
"inputHash": "b3:...",
"stage": "signature_verification"
}
}
}
```
### Warning Response
```json
{
"result": {
"status": "accepted_with_warnings",
"warnings": [
{
"code": "W3001",
"category": "provenance_unknown",
"message": "SBOM accepted without verified provenance",
"details": {
"reason": "No signature present",
"fallbackLevel": 2
}
}
],
"output": {...}
}
}
```
## Retry Configuration
### Backoff Strategies
```json
{
"backoff": {
"exponential": {
"description": "2^attempt * base, capped at max",
"config": {
"base": 1000,
"factor": 2,
"max": 60000,
"jitter": 0.1
},
"example": [1000, 2000, 4000, 8000, 16000, 32000, 60000]
},
"linear": {
"description": "initial + (attempt * increment), capped at max",
"config": {
"initial": 1000,
"increment": 1000,
"max": 30000
},
"example": [1000, 2000, 3000, 4000, 5000]
},
"fixed": {
"description": "Constant delay between retries",
"config": {
"delay": 5000
},
"example": [5000, 5000, 5000]
}
}
}
```
### Retry Decision Logic
```python
def should_retry(error: IngestError, attempt: int) -> RetryDecision:
if error.code.startswith('E2'):
return RetryDecision(retry=False, reason="Non-retryable error")
config = RETRY_CONFIG.get(error.category)
if not config:
return RetryDecision(retry=False, reason="Unknown error category")
if attempt >= config.max_retries:
return RetryDecision(retry=False, reason="Max retries exceeded")
delay = calculate_backoff(config, attempt)
return RetryDecision(retry=True, delay=delay)
```
## Diagnostic Output
### Deterministic Diagnostics
All error diagnostics must be deterministic and reproducible:
```json
{
"diagnostics": {
"timestamp": "2025-12-04T12:00:00Z",
"traceId": "deterministic-trace-id",
"inputHash": "b3:...",
"stage": "normalization",
"context": {
"tool": "syft",
"toolVersion": "1.0.0",
"adapterVersion": "1.0.0",
"inputSize": 12345,
"componentCount": 42
},
"errorChain": [
{
"stage": "schema_validation",
"error": "Missing required field: artifacts[0].purl",
"path": "/artifacts/0"
}
]
}
}
```
### Offline Diagnostics
For offline mode, diagnostics include:
- No timestamps that depend on wall clock
- Deterministic trace IDs (based on input hash)
- All context from bundled metadata
```json
{
"diagnostics": {
"mode": "offline",
"kitVersion": "1.0.0",
"traceId": "b3:input-hash-derived-trace-id",
"kitHash": "b3:...",
"trustRootHash": "b3:..."
}
}
```
## Error Handling Workflow
```
┌─────────────┐
│ Ingest │
│ Request │
└─────────────┘
┌─────────────┐
│ Validate │──Error──► E2008 schema_invalid
└─────────────┘
┌─────────────┐
│ Verify │──Error──► E2001-E2007 signature errors
│ Signature │
└─────────────┘
┌─────────────┐
│ Normalize │──Error──► E2008-E2009 format errors
└─────────────┘
┌─────────────┐
│ Store │──Error──► E1001-E1006 retryable errors
└─────────────┘
┌─────────────┐
│ Success │
│ or Warn │
└─────────────┘
```
## API Error Responses
### HTTP Status Mapping
| Error Category | HTTP Status | Response Body |
|----------------|-------------|---------------|
| Retryable (E1xxx) | 503 | Error with Retry-After header |
| Rate limit (E1003) | 429 | Error with Retry-After header |
| Signature (E2001-E2007) | 400 | Error with details |
| Schema (E2008) | 400 | Error with validation details |
| Version (E2009) | 400 | Error with supported versions |
| No evidence (E2010) | 400 | Error with fallback options |
### Example Error Response
```http
HTTP/1.1 400 Bad Request
Content-Type: application/json
X-Stellaops-Error-Code: E2001
X-Stellaops-Trace-Id: abc123...
```
### Retry Response
```http
HTTP/1.1 503 Service Unavailable
Content-Type: application/json
Retry-After: 5
X-Stellaops-Error-Code: E1004
X-Stellaops-Retry-Attempt: 1
```
## Logging
### Error Log Format
```json
{
"level": "error",
"timestamp": "2025-12-04T12:00:00Z",
"logger": "stellaops.scanner.ingest",
"message": "Ingest failed: signature_invalid",
"error": {
"code": "E2001",
"category": "signature_invalid"
},
"context": {
"traceId": "abc123...",
"tool": "syft",
"inputHash": "b3:..."
}
}
```
## Links
- Sprint: `docs/implplan/SPRINT_0186_0001_0001_record_deterministic_execution.md` (CM10)
- Normalization: `docs/modules/scanner/design/competitor-ingest-normalization.md` (CM1)
- Verification: `docs/modules/scanner/design/competitor-signature-verification.md` (CM2)
- Offline Kit: `docs/modules/scanner/design/competitor-offline-ingest-kit.md` (CM5)
"timestamp": "2025-12-04T12:00:00Z",
"logger": "stellaops.scanner.ingest",
"message": "Ingest failed: signature_invalid",
"error": {
"code": "E2001",
"category": "signature_invalid"
},
"context": {
"traceId": "abc123...",
"tool": "syft",
"inputHash": "b3:..."
}
}
```
## Links
- Sprint: `docs/implplan/SPRINT_0186_0001_0001_record_deterministic_execution.md` (CM10)
- Normalization: `docs/modules/scanner/design/competitor-ingest-normalization.md` (CM1)
- Verification: `docs/modules/scanner/design/competitor-signature-verification.md` (CM2)
- Offline Kit: `docs/modules/scanner/design/competitor-offline-ingest-kit.md` (CM5)