# Shoulder Transparency Report **Product:** Shoulder Security Scanner **Version:** Commit 844e689 **Report Date:** 2026-01-19 **Security Contact:** security@shoulder.dev --- ## Table of Contents 1. [Executive Summary](#1-executive-summary) 2. [Product Overview](#2-product-overview) 3. [Data Handling and Privacy Commitments](#3-data-handling-and-privacy-commitments) 4. [Network Behavior](#4-network-behavior) 5. [Filesystem Behavior](#5-filesystem-behavior) 6. [Execution and Safety Boundaries](#6-execution-and-safety-boundaries) 7. [Logging, Diagnostics, and Crash Reporting](#7-logging-diagnostics-and-crash-reporting) 8. [Security Measures](#8-security-measures) 9. [Configuration Controls](#9-configuration-controls) 10. [Verification Notes](#10-verification-notes) 11. [Open Questions / Verification Needed](#11-open-questions--verification-needed) 12. [Changelog / Version Scope](#12-changelog--version-scope) 13. [Security Contact](#13-security-contact) --- ## 1) Executive Summary **What Shoulder Is:** Shoulder is a local-first static security scanner for source code. It detects vulnerabilities through taint flow analysis, pattern matching, and security control validation. Supported languages include JavaScript/TypeScript, Python, Go, Dockerfile, and YAML (Kubernetes manifests). **Privacy Posture:** Shoulder operates with a local-first architecture. All security scanning—including code parsing, AST/CFG/DFG graph building, taint analysis, and finding generation—occurs entirely on the user's machine. No source code, analysis data, or vulnerability findings are transmitted externally. Optional cloud features (package vulnerability lookups and update checks) send only package names/versions or version metadata to the API endpoint. ### Key Guarantees - All security scanning is performed locally; source code never leaves the user's machine - No telemetry, analytics, or usage tracking is collected or transmitted - No advertising identifiers, user fingerprinting, or behavioral tracking - Crash data is not reported externally; errors are logged locally only - Network calls are limited to two opt-in features: update checks and package vulnerability scanning - Both network features can be disabled via environment variables - Source code is never modified or deleted by the scanner ### Key Limitations - Update checks are enabled by default (opt-out via `SHOULDER_DISABLE_UPDATES=1`) - Package vulnerability scanning sends package names/versions to `api.shoulder.dev` - The local gRPC server (for IDE integration) does not use TLS (localhost-only by design) - No formal third-party security audit has been conducted on this codebase --- ## 2) Product Overview ### Primary Functions 1. **Static Security Analysis:** Detects vulnerabilities through taint flow analysis (tracking data from untrusted sources to dangerous sinks) and pattern matching 2. **Security Control Validation:** Verifies presence of security controls such as rate limiting, authentication middleware, secure headers, and CSRF protection 3. **Package Vulnerability Scanning:** Optional API-based lookup of known CVEs in project dependencies 4. **Test Impact Analysis:** Identifies which tests to run based on code changes using coverage data ### Supported Languages & Frameworks | Language | Frameworks | |----------|------------| | JavaScript/TypeScript | Express, Fastify, Koa, Next.js, NestJS, tRPC | | Python | Flask, Django, FastAPI | | Go | Gin, Chi, Echo, Fiber, Gorilla, standard library | | Configuration | Dockerfile, Kubernetes YAML | ### Deployment Modes | Mode | Description | |------|-------------| | **CLI (Default)** | Single-pass scan via `shouldersec scan ` | | **Serve Mode** | Long-running gRPC server for incremental IDE integration | | **LSP Server** | Language Server Protocol for editor diagnostics | | **MCP Server** | Model Context Protocol server for AI assistant integration | | **Test Impact** | Git-aware test selection for CI optimization | ### Typical Workflow 1. User runs `shouldersec scan .` from project root 2. Scanner builds code graph using TreeSitter AST parsing (no regex-based parsing) 3. Taint analyzer traces data flow from sources (user input) to sinks (dangerous operations) 4. Pattern detector identifies security misconfigurations 5. Findings are displayed in console, JSON, or SARIF format 6. All analysis is performed locally; results remain on user's machine --- ## 3) Data Handling and Privacy Commitments ### Types of Input Data Processed | Data Type | How Processed | Where Stored | |-----------|---------------|--------------| | Source code files | Parsed into AST using TreeSitter; never transmitted | Memory only during analysis | | Code graph (AST/CFG/DFG) | Cached locally for incremental scans | `~/.cache/shouldersec/` | | Dependency manifests | Read to extract package names/versions | Not persisted | | Configuration files | Read for framework detection | Not persisted | | Custom security rules | Loaded from `.shoulder/rules/` | User's project directory | ### Does Data Leave the Machine? | Scenario | Data Transmitted? | Destination | |----------|-------------------|-------------| | Normal security scan | No | N/A | | Package vulnerability scan | Yes: package names, versions, ecosystem | `api.shoulder.dev` | | Update check | Yes: OS type, current version (via User-Agent) | `api.shoulder.dev` | | IDE integration (gRPC) | No: localhost only | 127.0.0.1 | ### Local Storage | Location | Purpose | Retention | |----------|---------|-----------| | `~/.cache/shouldersec/` | Serialized code graph cache | Until manually cleared or source changes | | `~/.shoulder/logs/` | Debug logs (serve mode only) | 10 most recent files | | `~/.shoulder/sessions.json` | Server session mapping | Indefinite | | `~/.shoulder/servers.json` | Running server registry | Session lifetime | | `.shoulder/fp_history.json` | False positive dismissals | 12 months, max 10,000 records | ### What We Do NOT Collect - **No telemetry or analytics:** Shoulder does not collect usage statistics, feature usage, or behavioral data - **No user tracking:** No user IDs, session tracking, or cross-session correlation - **No code transmission:** Source code content never leaves the local machine - **No finding transmission:** Vulnerability findings are not sent to any server - **No keystroke capture:** No input logging or clipboard access - **No advertising identifiers:** No tracking for marketing purposes - **No crash reporting:** Errors are logged locally only; no external crash reporting service --- ## 4) Network Behavior | Purpose | When | Destination | Data Sent | Data Received | Disable? | Security | |---------|------|-------------|-----------|---------------|----------|----------| | Update check | Once per 24h (throttled) | `https://api.shoulder.dev/v1/cli/releases/{os}/latest` | OS type, User-Agent with current version | Latest version number, download URL, SHA256 checksum, changelog | `SHOULDER_DISABLE_UPDATES=1` | HTTPS, 5s timeout, TLS cert validation | | Package vulnerability scan | On-demand (`packages` command) | `https://api.shoulder.dev/v1/packages/scan` | Package names, versions, ecosystems, dev dependency flag | CVE data, CVSS scores, license info, fix versions | Don't invoke `packages` command | HTTPS, optional Bearer auth, 120s timeout | | Docker image version scan | On-demand (Dockerfile analysis) | `https://api.shoulder.dev/v1/images/batch/versions` | Image names, tags | Version metadata, EOL dates, recommended versions | Part of Dockerfile scan | HTTPS, optional Bearer auth | | Binary download | Manual update only | `https://github.com/shoulderdev/binaries/releases` | HTTP GET request (no body) | Binary archive (tar.gz) | N/A | HTTPS, SHA256 verified | ### Security Controls for Network Calls - All API calls use HTTPS with Go standard library TLS defaults (system CA validation) - HTTP client timeouts: 5 seconds for update checks, 120 seconds for batch operations - Rate limiting: Server returns HTTP 429 when limits exceeded; client handles gracefully - Authentication: Optional `SHOULDER_API_KEY` sent as Bearer token when configured ### Fully Offline Operation Shoulder can operate fully offline. The following features work without network: - Source code scanning (all vulnerability detection) - Taint flow analysis and pattern matching - Custom rule loading and validation - Report generation (console, JSON, SARIF) - Code graph caching and incremental analysis - IDE integration via local gRPC server Network-required features: - Package vulnerability lookup (sends package names/versions to API) - Update notifications (opt-out available via environment variable) --- ## 5) Filesystem Behavior ### Read Operations | Location | Purpose | Access Pattern | |----------|---------|----------------| | Project directory (recursive) | Source code for analysis | Read-only; respects exclude patterns | | `rules/` (embedded or local) | Security rules in YAML format | Read-only | | `~/.shoulder/` | User configuration and state | Read on startup | | `.shoulder/` (in project) | Project configuration and custom rules | Read on startup | | `~/.cache/shouldersec/` | Graph cache for incremental scans | Read/write | ### Write Operations | Location | What's Written | When | Retention | |----------|----------------|------|-----------| | `~/.cache/shouldersec/{hash}/graph.gob` | Serialized code graph (GOB format) | After successful scan | Until cache cleared | | `~/.cache/shouldersec/{hash}/metadata.json` | Cache metadata (version, timestamp) | After successful scan | Until cache cleared | | `~/.shoulder/logs/{session}_{date}.log` | Debug logs | Serve mode only | 10 files maximum | | `~/.shoulder/sessions.json` | Session ID to project mapping | Server startup | Indefinite | | `~/.shoulder/servers.json` | Running server registry | Server start/stop | Session lifetime | | `.shoulder/fp_history.json` | False positive dismissal records | When user dismisses finding | 12 months, max 10,000 | | User-specified output file | Scan results (JSON/SARIF) | When `--output` specified | User-managed | ### Temporary Files | File | Location | When Created | Cleanup | |------|----------|--------------|---------| | `shouldersec-update-*.tar.gz` | System temp directory | During binary update | Immediately after extraction | | `shouldersec-new-*` | System temp directory | During binary update | After atomic replacement | | Lock files (`.lock`) | `~/.shoulder/` or system temp | Server/autostart operations | Released after operation | ### No File Deletion / No Source Modification **Shoulder does not modify or delete user source code.** All write operations are limited to: - Cache directories under `~/.cache/shouldersec/` - Configuration/state directories under `~/.shoulder/` - IDE integration files (`.claude/`, `.cursor/`) when explicitly installed - User-specified output files The following deletions may occur: | What's Deleted | When | Purpose | |----------------|------|---------| | Stale cache entries | When source files change | Cache invalidation | | Old log files | When > 10 log files exist | Log rotation | | Aged FP history records | Records > 12 months old | Database cleanup | | Temp files | Immediately after use | Cleanup during updates | --- ## 6) Execution and Safety Boundaries ### Subprocess Spawning | Subprocess | Purpose | When | Security Controls | |------------|---------|------|-------------------| | `shouldersec serve start` | Background server for IDE integration | Autostart/install hooks | Executable path from `os.Executable()`; no user input | | Test runners (`pytest`, `jest`) | Test impact analysis | `test-impact` command | Arguments passed as slice (no shell injection); paths validated | | IDE CLIs (`code`, `cursor`) | Extension install/uninstall | Install commands | Hardcoded extension ID; no user input | ### No Untrusted Code Execution - Shoulder does not execute code from scanned projects - Custom rules (`.shoulder/rules/*.yaml`) are declarative YAML only; no code execution - TreeSitter parses code into AST without executing it - No `eval()`, dynamic imports, reflection-based invocation, or script interpretation - No plugin loading system or runtime extensions ### Plugin/Extension Model - All language analyzers are compiled into the binary - No runtime plugin loading or dynamic extensions - Custom rules are YAML-only with validated schema - Hook integrations (Claude Code, Cursor) read/write JSON; no arbitrary execution ### Resource Controls | Resource | Control | Default | |----------|---------|---------| | HTTP timeout (updates) | Non-blocking with timeout | 5 seconds | | HTTP timeout (API calls) | Context-based timeout | 120 seconds | | Autostart wait timeout | Maximum wait for server | 15 seconds | | Lock file TTL | Prevent stale locks | 30 seconds | | File watch interval | Polling frequency | 100ms | --- ## 7) Logging, Diagnostics, and Crash Reporting ### What Gets Logged | Log Level | Content | Sensitive Data? | |-----------|---------|-----------------| | ERROR | Fatal errors, configuration issues | No | | WARN | Non-fatal issues, deprecation notices | No | | INFO | Scan progress, finding summaries | File paths (relative) | | DEBUG | Detailed analysis steps, graph building | File paths, node counts, sizes | **Not logged:** Source code content, vulnerability details, API keys (masked) ### Where Logs Go | Mode | Destination | Format | |------|-------------|--------| | CLI scan | stderr | Timestamped text with level | | Serve mode | stderr + `~/.shoulder/logs/` | Timestamped text | | JSON/SARIF output | Suppressed (silent mode) | N/A | ### Crash Reporting **No external crash reporting.** Error handling: - Panics are recovered where possible for graceful shutdown - Errors logged locally to stderr and log files - Stack traces written to local logs only - Server tracks shutdown reason internally (signal, panic, error, graceful) - No Sentry, Datadog, Bugsnag, or similar external services ### Verbosity Controls | Control | Method | |---------|--------| | Log level | `--log-level {error\|warn\|info\|debug}` or `-v` | | Silent mode | `--json` or `--sarif` (auto-silent) | | Debug override | `DEBUG=1` environment variable | | Explicit level | `SHOULDERSEC_LOG_LEVEL` environment variable | Priority: CLI flag > `DEBUG` env var > `SHOULDERSEC_LOG_LEVEL` > default (INFO) --- ## 8) Security Measures ### Dependency Integrity - Go modules with `go.sum` checksums for reproducible builds - TreeSitter uses official Go bindings from `github.com/tree-sitter/` - No runtime dependency downloads; all dependencies compiled into binary - Security rules embedded in binary with encryption ### Update Verification | Check | Implementation | |-------|----------------| | Version comparison | Semantic versioning parsing | | SHA256 checksum | Provided in update response; verified before replacement | | Atomic replacement | Backup created; binary swapped atomically | | Version enforcement | Server can specify minimum supported version | ### TLS and Certificate Validation | Connection | TLS | Certificate Validation | |------------|-----|----------------------| | API calls to `api.shoulder.dev` | HTTPS enforced | Go standard library defaults (system CA) | | gRPC server (localhost) | None | N/A (localhost-only binding) | | Binary downloads from GitHub | HTTPS | Go standard library defaults | ### Secrets Handling | Secret | Storage | Transmission | |--------|---------|--------------| | `SHOULDER_API_KEY` | Environment variable only | Bearer token in Authorization header | | API keys in output | Masked in logs and errors | Never displayed to user | ### Principle of Least Privilege - Scanner reads source code but does not modify it - Cache/config writes limited to user's home directory - gRPC server binds to `localhost` only (not network-exposed) - No elevated privileges required for any operation - File permissions: 0644 for files, 0755 for directories --- ## 9) Configuration Controls ### Privacy and Security Controls | Control | Method | Effect | |---------|--------|--------| | Disable update checks | `SHOULDER_DISABLE_UPDATES=1` | No network calls for version checks | | Disable package scanning | Don't invoke `packages` command | No package data sent externally | | Disable caching | `--no-cache` flag | No graph cache written to disk | | Custom API endpoint | `SHOULDER_API_URL` env var | Override API destination (for testing) | | Development mode | `SHOULDER_ENV=development` | Use localhost API | ### Output Controls | Control | Method | Effect | |---------|--------|--------| | Machine-readable output | `--json` or `--sarif` | Structured output, silent logging | | Output file | `--output ` | Write results to file instead of stdout | | Severity filter | `--severity {critical\|high\|medium\|low}` | Filter findings by severity | | Confidence filter | `--min-confidence 0.0-1.0` | Filter by confidence score | | Hide remediation | `--no-remediation` | Exclude fix suggestions from output | ### Logging Controls | Control | Method | |---------|--------| | Log level | `--log-level` or `SHOULDERSEC_LOG_LEVEL` env var | | Debug mode | `-v` flag or `DEBUG=1` env var | | Timestamps | `--no-timestamps` flag | ### IDE Integration Controls | Control | Method | |---------|--------| | Install hooks | `shouldersec install claude` / `shouldersec install cursor` | | Uninstall hooks | `shouldersec uninstall claude` / `shouldersec uninstall cursor` | | Server port | `--port ` (0 for auto-assign) | | Watch parent PID | `--watch-pid ` (exit when parent exits) | --- ## 10) Verification Notes This report was compiled through systematic codebase analysis: 1. **Network calls:** Searched for `http.Client`, `http.Get`, `http.Post`, `net/http`, `grpc` usage. Identified HTTP client modules in the updater and API client packages. 2. **Filesystem operations:** Searched for `os.ReadFile`, `os.WriteFile`, `os.Create`, `os.Remove`, `os.MkdirAll`, `filepath.Walk`. Mapped all read/write locations and verified no source code modification. 3. **Logging system:** Reviewed the logging package implementation and all log call sites. Verified log content does not include source code or sensitive data. 4. **Subprocess spawning:** Searched for `exec.Command`, `os/exec` usage. Verified all subprocess calls use argument slices (no shell injection) with validated inputs. 5. **Environment variables:** Searched for `os.Getenv` calls. Documented all security-relevant variables and their effects. 6. **External dependencies:** Reviewed `go.mod` for network-capable libraries. Identified: `google.golang.org/grpc`, `google.golang.org/protobuf`, `gopkg.in/yaml.v3`, TreeSitter bindings. 7. **Configuration loading:** Reviewed config package for file access patterns and verified no unexpected file operations. 8. **Temp file handling:** Verified all temp files use `defer os.Remove()` for cleanup. --- ## 11) Open Questions / Verification Needed - **Proxy support:** Whether `HTTP_PROXY`/`HTTPS_PROXY` environment variables are fully respected by all HTTP clients (relies on Go standard library behavior) - **Custom CA bundles:** Whether `SSL_CERT_FILE` or `SSL_CERT_DIR` environment variables are supported for custom certificate authorities - **SHA256 verification completeness:** Whether the checksum provided in update responses is verified in all code paths before binary replacement - **File permission hardening:** Current implementation uses standard Unix defaults (0755/0644); no additional permission restrictions enforced - **Security audit:** No formal third-party security audit has been conducted on this codebase --- ## 12) Changelog / Version Scope | Field | Value | |-------|-------| | Report applies to | Commit 844e689 | | Report date | 2026-01-19 | | Main branch | `main` | | Previous report | Commit 79f8993 (2026-01-19) | ### Changes Since Previous Report - Updated commit reference from 79f8993 to 844e689 - Added Table of Contents for navigation - Expanded filesystem behavior documentation with lock files and temp file details - Added IDE integration controls section - Clarified gRPC server binding is localhost-only - Enhanced verification methodology documentation ### Assumptions - This report is based on source code analysis at the specified commit - Behavior may differ in future versions - Custom builds or forks may behave differently - Production API (`api.shoulder.dev`) behavior is documented based on client-side code only --- ## 13) Security Contact For reporting security vulnerabilities in Shoulder itself: - **Email:** security@shoulder.dev - **Response:** We aim to acknowledge reports within 48 hours - **Disclosure:** We support coordinated disclosure and will work with researchers to address issues before public disclosure We encourage responsible disclosure and appreciate reports from the security community. --- *This transparency report was generated to help security-conscious users understand Shoulder's data handling, network behavior, and privacy posture.* --- **Report Generation Details:** This report was generated using Claude Opus 4.5 (claude-opus-4-5-20251101) by Anthropic on 2026-01-19. The analysis was performed through systematic codebase exploration using Claude Code CLI tooling.