speedarr/Speedarr
Smooth streams first, downloads and seeding with what's left
- Repository: https://github.com/speedarr/Speedarr
- Commit:
9dc6c14600747ebcbdbc53460faabae33dbd52b2 - Generated: 2026-11-13T23:55:45+00:00
- Scorer 0.1.0, scoring prov-4+qual-2+sec-2, report schema v2
Scores
| Pillar | Score | Signal | Confidence | Coverage |
|---|---|---|---|---|
| AI provenance (estimated AI-generated share) | 1 | explicit | 95% | 100% |
| Code quality | 50 | weak | 90% | 100% |
| Security | 58 | weak | 85% | 100% |
AI provenance
Explicit AI attribution on 1% of first-party code added; an estimated 1% including velocity signals.
- Explicitly attributed share (lower bound): 1.1%
- Unattributed share in AI-consistent velocity bursts: 4.6%
- Estimated AI-generated share: 1.1%
| AI tool | Attributed commits | Lines added |
|---|---|---|
| Claude Code | 11 | 442 |
Current source lines last changed by AI-attributed commits: 213 of 30,224.
Too few lines in one group to compare finding densities.
- Stylometry index: 0.17 per 1,000 lines (narrated steps 1, placeholders 0, assistant phrasing 0, emoji 8). Reported as a signal, not scored.
| Month | Lines added | Attributed to AI |
|---|---|---|
| 2026-02 | 27,953 | 2% |
| 2026-03 | 200 | 0% |
| 2026-05 | 26 | 0% |
| 2026-06 | 6,937 | 0% |
| 2026-07 | 125 | 0% |
| 2026-08 | 1,576 | 0% |
| 2026-09 | 5,249 | 0% |
Evidence
- Claude Code: trailer 'Co-Authored-By: Claude' (7a982eeaa581)
- Claude Code: trailer 'Co-Authored-By: Claude' (23bae15e3bc3)
- Claude Code: trailer 'Co-Authored-By: Claude' (41b97c3fba7e)
- Claude Code: trailer 'Co-Authored-By: Claude' (62aab996a9e7)
- Claude Code: trailer 'Co-Authored-By: Claude' (1652d3e20ac6)
- Claude Code: trailer 'Co-Authored-By: Claude' (28b864d5e243)
- Claude Code: trailer 'Co-Authored-By: Claude' (3aa8665d2aa4)
- Claude Code: trailer 'Co-Authored-By: Claude' (ffb12ff4d371)
- Claude Code: trailer 'Co-Authored-By: Claude' (4c1462962447)
- Claude Code: trailer 'Co-Authored-By: Claude' (31aa73a3616a)
- Claude Code: trailer 'Co-Authored-By: Claude' (023c2dcf6134)
- 1,942 lines of first-party code in ~3.3h (584 lines/hour, 13 commit session) (05e8941c36e4)
- step-by-step narration comment: # First, walk interface names to filter early (backend/app/)
AI provenance describes how code was produced; it is not a quality judgment. Unless attribution is explicit, these are signals consistent with AI generation, not proof. Squash/rebase workflows, imported code, and rewritten history reduce accuracy.
Code quality
Code quality is weak: test-to-source ratio 0.17, no CI test run detected; 33% of function code in complex or long functions; 11% duplicated lines. Weakest area: complexity.
| Area | Score |
|---|---|
| Complexity (lizard) | 38 |
| Duplication | 53 |
| Code smells (Opengrep) | 42 |
| Tests and CI | 54 |
| Documentation | 65 |
| Type safety | 74 |
| Process (Scorecard review/maintenance) | n/a |
- Functions: 1,345; mean complexity 3.4, 90th percentile 7; 36 complex and 22 long functions
- Duplicated lines: 10.6% of 22,755 compared
- Tests: 5,193 test lines for 30,224 source lines (ratio 0.17); CI test commands: none detected; 42% of recent source commits also change tests
- Docs missing or thin: contributing, changelog
Most complex functions:
- test_connection in backend/app/api/settings.py: complexity 118, 472 lines
- NotificationsSettings in frontend/src/components/settings/NotificationsSettings.tsx: complexity 67, 402 lines
- _download_poll_cycle in backend/app/services/polling_monitor.py: complexity 51, 199 lines
- discover_interfaces in backend/app/services/snmp_monitor.py: complexity 43, 131 lines
- NotificationsStep in frontend/src/components/wizard/steps/NotificationsStep.tsx: complexity 41, 304 lines
Security
Security posture is weak: 40 known vulnerabilities in 12 dependencies; 7 high-severity SAST findings; 14 high-severity workflow issues. Weakest area: ci actions.
| Area | Score |
|---|---|
| Secrets (gitleaks, tree + history) | 100 |
| Static analysis (Opengrep) | 88 |
| Vulnerable dependencies (OSV) | 26 |
| CI workflows (zizmor) | 6 |
| Posture (policy, updates, signing, lockfiles) | 40 |
| OpenSSF Scorecard | n/a |
-
Known vulnerabilities: 40 in 12 packages (critical 0, high 20, medium 18, low 2)
-
Posture checks passed: dependency updates, lockfiles; missing: security policy, signed commits
Top findings
| Severity | Finding | Location |
|---|---|---|
| high | opengrep/dockerfile.security.missing-user-entrypoint: By not specifying a USER, a program in the container may run as 'root'. This is a security hazard. If an attacker can control a process running as root, they may have control over the container. Ensure that the last USER in a Dockerfile is a USER other than 'root'. [confidence medium] |
backend/Dockerfile:104 |
| high | opengrep/dockerfile.security.missing-user: By not specifying a USER, a program in the container may run as 'root'. This is a security hazard. If an attacker can control a process running as root, they may have control over the container. Ensure that the last USER in a Dockerfile is a USER other than 'root'. [confidence medium] |
backend/Dockerfile:105 |
| high | opengrep/python.lang.security.use-defused-xml: The Python documentation recommends using defusedxml instead of xml because the native Python xml library is vulnerable to XML External Entity (XXE) attacks. These attacks can leak confidential data and "XML bombs" can cause denial of service. [confidence low] |
backend/app/clients/plex.py:7 |
| high | opengrep/python.sqlalchemy.security.sqlalchemy-execute-raw-query: Avoiding SQL string concatenation: untrusted input concatenated with raw SQL query can result in SQL Injection. In order to execute raw query safely, prepared statement should be used. SQLAlchemy provides TextualSQL to easily used prepared statement with named parameters. For complex SQL composition [confidence low] |
backend/app/database.py:88 |
| high | opengrep/python.sqlalchemy.security.audit.avoid-sqlalchemy-text: sqlalchemy.text passes the constructed SQL statement to the database mostly unchanged. This means that the usual SQL injection protections are not applied and this function is vulnerable to SQL injection if user input can reach here. Use normal SQLAlchemy operators (such as or_, and_, etc.) to const [confidence medium] |
backend/app/database.py:134 |
| high | opengrep/python.sqlalchemy.security.audit.avoid-sqlalchemy-text: sqlalchemy.text passes the constructed SQL statement to the database mostly unchanged. This means that the usual SQL injection protections are not applied and this function is vulnerable to SQL injection if user input can reach here. Use normal SQLAlchemy operators (such as or_, and_, etc.) to const [confidence medium] |
backend/app/database.py:196 |
| high | opengrep/python.sqlalchemy.security.audit.avoid-sqlalchemy-text: sqlalchemy.text passes the constructed SQL statement to the database mostly unchanged. This means that the usual SQL injection protections are not applied and this function is vulnerable to SQL injection if user input can reach here. Use normal SQLAlchemy operators (such as or_, and_, etc.) to const [confidence medium] |
backend/app/database.py:201 |
| high | osv/GHSA-x33g-cr3x-6449: pyjwt@2.14.0 (PyPI) is affected by PYSEC-2026-4183, GHSA-x33g-cr3x-6449; also in backend/requirements.txt |
backend/requirements-dev.txt |
| high | osv/GHSA-2g87-pp6c-29x5: aiohttp@3.14.3 (PyPI) is affected by GHSA-2g87-pp6c-29x5; also in backend/requirements.txt |
backend/requirements-dev.txt |
| high | osv/GHSA-5wr8-gcqf-gqf3: aiohttp@3.14.3 (PyPI) is affected by GHSA-5wr8-gcqf-gqf3; also in backend/requirements.txt |
backend/requirements-dev.txt |
| high | osv/GHSA-9xw5-w5jj-pvcg: aiohttp@3.14.3 (PyPI) is affected by GHSA-9xw5-w5jj-pvcg; also in backend/requirements.txt |
backend/requirements-dev.txt |
| high | osv/GHSA-2qm8-x737-gmw5: pyasn1@0.6.4 (PyPI) is affected by GHSA-2qm8-x737-gmw5; also in backend/requirements.txt |
backend/requirements-dev.txt |
| high | osv/GHSA-9m75-vc3g-4x39: pyasn1@0.6.4 (PyPI) is affected by GHSA-9m75-vc3g-4x39; also in backend/requirements.txt |
backend/requirements-dev.txt |
| high | osv/GHSA-fm9c-5rcf-2q5p: pyasn1@0.6.4 (PyPI) is affected by GHSA-fm9c-5rcf-2q5p; also in backend/requirements.txt |
backend/requirements-dev.txt |
| high | osv/GHSA-mm57-4v3p-rchx: pyasn1@0.6.4 (PyPI) is affected by GHSA-mm57-4v3p-rchx; also in backend/requirements.txt |
backend/requirements-dev.txt |
| high | osv/GHSA-6j4f-fj2g-mc7p: brace-expansion@5.0.9 (npm) is affected by GHSA-6j4f-fj2g-mc7p |
frontend/package-lock.json |
| high | osv/GHSA-qhr7-859c-m2p7: brace-expansion@5.0.9 (npm) is affected by GHSA-qhr7-859c-m2p7 |
frontend/package-lock.json |
| high | osv/GHSA-8r9p-f939-6h3c: follow-redirects@1.16.0 (npm) is affected by GHSA-8r9p-f939-6h3c |
frontend/package-lock.json |
| high | osv/GHSA-mrwp-f3q8-3g9p: follow-redirects@1.16.0 (npm) is affected by GHSA-mrwp-f3q8-3g9p |
frontend/package-lock.json |
| high | osv/GHSA-q3jh-wrc6-jgq8: follow-redirects@1.16.0 (npm) is affected by GHSA-q3jh-wrc6-jgq8 |
frontend/package-lock.json |
| high | osv/GHSA-68fv-2mgg-jv7q: source-map-js@1.2.1 (npm) is affected by GHSA-68fv-2mgg-jv7q |
frontend/package-lock.json |
| high | osv/GHSA-2m5v-pch6-74hx: undici@8.10.2 (npm) is affected by GHSA-2m5v-pch6-74hx |
frontend/package-lock.json |
| high | osv/GHSA-4w7w-5xrc-9h26: undici@8.10.2 (npm) is affected by GHSA-4w7w-5xrc-9h26 |
frontend/package-lock.json |
| high | osv/GHSA-qrxm-fqhp-jwvm: undici@8.10.2 (npm) is affected by GHSA-qrxm-fqhp-jwvm |
frontend/package-lock.json |
| high | osv/GHSA-xjj6-f33q-929c: undici@8.10.2 (npm) is affected by GHSA-xjj6-f33q-929c |
frontend/package-lock.json |
Static signals only: the scorer never runs the project's code. Secret findings are pattern matches that were not verified, and secret values are never stored.
Repository profile
- Source lines: 30,224; test lines: 5,193
| Language | Lines |
|---|---|
| TypeScript | 17,898 |
| Python | 17,385 |
| JavaScript | 108 |
| Shell | 26 |