Dependencies
Dependencies connect claims to their sources and to other claims. When a source changes, TruthKeeper uses these dependencies to identify all affected claims.
Dependency Types
TruthKeeper uses a three-tier dependency model:
HARD
The claim is invalid if the source changes. Use for direct factual dependencies.
Example: “Function X calls function Y” depends on both functions existing.
SOFT
The claim may need review if the source changes. Use for contextual dependencies.
Example: “The API uses REST conventions” depends on API design docs.
DERIVED
The claim was computed from the source. Use for aggregated knowledge.
Example: “The codebase has 42 API endpoints” is derived from scanning all routes.
Dependency Targets
Dependencies can point to:
External Sources
{
"target": "file://src/services/user.py",
"type": "HARD"
}
{
"target": "git://main/src/api/routes.py@abc123",
"type": "HARD"
}
{
"target": "https://api.example.com/v1/schema",
"type": "SOFT"
}Other Claims
{
"target": "claim://clm_abc123",
"type": "DERIVED"
}Cascade Propagation
When a source changes, TruthKeeper walks the dependency graph to identify all affected claims. The cascade algorithm:
- Source watcher detects change
- Find all claims with direct dependencies on that source
- Mark direct dependents as STALE
- Find claims that depend on those claims
- Mark transitive dependents based on dependency type
- Calculate blast radius for each affected claim
- Queue high-impact claims for human review
Source Change: file://src/auth.py modified
│
▼
┌──────────────────────────────────────────────┐
│ Direct Dependencies (HARD) │
├──────────────────────────────────────────────┤
│ Claim: "AuthService validates tokens" │ → STALE
│ Claim: "JWT tokens expire after 1 hour" │ → STALE
└──────────────────────────────────────────────┘
│
▼
┌──────────────────────────────────────────────┐
│ Transitive Dependencies │
├──────────────────────────────────────────────┤
│ Claim: "API requires authentication" │ → SUSPECT (SOFT)
│ Claim: "42 endpoints use auth" │ → SUSPECT (DERIVED)
└──────────────────────────────────────────────┘Cascade Rules
| Parent State | Dependency Type | Child State |
|---|---|---|
| STALE | HARD | STALE |
| STALE | SOFT | SUSPECT |
| STALE | DERIVED | SUSPECT |
| OUTDATED | HARD | OUTDATED |
| OUTDATED | SOFT | CONTESTED |
| OUTDATED | DERIVED | STALE |
Source Watchers
Source watchers monitor external sources and notify TruthKeeper when they change.
File Watcher
from truthkeeper.watchers import FileSourceWatcher
watcher = FileSourceWatcher(
client=client,
paths=["src/", "lib/"],
patterns=["**/*.py", "**/*.ts"],
ignore=["**/__pycache__/**", "**/node_modules/**"]
)
await watcher.start()Git Watcher
from truthkeeper.watchers import GitSourceWatcher
watcher = GitSourceWatcher(
client=client,
repo_path=".",
branch="main",
poll_interval=60 # seconds
)
await watcher.start()Webhook Receiver
# In your CI/CD pipeline
curl -X POST http://truthkeeper:8000/api/v1/sources/changed \
-H "Content-Type: application/json" \
-d '{
"uri": "file://src/api/routes.py",
"change_type": "MODIFIED",
"commit": "abc123"
}'Stale Claims Cache
For efficient cascade resolution, TruthKeeper maintains a cache of stale claims indexed by source. This allows O(1) lookup of affected claims when a source changes.
# Get all stale claims efficiently
stale = await client.get_stale_claims()
# Get stale claims for a specific source
stale = await client.get_stale_claims(
source="file://src/auth.py"
)
# Batch reverify
results = await client.reverify_claims([c.id for c in stale])Best Practices
Choosing Dependency Types
- HARD: Use when the claim directly quotes or references specific code/data
- SOFT: Use when the claim is about patterns, conventions, or design decisions
- DERIVED: Use when the claim summarizes or aggregates information
Avoiding Dependency Cycles
TruthKeeper detects and prevents circular dependencies. If you need bidirectional relationships, use DERIVED dependencies which don't cascade infinitely.
Dependency Granularity
- Too coarse: “depends on src/” triggers on any file change
- Too fine: “depends on line 42” breaks on any edit
- Just right: “depends on src/auth.py:AuthService.validate”
Next Steps
- Verification - How stale claims are reverified
- Blast Radius - Impact analysis for changes
- API Reference - Source and dependency APIs