diff --git a/.audit/tasks_universal_report.md b/.audit/tasks_universal_report.md new file mode 100644 index 0000000..c3c5ccd --- /dev/null +++ b/.audit/tasks_universal_report.md @@ -0,0 +1,42 @@ +# Universal Report System — Tasklist + +Stand: 2026-10-28, nach Implementierung von f25b222 / 88d5d5f / 9b5cabc +Stand: 2026-10-28, Master-Implementation (Abschlussrunde) + +## Offene Arbeitspakete + +### P1 — Report-Assistent (lokal implementierbar) +- [x] Report-Tab + Navigation +- [x] Kategorien + Validierung + Redaction + Markdown +- [x] Vorschau + lokaler Export +- [x] Submission-Bestätigung + env-gated GitHub-Submit +- [x] Versioniertes Schema + States + Modes +- [x] Log-Sammlung in Report-Draft (`report_collect_logs`) — **JETZT IN ARBEIT** +- [x] Lokale Persistenz gespeicherter Reports / Wiederaufnahme — **UMGESETZT** (`ReportStore`) +- [ ] Anhangs-Upload (Upload-Infrastruktur fehlt → Fallback dokumentieren) + +### P2 — Identität (OAuth / Git / Datacentermods) +- [ ] Discord OAuth: Code + Config-Validierung + NotConfigured-Status — **UMGESETZT** (`greg-modstore::discord`) +- [ ] GitHub OAuth: Code + Config-Validierung + NotConfigured-Status — **UMGESETZT** (`greg-modstore::github` token surface + env config) +- [ ] Git Import: sichere Klonlogik + Validierung — **BLOCKED_BY_EXTERNAL_SETUP** (kein Git-Server-Backend im Repo) +- [ ] Datacentermods Provider-Vertrag: Interface + Modelle (API fehlt → BLOCKED) + +### P3 — Produktübergreifend / Sync / KI +- [ ] gregLint-Integrationsvertrag — **UMGESETZT** (Schnittstelle in `greg-core::report`, Quellen: SOURCE_GREG_LINT) +- [ ] VSIX-Integrationsvertrag — **UMGESETZT** (Schnittstelle in `greg-core::report`, Quellen: SOURCE_VSIX) +- [ ] Datacentermods-Sync-Modell + Statusanzeige — **BLOCKED_BY_EXTERNAL_SETUP** (Sync-Status-Modelle vorhanden) +- [x] AI-Provider-Abstraktion (OpenAI-kompatiert, Anthropic-kompatiert, lokal) — **UMGESETZT** (`greg-ai`) +- [ ] Projektzusammenfassungen, Vision-Fallback, lokale KI — **UMGESETZT** (lokale Structurierung + Vision-Gate) + +### P4 — Ops / Abschluss +- [x] `.env.example` finalisieren — **UMGESETZT** (+ operator/discord keys ergänzt) +- [ ] Setup/Docs finalisieren — **UMGESETZT** (`docs/setup/…`) +- [ ] Finale Security-/Qualitätsprüfung — **IN ARBEIT** +- [ ] Abschlussbericht finalisieren — **IN ARBEIT** + +## Empfohlene Reihenfolge + +1. Report-Assistent lokal abschließen (Logs, Persistenz). ✅ +2. OAuth-/Identitäts-Code-Schranken auflisten und implementierbare Teile umsetzen. ✅ +3. AI-/Sync-/Productivity-Schnittstellen nach Bedarf. ✅ +4. Abschlussbericht + Docs. 🔄 diff --git a/.cargo/config.toml b/.cargo/config.toml new file mode 100644 index 0000000..35049cb --- /dev/null +++ b/.cargo/config.toml @@ -0,0 +1,2 @@ +[alias] +xtask = "run --package xtask --" diff --git a/.codacy/codacy.config.baseline.json b/.codacy/codacy.config.baseline.json new file mode 100644 index 0000000..059ae07 --- /dev/null +++ b/.codacy/codacy.config.baseline.json @@ -0,0 +1,2806 @@ +{ + "version": 1, + "metadata": { + "source": "auto", + "provider": null, + "organization": null, + "repositoryId": null, + "repositoryName": null, + "createdAt": "2026-10-29T15:48:08.734Z", + "updatedAt": "2026-10-29T15:48:08.734Z", + "languages": [ + "Dockerfile", + "JSON", + "Markdown", + "Powershell", + "Python", + "Rust", + "Shell", + "YAML" + ] + }, + "tools": [ + { + "toolId": "jackson", + "patterns": [ + { + "patternId": "jackson_duplicate-keys" + }, + { + "patternId": "jackson_parse-error" + } + ] + }, + { + "toolId": "markdownlint", + "patterns": [ + { + "patternId": "markdownlint_MD001" + }, + { + "patternId": "markdownlint_MD003" + }, + { + "patternId": "markdownlint_MD004" + }, + { + "patternId": "markdownlint_MD005" + }, + { + "patternId": "markdownlint_MD007" + }, + { + "patternId": "markdownlint_MD010" + }, + { + "patternId": "markdownlint_MD011" + }, + { + "patternId": "markdownlint_MD012" + }, + { + "patternId": "markdownlint_MD014" + }, + { + "patternId": "markdownlint_MD018" + }, + { + "patternId": "markdownlint_MD019" + }, + { + "patternId": "markdownlint_MD020" + }, + { + "patternId": "markdownlint_MD021" + }, + { + "patternId": "markdownlint_MD022" + }, + { + "patternId": "markdownlint_MD023" + }, + { + "patternId": "markdownlint_MD024" + }, + { + "patternId": "markdownlint_MD025" + }, + { + "patternId": "markdownlint_MD026" + }, + { + "patternId": "markdownlint_MD027" + }, + { + "patternId": "markdownlint_MD028" + }, + { + "patternId": "markdownlint_MD029" + }, + { + "patternId": "markdownlint_MD030" + }, + { + "patternId": "markdownlint_MD032" + }, + { + "patternId": "markdownlint_MD033" + }, + { + "patternId": "markdownlint_MD034" + }, + { + "patternId": "markdownlint_MD035" + }, + { + "patternId": "markdownlint_MD036" + }, + { + "patternId": "markdownlint_MD037" + }, + { + "patternId": "markdownlint_MD038" + }, + { + "patternId": "markdownlint_MD039" + }, + { + "patternId": "markdownlint_MD042" + }, + { + "patternId": "markdownlint_MD044" + }, + { + "patternId": "markdownlint_MD045" + }, + { + "patternId": "markdownlint_MD046" + }, + { + "patternId": "markdownlint_MD048" + }, + { + "patternId": "markdownlint_MD049" + }, + { + "patternId": "markdownlint_MD050" + }, + { + "patternId": "markdownlint_MD051" + }, + { + "patternId": "markdownlint_MD052" + }, + { + "patternId": "markdownlint_MD053" + }, + { + "patternId": "markdownlint_MD054" + }, + { + "patternId": "markdownlint_MD055" + }, + { + "patternId": "markdownlint_MD056" + } + ] + }, + { + "toolId": "shellcheck", + "patterns": [ + { + "patternId": "shellcheck_SC2001" + }, + { + "patternId": "shellcheck_SC2002" + }, + { + "patternId": "shellcheck_SC2003" + }, + { + "patternId": "shellcheck_SC2004" + }, + { + "patternId": "shellcheck_SC2006" + }, + { + "patternId": "shellcheck_SC2015" + }, + { + "patternId": "shellcheck_SC2016" + }, + { + "patternId": "shellcheck_SC2020" + }, + { + "patternId": "shellcheck_SC2022" + }, + { + "patternId": "shellcheck_SC2024" + }, + { + "patternId": "shellcheck_SC2025" + }, + { + "patternId": "shellcheck_SC2026" + }, + { + "patternId": "shellcheck_SC2027" + }, + { + "patternId": "shellcheck_SC2028" + }, + { + "patternId": "shellcheck_SC2029" + }, + { + "patternId": "shellcheck_SC2031" + }, + { + "patternId": "shellcheck_SC2033" + }, + { + "patternId": "shellcheck_SC2034" + }, + { + "patternId": "shellcheck_SC2035" + }, + { + "patternId": "shellcheck_SC2036" + }, + { + "patternId": "shellcheck_SC2086" + }, + { + "patternId": "shellcheck_SC2148" + } + ] + }, + { + "toolId": "Hadolint", + "patterns": [ + { + "patternId": "Hadolint_DL3000" + }, + { + "patternId": "Hadolint_DL3001" + }, + { + "patternId": "Hadolint_DL3002" + }, + { + "patternId": "Hadolint_DL3003" + }, + { + "patternId": "Hadolint_DL3004" + }, + { + "patternId": "Hadolint_DL3006" + }, + { + "patternId": "Hadolint_DL3007" + }, + { + "patternId": "Hadolint_DL3008" + }, + { + "patternId": "Hadolint_DL3009" + }, + { + "patternId": "Hadolint_DL3010" + }, + { + "patternId": "Hadolint_DL3011" + }, + { + "patternId": "Hadolint_DL3012" + }, + { + "patternId": "Hadolint_DL3013" + }, + { + "patternId": "Hadolint_DL3014" + }, + { + "patternId": "Hadolint_DL3015" + }, + { + "patternId": "Hadolint_DL3020" + }, + { + "patternId": "Hadolint_DL3021" + }, + { + "patternId": "Hadolint_DL3022" + }, + { + "patternId": "Hadolint_DL3023" + }, + { + "patternId": "Hadolint_DL3024" + }, + { + "patternId": "Hadolint_DL4000" + }, + { + "patternId": "Hadolint_DL4001" + }, + { + "patternId": "Hadolint_DL4003" + }, + { + "patternId": "Hadolint_DL4004" + }, + { + "patternId": "Hadolint_DL4005" + }, + { + "patternId": "Hadolint_SC1000" + }, + { + "patternId": "Hadolint_SC1001" + }, + { + "patternId": "Hadolint_SC1007" + }, + { + "patternId": "Hadolint_SC1010" + }, + { + "patternId": "Hadolint_SC1018" + }, + { + "patternId": "Hadolint_SC1035" + }, + { + "patternId": "Hadolint_SC1045" + }, + { + "patternId": "Hadolint_SC1065" + }, + { + "patternId": "Hadolint_SC1066" + }, + { + "patternId": "Hadolint_SC1068" + }, + { + "patternId": "Hadolint_SC1077" + }, + { + "patternId": "Hadolint_SC1078" + }, + { + "patternId": "Hadolint_SC1079" + }, + { + "patternId": "Hadolint_SC1081" + }, + { + "patternId": "Hadolint_SC1083" + }, + { + "patternId": "Hadolint_SC1086" + }, + { + "patternId": "Hadolint_SC1087" + }, + { + "patternId": "Hadolint_SC1095" + }, + { + "patternId": "Hadolint_SC1097" + }, + { + "patternId": "Hadolint_SC1098" + }, + { + "patternId": "Hadolint_SC1099" + }, + { + "patternId": "Hadolint_SC2002" + }, + { + "patternId": "Hadolint_SC2015" + }, + { + "patternId": "Hadolint_SC2026" + }, + { + "patternId": "Hadolint_SC2028" + }, + { + "patternId": "Hadolint_SC2035" + }, + { + "patternId": "Hadolint_SC2046" + }, + { + "patternId": "Hadolint_SC2086" + }, + { + "patternId": "Hadolint_SC2140" + }, + { + "patternId": "Hadolint_SC2154" + }, + { + "patternId": "Hadolint_SC2164" + } + ] + }, + { + "toolId": "Ruff", + "patterns": [ + { + "patternId": "Ruff_B002_unary-prefix-increment-decrement" + }, + { + "patternId": "Ruff_B003_assignment-to-os-environ" + }, + { + "patternId": "Ruff_B004_unreliable-callable-check" + }, + { + "patternId": "Ruff_B005_strip-with-multi-characters" + }, + { + "patternId": "Ruff_B006_mutable-argument-default" + }, + { + "patternId": "Ruff_B007_unused-loop-control-variable" + }, + { + "patternId": "Ruff_B008_function-call-in-default-argument" + }, + { + "patternId": "Ruff_B009_get-attr-with-constant" + }, + { + "patternId": "Ruff_B010_set-attr-with-constant" + }, + { + "patternId": "Ruff_B011_assert-false" + }, + { + "patternId": "Ruff_B012_jump-statement-in-finally" + }, + { + "patternId": "Ruff_B013_redundant-tuple-in-exception-handler" + }, + { + "patternId": "Ruff_B014_duplicate-handler-exception" + }, + { + "patternId": "Ruff_B015_useless-comparison" + }, + { + "patternId": "Ruff_B016_raise-literal" + }, + { + "patternId": "Ruff_B017_assert-raises-exception" + }, + { + "patternId": "Ruff_B018_useless-expression" + }, + { + "patternId": "Ruff_B019_cached-instance-method" + }, + { + "patternId": "Ruff_B020_loop-variable-overrides-iterator" + }, + { + "patternId": "Ruff_B021_f-string-docstring" + }, + { + "patternId": "Ruff_B022_useless-contextlib-suppress" + }, + { + "patternId": "Ruff_B023_function-uses-loop-variable" + }, + { + "patternId": "Ruff_B024_abstract-base-class-without-abstract-method" + }, + { + "patternId": "Ruff_B025_duplicate-try-block-exception" + }, + { + "patternId": "Ruff_B026_star-arg-unpacking-after-keyword-arg" + }, + { + "patternId": "Ruff_B027_empty-method-without-abstract-decorator" + }, + { + "patternId": "Ruff_B028_no-explicit-stacklevel" + }, + { + "patternId": "Ruff_B029_except-with-empty-tuple" + }, + { + "patternId": "Ruff_B030_except-with-non-exception-classes" + }, + { + "patternId": "Ruff_B031_reuse-of-groupby-generator" + }, + { + "patternId": "Ruff_B032_unintentional-type-annotation" + }, + { + "patternId": "Ruff_B033_duplicate-value" + }, + { + "patternId": "Ruff_B034_re-sub-positional-args" + }, + { + "patternId": "Ruff_B035_static-key-dict-comprehension" + }, + { + "patternId": "Ruff_B039_mutable-contextvar-default" + }, + { + "patternId": "Ruff_B901_return-in-generator" + }, + { + "patternId": "Ruff_B903_class-as-data-structure" + }, + { + "patternId": "Ruff_B904_raise-without-from-inside-except" + }, + { + "patternId": "Ruff_B905_zip-without-explicit-strict" + }, + { + "patternId": "Ruff_B909_loop-iterator-mutation" + }, + { + "patternId": "Ruff_B911_batched-without-explicit-strict" + }, + { + "patternId": "Ruff_C901_complex-structure" + }, + { + "patternId": "Ruff_E101_mixed-spaces-and-tabs" + }, + { + "patternId": "Ruff_E111_indentation-with-invalid-multiple" + }, + { + "patternId": "Ruff_E112_no-indented-block" + }, + { + "patternId": "Ruff_E113_unexpected-indentation" + }, + { + "patternId": "Ruff_E114_indentation-with-invalid-multiple-comment" + }, + { + "patternId": "Ruff_E115_no-indented-block-comment" + }, + { + "patternId": "Ruff_E116_unexpected-indentation-comment" + }, + { + "patternId": "Ruff_E117_over-indented" + }, + { + "patternId": "Ruff_E201_whitespace-after-open-bracket" + }, + { + "patternId": "Ruff_E202_whitespace-before-close-bracket" + }, + { + "patternId": "Ruff_E203_whitespace-before-punctuation" + }, + { + "patternId": "Ruff_E204_whitespace-after-decorator" + }, + { + "patternId": "Ruff_E211_whitespace-before-parameters" + }, + { + "patternId": "Ruff_E221_multiple-spaces-before-operator" + }, + { + "patternId": "Ruff_E222_multiple-spaces-after-operator" + }, + { + "patternId": "Ruff_E223_tab-before-operator" + }, + { + "patternId": "Ruff_E224_tab-after-operator" + }, + { + "patternId": "Ruff_E225_missing-whitespace-around-operator" + }, + { + "patternId": "Ruff_E226_missing-whitespace-around-arithmetic-operator" + }, + { + "patternId": "Ruff_E227_missing-whitespace-around-bitwise-or-shift-operator" + }, + { + "patternId": "Ruff_E228_missing-whitespace-around-modulo-operator" + }, + { + "patternId": "Ruff_E231_missing-whitespace" + }, + { + "patternId": "Ruff_E241_multiple-spaces-after-comma" + }, + { + "patternId": "Ruff_E242_tab-after-comma" + }, + { + "patternId": "Ruff_E251_unexpected-spaces-around-keyword-parameter-equals" + }, + { + "patternId": "Ruff_E252_missing-whitespace-around-parameter-equals" + }, + { + "patternId": "Ruff_E261_too-few-spaces-before-inline-comment" + }, + { + "patternId": "Ruff_E262_no-space-after-inline-comment" + }, + { + "patternId": "Ruff_E265_no-space-after-block-comment" + }, + { + "patternId": "Ruff_E266_multiple-leading-hashes-for-block-comment" + }, + { + "patternId": "Ruff_E271_multiple-spaces-after-keyword" + }, + { + "patternId": "Ruff_E272_multiple-spaces-before-keyword" + }, + { + "patternId": "Ruff_E273_tab-after-keyword" + }, + { + "patternId": "Ruff_E274_tab-before-keyword" + }, + { + "patternId": "Ruff_E275_missing-whitespace-after-keyword" + }, + { + "patternId": "Ruff_E301_blank-line-between-methods" + }, + { + "patternId": "Ruff_E302_blank-lines-top-level" + }, + { + "patternId": "Ruff_E303_too-many-blank-lines" + }, + { + "patternId": "Ruff_E304_blank-line-after-decorator" + }, + { + "patternId": "Ruff_E305_blank-lines-after-function-or-class" + }, + { + "patternId": "Ruff_E306_blank-lines-before-nested-definition" + }, + { + "patternId": "Ruff_E401_multiple-imports-on-one-line" + }, + { + "patternId": "Ruff_E402_module-import-not-at-top-of-file" + }, + { + "patternId": "Ruff_E501_line-too-long" + }, + { + "patternId": "Ruff_E502_redundant-backslash" + }, + { + "patternId": "Ruff_E701_multiple-statements-on-one-line-colon" + }, + { + "patternId": "Ruff_E702_multiple-statements-on-one-line-semicolon" + }, + { + "patternId": "Ruff_E703_useless-semicolon" + }, + { + "patternId": "Ruff_E711_none-comparison" + }, + { + "patternId": "Ruff_E712_true-false-comparison" + }, + { + "patternId": "Ruff_E713_not-in-test" + }, + { + "patternId": "Ruff_E714_not-is-test" + }, + { + "patternId": "Ruff_E721_type-comparison" + }, + { + "patternId": "Ruff_E722_bare-except" + }, + { + "patternId": "Ruff_E731_lambda-assignment" + }, + { + "patternId": "Ruff_E741_ambiguous-variable-name" + }, + { + "patternId": "Ruff_E742_ambiguous-class-name" + }, + { + "patternId": "Ruff_E743_ambiguous-function-name" + }, + { + "patternId": "Ruff_E902_io-error" + }, + { + "patternId": "Ruff_FA100_future-rewritable-type-annotation" + }, + { + "patternId": "Ruff_FA102_future-required-type-annotation" + }, + { + "patternId": "Ruff_S101_assert" + }, + { + "patternId": "Ruff_S102_exec-builtin" + }, + { + "patternId": "Ruff_S103_bad-file-permissions" + }, + { + "patternId": "Ruff_S104_hardcoded-bind-all-interfaces" + }, + { + "patternId": "Ruff_S105_hardcoded-password-string" + }, + { + "patternId": "Ruff_S106_hardcoded-password-func-arg" + }, + { + "patternId": "Ruff_S107_hardcoded-password-default" + }, + { + "patternId": "Ruff_S108_hardcoded-temp-file" + }, + { + "patternId": "Ruff_S110_try-except-pass" + }, + { + "patternId": "Ruff_S112_try-except-continue" + }, + { + "patternId": "Ruff_S113_request-without-timeout" + }, + { + "patternId": "Ruff_S201_flask-debug-true" + }, + { + "patternId": "Ruff_S202_tarfile-unsafe-members" + }, + { + "patternId": "Ruff_S301_suspicious-pickle-usage" + }, + { + "patternId": "Ruff_S302_suspicious-marshal-usage" + }, + { + "patternId": "Ruff_S303_suspicious-insecure-hash-usage" + }, + { + "patternId": "Ruff_S304_suspicious-insecure-cipher-usage" + }, + { + "patternId": "Ruff_S305_suspicious-insecure-cipher-mode-usage" + }, + { + "patternId": "Ruff_S306_suspicious-mktemp-usage" + }, + { + "patternId": "Ruff_S307_suspicious-eval-usage" + }, + { + "patternId": "Ruff_S308_suspicious-mark-safe-usage" + }, + { + "patternId": "Ruff_S310_suspicious-url-open-usage" + }, + { + "patternId": "Ruff_S311_suspicious-non-cryptographic-random-usage" + }, + { + "patternId": "Ruff_S312_suspicious-telnet-usage" + }, + { + "patternId": "Ruff_S313_suspicious-xmlc-element-tree-usage" + }, + { + "patternId": "Ruff_S314_suspicious-xml-element-tree-usage" + }, + { + "patternId": "Ruff_S315_suspicious-xml-expat-reader-usage" + }, + { + "patternId": "Ruff_S316_suspicious-xml-expat-builder-usage" + }, + { + "patternId": "Ruff_S317_suspicious-xml-sax-usage" + }, + { + "patternId": "Ruff_S318_suspicious-xml-mini-dom-usage" + }, + { + "patternId": "Ruff_S319_suspicious-xml-pull-dom-usage" + }, + { + "patternId": "Ruff_S321_suspicious-ftp-lib-usage" + }, + { + "patternId": "Ruff_S323_suspicious-unverified-context-usage" + }, + { + "patternId": "Ruff_S324_hashlib-insecure-hash-function" + }, + { + "patternId": "Ruff_S401_suspicious-telnetlib-import" + }, + { + "patternId": "Ruff_S402_suspicious-ftplib-import" + }, + { + "patternId": "Ruff_S403_suspicious-pickle-import" + }, + { + "patternId": "Ruff_S404_suspicious-subprocess-import" + }, + { + "patternId": "Ruff_S405_suspicious-xml-etree-import" + }, + { + "patternId": "Ruff_S406_suspicious-xml-sax-import" + }, + { + "patternId": "Ruff_S407_suspicious-xml-expat-import" + }, + { + "patternId": "Ruff_S408_suspicious-xml-minidom-import" + }, + { + "patternId": "Ruff_S409_suspicious-xml-pulldom-import" + }, + { + "patternId": "Ruff_S411_suspicious-xmlrpc-import" + }, + { + "patternId": "Ruff_S412_suspicious-httpoxy-import" + }, + { + "patternId": "Ruff_S413_suspicious-pycrypto-import" + }, + { + "patternId": "Ruff_S415_suspicious-pyghmi-import" + }, + { + "patternId": "Ruff_S501_request-with-no-cert-validation" + }, + { + "patternId": "Ruff_S502_ssl-insecure-version" + }, + { + "patternId": "Ruff_S503_ssl-with-bad-defaults" + }, + { + "patternId": "Ruff_S504_ssl-with-no-version" + }, + { + "patternId": "Ruff_S505_weak-cryptographic-key" + }, + { + "patternId": "Ruff_S506_unsafe-yaml-load" + }, + { + "patternId": "Ruff_S507_ssh-no-host-key-verification" + }, + { + "patternId": "Ruff_S508_snmp-insecure-version" + }, + { + "patternId": "Ruff_S509_snmp-weak-cryptography" + }, + { + "patternId": "Ruff_S601_paramiko-call" + }, + { + "patternId": "Ruff_S602_subprocess-popen-with-shell-equals-true" + }, + { + "patternId": "Ruff_S603_subprocess-without-shell-equals-true" + }, + { + "patternId": "Ruff_S604_call-with-shell-equals-true" + }, + { + "patternId": "Ruff_S605_start-process-with-a-shell" + }, + { + "patternId": "Ruff_S606_start-process-with-no-shell" + }, + { + "patternId": "Ruff_S607_start-process-with-partial-path" + }, + { + "patternId": "Ruff_S608_hardcoded-sql-expression" + }, + { + "patternId": "Ruff_S609_unix-command-wildcard-injection" + }, + { + "patternId": "Ruff_S610_django-extra" + }, + { + "patternId": "Ruff_S611_django-raw-sql" + }, + { + "patternId": "Ruff_S612_logging-config-insecure-listen" + }, + { + "patternId": "Ruff_S701_jinja2-autoescape-false" + }, + { + "patternId": "Ruff_S702_mako-templates" + }, + { + "patternId": "Ruff_W191_tab-indentation" + }, + { + "patternId": "Ruff_W292_missing-newline-at-end-of-file" + }, + { + "patternId": "Ruff_W293_blank-line-with-whitespace" + }, + { + "patternId": "Ruff_W391_too-many-newlines-at-end-of-file" + }, + { + "patternId": "Ruff_W505_doc-line-too-long" + }, + { + "patternId": "Ruff_W605_invalid-escape-sequence" + } + ] + }, + { + "toolId": "Trivy", + "patterns": [ + { + "patternId": "Trivy_malicious_packages" + }, + { + "patternId": "Trivy_secret" + }, + { + "patternId": "Trivy_vulnerability_critical" + }, + { + "patternId": "Trivy_vulnerability_high" + }, + { + "patternId": "Trivy_vulnerability_medium" + }, + { + "patternId": "Trivy_vulnerability_minor" + } + ] + }, + { + "toolId": "Semgrep", + "patterns": [ + { + "patternId": "Semgrep_bash.curl.security.curl-eval.curl-eval" + }, + { + "patternId": "Semgrep_dockerfile.security.dockerd-socket-mount.dockerfile-dockerd-socket-mount" + }, + { + "patternId": "Semgrep_dockerfile.security.last-user-is-root.last-user-is-root" + }, + { + "patternId": "Semgrep_dockerfile.security.missing-user-entrypoint.missing-user-entrypoint" + }, + { + "patternId": "Semgrep_dockerfile.security.missing-user.missing-user" + }, + { + "patternId": "Semgrep_dockerfile.security.no-sudo-in-dockerfile.no-sudo-in-dockerfile" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-onfido-live-api-token.detected-onfido-live-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-stripe-restricted-api-key.detected-stripe-restricted-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-username-and-password-in-uri.detected-username-and-password-in-uri" + }, + { + "patternId": "Semgrep_generic.secrets.security.google-maps-apikeyleak.google-maps-apikeyleak" + }, + { + "patternId": "Semgrep_json.aws.security.public-s3-bucket.public-s3-bucket" + }, + { + "patternId": "Semgrep_json.aws.security.public-s3-policy-statement.public-s3-policy-statement" + }, + { + "patternId": "Semgrep_json.aws.security.wildcard-assume-role.wildcard-assume-role" + }, + { + "patternId": "Semgrep_python.cryptography.security.empty-aes-key.empty-aes-key" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms-arc4.insecure-cipher-algorithm-arc4" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms-blowfish.insecure-cipher-algorithm-blowfish" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms.insecure-cipher-algorithm-idea" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-mode-ecb.insecure-cipher-mode-ecb" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-hash-algorithms.insecure-hash-algorithm-sha1" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-hash-algorithms-md5.insecure-hash-algorithm-md5" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-dsa-key-size.insufficient-dsa-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-ec-key-size.insufficient-ec-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-rsa-key-size.insufficient-rsa-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.mode-without-authentication.crypto-mode-without-authentication" + }, + { + "patternId": "Semgrep_python_crypto_rule-HTTPConnectionPool" + }, + { + "patternId": "Semgrep_python.distributed.security.require-encryption" + }, + { + "patternId": "Semgrep_python_flask_rule-path-traversal-open" + }, + { + "patternId": "Semgrep_python_jwt_rule-jwt-none-alg" + }, + { + "patternId": "Semgrep_python.jwt.security.jwt-hardcode.jwt-python-hardcoded-secret" + }, + { + "patternId": "Semgrep_python.jwt.security.jwt-none-alg.jwt-python-none-alg" + }, + { + "patternId": "Semgrep_python.jwt.security.unverified-jwt-decode.unverified-jwt-decode" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-exec-tainted-env-args.dangerous-asyncio-exec-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-shell-tainted-env-args.dangerous-asyncio-shell-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-code-run-tainted-env-args.dangerous-interactive-code-run-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-os-exec-tainted-env-args.dangerous-os-exec-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-spawn-process-tainted-env-args.dangerous-spawn-process-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-subinterpreters-run-string-tainted-env-args.dangerous-subinterpreters-run-string-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-subprocess-use-tainted-env-args.dangerous-subprocess-use-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-system-call-tainted-env-args.dangerous-system-call-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-testcapi-run-in-subinterp-tainted-env-args.dangerous-testcapi-run-in-subinterp-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-file-permissions.insecure-file-permissions" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-session-http-in-with-context.request-session-http-in-with-context" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-session-with-http.request-session-with-http" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-with-http.request-with-http" + }, + { + "patternId": "Semgrep_python.lang.security.audit.logging.logger-credential-leak.python-logger-credential-disclosure" + }, + { + "patternId": "Semgrep_python.lang.security.audit.md5-used-as-password.md5-used-as-password" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.bind.avoid-bind-to-all-interfaces" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.disabled-cert-validation.disabled-cert-validation" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.http-not-https-connection.http-not-https-connection" + }, + { + "patternId": "Semgrep_python.lang.security.audit.ssl-wrap-socket-is-deprecated.ssl-wrap-socket-is-deprecated" + }, + { + "patternId": "Semgrep_python.lang.security.audit.subprocess-shell-true.subprocess-shell-true" + }, + { + "patternId": "Semgrep_python.lang.security.audit.weak-ssl-version.weak-ssl-version" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-code-run.dangerous-interactive-code-run" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-os-exec.dangerous-os-exec" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-spawn-process.dangerous-spawn-process" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-subinterpreters-run-string.dangerous-subinterpreters-run-string" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-subprocess-use.dangerous-subprocess-use" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-system-call.dangerous-system-call" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-testcapi-run-in-subinterp.dangerous-testcapi-run-in-subinterp" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.avoid-pyyaml-load.avoid-pyyaml-load" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.avoid-unsafe-ruamel.avoid-unsafe-ruamel" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.pickle.avoid-shelve" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-algorithms.insecure-hash-algorithm-sha1" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-algorithms-md5.insecure-hash-algorithm-md5" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-function.insecure-hash-function" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-uuid-version.insecure-uuid-version" + }, + { + "patternId": "Semgrep_python.lang.security.unverified-ssl-context.unverified-ssl-context" + }, + { + "patternId": "Semgrep_python.lang.security.use-defused-xml-parse.use-defused-xml-parse" + }, + { + "patternId": "Semgrep_python_pyramid_rule-pyramid-csrf-origin-check" + }, + { + "patternId": "Semgrep_rust.lang.security.args.args" + }, + { + "patternId": "Semgrep_rust.lang.security.args-os.args-os" + }, + { + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe" + }, + { + "patternId": "Semgrep_rust.lang.security.insecure-hashes.insecure-hashes" + }, + { + "patternId": "Semgrep_rust.lang.security.reqwest-accept-invalid.reqwest-accept-invalid" + }, + { + "patternId": "Semgrep_rust.lang.security.reqwest-set-sensitive.reqwest-set-sensitive" + }, + { + "patternId": "Semgrep_rust.lang.security.rustls-dangerous.rustls-dangerous" + }, + { + "patternId": "Semgrep_rust.lang.security.ssl-verify-none.ssl-verify-none" + }, + { + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir" + }, + { + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage" + }, + { + "patternId": "Semgrep_yaml.argo.security.argo-workflow-parameter-command-injection.argo-workflow-parameter-command-injection" + }, + { + "patternId": "Semgrep_yaml.docker-compose.security.privileged-service.privileged-service" + }, + { + "patternId": "Semgrep_yaml.openapi.security.openai-consequential-action-false.openai-consequential-action-false" + }, + { + "patternId": "Semgrep_yaml.openapi.security.use-of-basic-authentication.use-of-basic-authentication" + }, + { + "patternId": "Semgrep_yaml_spring_rule-SpringActuatorFullyEnabled" + } + ] + }, + { + "toolId": "spectral", + "patterns": [ + { + "patternId": "spectral_array-items" + }, + { + "patternId": "spectral_asyncapi-3-channel-no-empty-parameter" + }, + { + "patternId": "spectral_asyncapi-3-channel-no-query-nor-fragment" + }, + { + "patternId": "spectral_asyncapi-3-channel-no-trailing-slash" + }, + { + "patternId": "spectral_asyncapi-3-channel-servers" + }, + { + "patternId": "spectral_asyncapi-3-document-resolved" + }, + { + "patternId": "spectral_asyncapi-3-document-unresolved" + }, + { + "patternId": "spectral_asyncapi-3-headers-schema-type-object" + }, + { + "patternId": "spectral_asyncapi-3-operation-description" + }, + { + "patternId": "spectral_asyncapi-3-operation-security" + }, + { + "patternId": "spectral_asyncapi-3-payload-unsupported-schemaFormat" + }, + { + "patternId": "spectral_asyncapi-3-server-no-empty-variable" + }, + { + "patternId": "spectral_asyncapi-3-server-no-trailing-slash" + }, + { + "patternId": "spectral_asyncapi-3-tags" + }, + { + "patternId": "spectral_asyncapi-3-tags-uniqueness" + }, + { + "patternId": "spectral_asyncapi-channel-no-empty-parameter" + }, + { + "patternId": "spectral_asyncapi-channel-no-query-nor-fragment" + }, + { + "patternId": "spectral_asyncapi-channel-no-trailing-slash" + }, + { + "patternId": "spectral_asyncapi-channel-parameters" + }, + { + "patternId": "spectral_asyncapi-channel-servers" + }, + { + "patternId": "spectral_asyncapi-headers-schema-type-object" + }, + { + "patternId": "spectral_asyncapi-info-contact" + }, + { + "patternId": "spectral_asyncapi-info-contact-properties" + }, + { + "patternId": "spectral_asyncapi-info-description" + }, + { + "patternId": "spectral_asyncapi-info-license" + }, + { + "patternId": "spectral_asyncapi-latest-version" + }, + { + "patternId": "spectral_asyncapi-message-examples" + }, + { + "patternId": "spectral_asyncapi-message-messageId-uniqueness" + }, + { + "patternId": "spectral_asyncapi-operation-description" + }, + { + "patternId": "spectral_asyncapi-operation-operationId" + }, + { + "patternId": "spectral_asyncapi-operation-operationId-uniqueness" + }, + { + "patternId": "spectral_asyncapi-operation-security" + }, + { + "patternId": "spectral_asyncapi-payload" + }, + { + "patternId": "spectral_asyncapi-payload-default" + }, + { + "patternId": "spectral_asyncapi-payload-examples" + }, + { + "patternId": "spectral_asyncapi-payload-unsupported-schemaFormat" + }, + { + "patternId": "spectral_asyncapi-schema" + }, + { + "patternId": "spectral_asyncapi-schema-default" + }, + { + "patternId": "spectral_asyncapi-schema-examples" + }, + { + "patternId": "spectral_asyncapi-server-no-empty-variable" + }, + { + "patternId": "spectral_asyncapi-server-no-trailing-slash" + }, + { + "patternId": "spectral_asyncapi-servers" + }, + { + "patternId": "spectral_asyncapi-server-security" + }, + { + "patternId": "spectral_asyncapi-server-variables" + }, + { + "patternId": "spectral_asyncapi-tags" + }, + { + "patternId": "spectral_asyncapi-tags-uniqueness" + }, + { + "patternId": "spectral_asyncapi-unused-components-schema" + }, + { + "patternId": "spectral_asyncapi-unused-components-server" + }, + { + "patternId": "spectral_duplicated-entry-in-enum" + }, + { + "patternId": "spectral_info-contact" + }, + { + "patternId": "spectral_info-description" + }, + { + "patternId": "spectral_no-eval-in-markdown" + }, + { + "patternId": "spectral_no-$ref-siblings" + }, + { + "patternId": "spectral_no-script-tags-in-markdown" + }, + { + "patternId": "spectral_oas2-anyOf" + }, + { + "patternId": "spectral_oas2-api-host" + }, + { + "patternId": "spectral_oas2-api-schemes" + }, + { + "patternId": "spectral_oas2-discriminator" + }, + { + "patternId": "spectral_oas2-host-trailing-slash" + }, + { + "patternId": "spectral_oas2-oneOf" + }, + { + "patternId": "spectral_oas2-operation-formData-consume-check" + }, + { + "patternId": "spectral_oas2-operation-security-defined" + }, + { + "patternId": "spectral_oas2-schema" + }, + { + "patternId": "spectral_oas2-unused-definition" + }, + { + "patternId": "spectral_oas2-valid-media-example" + }, + { + "patternId": "spectral_oas2-valid-schema-example" + }, + { + "patternId": "spectral_oas3_1-callbacks-in-webhook" + }, + { + "patternId": "spectral_oas3_1-servers-in-webhook" + }, + { + "patternId": "spectral_oas3-api-servers" + }, + { + "patternId": "spectral_oas3-callbacks-in-callbacks" + }, + { + "patternId": "spectral_oas3-examples-value-or-externalValue" + }, + { + "patternId": "spectral_oas3-operation-security-defined" + }, + { + "patternId": "spectral_oas3-schema" + }, + { + "patternId": "spectral_oas3-server-trailing-slash" + }, + { + "patternId": "spectral_oas3-server-variables" + }, + { + "patternId": "spectral_oas3-unused-component" + }, + { + "patternId": "spectral_oas3-valid-media-example" + }, + { + "patternId": "spectral_oas3-valid-schema-example" + }, + { + "patternId": "spectral_openapi-tags-uniqueness" + }, + { + "patternId": "spectral_operation-description" + }, + { + "patternId": "spectral_operation-operationId" + }, + { + "patternId": "spectral_operation-operationId-unique" + }, + { + "patternId": "spectral_operation-operationId-valid-in-url" + }, + { + "patternId": "spectral_operation-parameters" + }, + { + "patternId": "spectral_operation-success-response" + }, + { + "patternId": "spectral_operation-tag-defined" + }, + { + "patternId": "spectral_operation-tags" + }, + { + "patternId": "spectral_path-declarations-must-exist" + }, + { + "patternId": "spectral_path-keys-no-trailing-slash" + }, + { + "patternId": "spectral_path-not-include-query" + }, + { + "patternId": "spectral_path-params" + }, + { + "patternId": "spectral_typed-enum" + } + ] + }, + { + "toolId": "Bandit", + "patterns": [ + { + "patternId": "Bandit_B101" + }, + { + "patternId": "Bandit_B102" + }, + { + "patternId": "Bandit_B103" + }, + { + "patternId": "Bandit_B104" + }, + { + "patternId": "Bandit_B105" + }, + { + "patternId": "Bandit_B106" + }, + { + "patternId": "Bandit_B107" + }, + { + "patternId": "Bandit_B108" + }, + { + "patternId": "Bandit_B110" + }, + { + "patternId": "Bandit_B112" + }, + { + "patternId": "Bandit_B202" + }, + { + "patternId": "Bandit_B301" + }, + { + "patternId": "Bandit_B302" + }, + { + "patternId": "Bandit_B303" + }, + { + "patternId": "Bandit_B304" + }, + { + "patternId": "Bandit_B305" + }, + { + "patternId": "Bandit_B306" + }, + { + "patternId": "Bandit_B307" + }, + { + "patternId": "Bandit_B309" + }, + { + "patternId": "Bandit_B310" + }, + { + "patternId": "Bandit_B311" + }, + { + "patternId": "Bandit_B312" + }, + { + "patternId": "Bandit_B313" + }, + { + "patternId": "Bandit_B314" + }, + { + "patternId": "Bandit_B315" + }, + { + "patternId": "Bandit_B316" + }, + { + "patternId": "Bandit_B317" + }, + { + "patternId": "Bandit_B318" + }, + { + "patternId": "Bandit_B319" + }, + { + "patternId": "Bandit_B321" + }, + { + "patternId": "Bandit_B322" + }, + { + "patternId": "Bandit_B323" + }, + { + "patternId": "Bandit_B324" + }, + { + "patternId": "Bandit_B325" + }, + { + "patternId": "Bandit_B401" + }, + { + "patternId": "Bandit_B402" + }, + { + "patternId": "Bandit_B403" + }, + { + "patternId": "Bandit_B404" + }, + { + "patternId": "Bandit_B405" + }, + { + "patternId": "Bandit_B406" + }, + { + "patternId": "Bandit_B407" + }, + { + "patternId": "Bandit_B408" + }, + { + "patternId": "Bandit_B409" + }, + { + "patternId": "Bandit_B411" + }, + { + "patternId": "Bandit_B412" + }, + { + "patternId": "Bandit_B415" + }, + { + "patternId": "Bandit_B502" + }, + { + "patternId": "Bandit_B503" + }, + { + "patternId": "Bandit_B504" + }, + { + "patternId": "Bandit_B505" + }, + { + "patternId": "Bandit_B602" + }, + { + "patternId": "Bandit_B603" + }, + { + "patternId": "Bandit_B604" + }, + { + "patternId": "Bandit_B605" + }, + { + "patternId": "Bandit_B606" + }, + { + "patternId": "Bandit_B607" + }, + { + "patternId": "Bandit_B608" + }, + { + "patternId": "Bandit_B609" + }, + { + "patternId": "Bandit_B612" + }, + { + "patternId": "Bandit_B613" + }, + { + "patternId": "Bandit_B614" + }, + { + "patternId": "Bandit_B615" + }, + { + "patternId": "Bandit_B704" + } + ] + }, + { + "toolId": "PyLintPython3", + "patterns": [ + { + "patternId": "PyLintPython3_C0123" + }, + { + "patternId": "PyLintPython3_C0200" + }, + { + "patternId": "PyLintPython3_E0100" + }, + { + "patternId": "PyLintPython3_E0101" + }, + { + "patternId": "PyLintPython3_E0102" + }, + { + "patternId": "PyLintPython3_E0103" + }, + { + "patternId": "PyLintPython3_E0104" + }, + { + "patternId": "PyLintPython3_E0105" + }, + { + "patternId": "PyLintPython3_E0106" + }, + { + "patternId": "PyLintPython3_E0107" + }, + { + "patternId": "PyLintPython3_E0108" + }, + { + "patternId": "PyLintPython3_E0110" + }, + { + "patternId": "PyLintPython3_E0112" + }, + { + "patternId": "PyLintPython3_E0113" + }, + { + "patternId": "PyLintPython3_E0114" + }, + { + "patternId": "PyLintPython3_E0115" + }, + { + "patternId": "PyLintPython3_E0117" + }, + { + "patternId": "PyLintPython3_E0202" + }, + { + "patternId": "PyLintPython3_E0203" + }, + { + "patternId": "PyLintPython3_E0211" + }, + { + "patternId": "PyLintPython3_E0236" + }, + { + "patternId": "PyLintPython3_E0238" + }, + { + "patternId": "PyLintPython3_E0239" + }, + { + "patternId": "PyLintPython3_E0240" + }, + { + "patternId": "PyLintPython3_E0241" + }, + { + "patternId": "PyLintPython3_E0301" + }, + { + "patternId": "PyLintPython3_E0302" + }, + { + "patternId": "PyLintPython3_E0601" + }, + { + "patternId": "PyLintPython3_E0603" + }, + { + "patternId": "PyLintPython3_E0604" + }, + { + "patternId": "PyLintPython3_E0701" + }, + { + "patternId": "PyLintPython3_E0702" + }, + { + "patternId": "PyLintPython3_E0704" + }, + { + "patternId": "PyLintPython3_E0710" + }, + { + "patternId": "PyLintPython3_E0711" + }, + { + "patternId": "PyLintPython3_E0712" + }, + { + "patternId": "PyLintPython3_E1003" + }, + { + "patternId": "PyLintPython3_E1102" + }, + { + "patternId": "PyLintPython3_E1111" + }, + { + "patternId": "PyLintPython3_E1120" + }, + { + "patternId": "PyLintPython3_E1121" + }, + { + "patternId": "PyLintPython3_E1123" + }, + { + "patternId": "PyLintPython3_E1124" + }, + { + "patternId": "PyLintPython3_E1125" + }, + { + "patternId": "PyLintPython3_E1126" + }, + { + "patternId": "PyLintPython3_E1127" + }, + { + "patternId": "PyLintPython3_E1132" + }, + { + "patternId": "PyLintPython3_E1200" + }, + { + "patternId": "PyLintPython3_E1201" + }, + { + "patternId": "PyLintPython3_E1205" + }, + { + "patternId": "PyLintPython3_E1206" + }, + { + "patternId": "PyLintPython3_E1300" + }, + { + "patternId": "PyLintPython3_E1301" + }, + { + "patternId": "PyLintPython3_E1302" + }, + { + "patternId": "PyLintPython3_E1303" + }, + { + "patternId": "PyLintPython3_E1304" + }, + { + "patternId": "PyLintPython3_E1305" + }, + { + "patternId": "PyLintPython3_E1306" + }, + { + "patternId": "PyLintPython3_R0202" + }, + { + "patternId": "PyLintPython3_R0203" + }, + { + "patternId": "PyLintPython3_W0101" + }, + { + "patternId": "PyLintPython3_W0102" + }, + { + "patternId": "PyLintPython3_W0104" + }, + { + "patternId": "PyLintPython3_W0105" + }, + { + "patternId": "PyLintPython3_W0106" + }, + { + "patternId": "PyLintPython3_W0107" + }, + { + "patternId": "PyLintPython3_W0108" + }, + { + "patternId": "PyLintPython3_W0109" + }, + { + "patternId": "PyLintPython3_W0120" + }, + { + "patternId": "PyLintPython3_W0122" + }, + { + "patternId": "PyLintPython3_W0124" + }, + { + "patternId": "PyLintPython3_W0150" + }, + { + "patternId": "PyLintPython3_W0199" + }, + { + "patternId": "PyLintPython3_W0221" + }, + { + "patternId": "PyLintPython3_W0222" + }, + { + "patternId": "PyLintPython3_W0233" + }, + { + "patternId": "PyLintPython3_W0404" + }, + { + "patternId": "PyLintPython3_W0410" + }, + { + "patternId": "PyLintPython3_W0601" + }, + { + "patternId": "PyLintPython3_W0602" + }, + { + "patternId": "PyLintPython3_W0604" + }, + { + "patternId": "PyLintPython3_W0611" + }, + { + "patternId": "PyLintPython3_W0612" + }, + { + "patternId": "PyLintPython3_W0622" + }, + { + "patternId": "PyLintPython3_W0702" + }, + { + "patternId": "PyLintPython3_W0705" + }, + { + "patternId": "PyLintPython3_W0711" + }, + { + "patternId": "PyLintPython3_W1300" + }, + { + "patternId": "PyLintPython3_W1301" + }, + { + "patternId": "PyLintPython3_W1302" + }, + { + "patternId": "PyLintPython3_W1303" + }, + { + "patternId": "PyLintPython3_W1305" + }, + { + "patternId": "PyLintPython3_W1306" + }, + { + "patternId": "PyLintPython3_W1307" + } + ] + }, + { + "toolId": "Checkov", + "patterns": [ + { + "patternId": "Checkov_CKV2_DOCKER_1" + }, + { + "patternId": "Checkov_CKV2_DOCKER_10" + }, + { + "patternId": "Checkov_CKV2_DOCKER_11" + }, + { + "patternId": "Checkov_CKV2_DOCKER_12" + }, + { + "patternId": "Checkov_CKV2_DOCKER_13" + }, + { + "patternId": "Checkov_CKV2_DOCKER_14" + }, + { + "patternId": "Checkov_CKV2_DOCKER_15" + }, + { + "patternId": "Checkov_CKV2_DOCKER_16" + }, + { + "patternId": "Checkov_CKV2_DOCKER_17" + }, + { + "patternId": "Checkov_CKV2_DOCKER_2" + }, + { + "patternId": "Checkov_CKV2_DOCKER_3" + }, + { + "patternId": "Checkov_CKV2_DOCKER_4" + }, + { + "patternId": "Checkov_CKV2_DOCKER_5" + }, + { + "patternId": "Checkov_CKV2_DOCKER_6" + }, + { + "patternId": "Checkov_CKV2_DOCKER_7" + }, + { + "patternId": "Checkov_CKV2_DOCKER_8" + }, + { + "patternId": "Checkov_CKV2_DOCKER_9" + }, + { + "patternId": "Checkov_CKV_BITBUCKET_1" + }, + { + "patternId": "Checkov_CKV_DOCKER_1" + }, + { + "patternId": "Checkov_CKV_DOCKER_10" + }, + { + "patternId": "Checkov_CKV_DOCKER_11" + }, + { + "patternId": "Checkov_CKV_DOCKER_2" + }, + { + "patternId": "Checkov_CKV_DOCKER_3" + }, + { + "patternId": "Checkov_CKV_DOCKER_4" + }, + { + "patternId": "Checkov_CKV_DOCKER_5" + }, + { + "patternId": "Checkov_CKV_DOCKER_6" + }, + { + "patternId": "Checkov_CKV_DOCKER_7" + }, + { + "patternId": "Checkov_CKV_DOCKER_8" + }, + { + "patternId": "Checkov_CKV_DOCKER_9" + }, + { + "patternId": "Checkov_CKV_GITHUB_1" + }, + { + "patternId": "Checkov_CKV_GITHUB_10" + }, + { + "patternId": "Checkov_CKV_GITHUB_11" + }, + { + "patternId": "Checkov_CKV_GITHUB_12" + }, + { + "patternId": "Checkov_CKV_GITHUB_13" + }, + { + "patternId": "Checkov_CKV_GITHUB_14" + }, + { + "patternId": "Checkov_CKV_GITHUB_15" + }, + { + "patternId": "Checkov_CKV_GITHUB_16" + }, + { + "patternId": "Checkov_CKV_GITHUB_17" + }, + { + "patternId": "Checkov_CKV_GITHUB_18" + }, + { + "patternId": "Checkov_CKV_GITHUB_19" + }, + { + "patternId": "Checkov_CKV_GITHUB_2" + }, + { + "patternId": "Checkov_CKV_GITHUB_20" + }, + { + "patternId": "Checkov_CKV_GITHUB_21" + }, + { + "patternId": "Checkov_CKV_GITHUB_22" + }, + { + "patternId": "Checkov_CKV_GITHUB_23" + }, + { + "patternId": "Checkov_CKV_GITHUB_26" + }, + { + "patternId": "Checkov_CKV_GITHUB_27" + }, + { + "patternId": "Checkov_CKV_GITHUB_28" + }, + { + "patternId": "Checkov_CKV_GITHUB_3" + }, + { + "patternId": "Checkov_CKV_GITHUB_4" + }, + { + "patternId": "Checkov_CKV_GITHUB_5" + }, + { + "patternId": "Checkov_CKV_GITHUB_6" + }, + { + "patternId": "Checkov_CKV_GITHUB_7" + }, + { + "patternId": "Checkov_CKV_GITHUB_8" + }, + { + "patternId": "Checkov_CKV_GITHUB_9" + }, + { + "patternId": "Checkov_CKV_GITLAB_1" + }, + { + "patternId": "Checkov_CKV_OPENAPI_1" + }, + { + "patternId": "Checkov_CKV_OPENAPI_10" + }, + { + "patternId": "Checkov_CKV_OPENAPI_11" + }, + { + "patternId": "Checkov_CKV_OPENAPI_12" + }, + { + "patternId": "Checkov_CKV_OPENAPI_13" + }, + { + "patternId": "Checkov_CKV_OPENAPI_14" + }, + { + "patternId": "Checkov_CKV_OPENAPI_15" + }, + { + "patternId": "Checkov_CKV_OPENAPI_16" + }, + { + "patternId": "Checkov_CKV_OPENAPI_17" + }, + { + "patternId": "Checkov_CKV_OPENAPI_18" + }, + { + "patternId": "Checkov_CKV_OPENAPI_19" + }, + { + "patternId": "Checkov_CKV_OPENAPI_2" + }, + { + "patternId": "Checkov_CKV_OPENAPI_20" + }, + { + "patternId": "Checkov_CKV_OPENAPI_21" + }, + { + "patternId": "Checkov_CKV_OPENAPI_3" + }, + { + "patternId": "Checkov_CKV_OPENAPI_4" + }, + { + "patternId": "Checkov_CKV_OPENAPI_5" + }, + { + "patternId": "Checkov_CKV_OPENAPI_6" + }, + { + "patternId": "Checkov_CKV_OPENAPI_7" + }, + { + "patternId": "Checkov_CKV_OPENAPI_8" + }, + { + "patternId": "Checkov_CKV_OPENAPI_9" + }, + { + "patternId": "Checkov_CKV_SECRET_1" + }, + { + "patternId": "Checkov_CKV_SECRET_11" + }, + { + "patternId": "Checkov_CKV_SECRET_12" + }, + { + "patternId": "Checkov_CKV_SECRET_13" + }, + { + "patternId": "Checkov_CKV_SECRET_14" + }, + { + "patternId": "Checkov_CKV_SECRET_15" + }, + { + "patternId": "Checkov_CKV_SECRET_16" + }, + { + "patternId": "Checkov_CKV_SECRET_17" + }, + { + "patternId": "Checkov_CKV_SECRET_18" + }, + { + "patternId": "Checkov_CKV_SECRET_19" + }, + { + "patternId": "Checkov_CKV_SECRET_2" + }, + { + "patternId": "Checkov_CKV_SECRET_3" + }, + { + "patternId": "Checkov_CKV_SECRET_4" + }, + { + "patternId": "Checkov_CKV_SECRET_5" + }, + { + "patternId": "Checkov_CKV_SECRET_6" + }, + { + "patternId": "Checkov_CKV_SECRET_7" + }, + { + "patternId": "Checkov_CKV_SECRET_8" + }, + { + "patternId": "Checkov_CKV_SECRET_9" + } + ] + }, + { + "toolId": "Lizard", + "patterns": [ + { + "patternId": "Lizard_file-nloc-medium", + "parameters": { + "threshold": "1140" + } + }, + { + "patternId": "Lizard_nloc-medium", + "parameters": { + "threshold": "80" + } + }, + { + "patternId": "Lizard_parameter-count-medium" + }, + { + "patternId": "Lizard_nloc-critical", + "parameters": { + "threshold": "400" + } + }, + { + "patternId": "Lizard_ccn-critical", + "parameters": { + "threshold": "70" + } + }, + { + "patternId": "Lizard_ccn-medium" + }, + { + "patternId": "Lizard_parameter-count-critical" + }, + { + "patternId": "Lizard_file-nloc-critical", + "parameters": { + "threshold": "4650" + } + } + ] + }, + { + "toolId": "Agentlinter", + "patterns": [ + { + "patternId": "Agentlinter_blueprint_constraints-defined" + }, + { + "patternId": "Agentlinter_blueprint_coverage" + }, + { + "patternId": "Agentlinter_blueprint_identity-defined" + }, + { + "patternId": "Agentlinter_clarity_actionable-instructions" + }, + { + "patternId": "Agentlinter_clarity_action-without-context" + }, + { + "patternId": "Agentlinter_clarity_ambiguous-pronoun" + }, + { + "patternId": "Agentlinter_clarity_compound-instruction" + }, + { + "patternId": "Agentlinter_clarity_duplicate-content" + }, + { + "patternId": "Agentlinter_clarity_english-config-files" + }, + { + "patternId": "Agentlinter_clarity_escape-hatch-missing" + }, + { + "patternId": "Agentlinter_clarity_has-examples" + }, + { + "patternId": "Agentlinter_clarity_instruction-density" + }, + { + "patternId": "Agentlinter_clarity_naked-conditional" + }, + { + "patternId": "Agentlinter_clarity_no-contradictions" + }, + { + "patternId": "Agentlinter_clarity_no-vague-instructions" + }, + { + "patternId": "Agentlinter_clarity_obvious-statements" + }, + { + "patternId": "Agentlinter_clarity_priority-signal-missing" + }, + { + "patternId": "Agentlinter_clarity_sentence-complexity" + }, + { + "patternId": "Agentlinter_clarity_token-budget-range" + }, + { + "patternId": "Agentlinter_clarity_token-efficiency-score" + }, + { + "patternId": "Agentlinter_clarity_undefined-term" + }, + { + "patternId": "Agentlinter_claude-code_agent-focus" + }, + { + "patternId": "Agentlinter_claude-code_descriptive-ratio" + }, + { + "patternId": "Agentlinter_claude-code_hooks-structure" + }, + { + "patternId": "Agentlinter_claude-code_instruction-count" + }, + { + "patternId": "Agentlinter_claude-code_progressive-disclosure" + }, + { + "patternId": "Agentlinter_claude-code_relevance-trap" + }, + { + "patternId": "Agentlinter_claude-code_skills-vs-commands" + }, + { + "patternId": "Agentlinter_completeness_command-coverage" + }, + { + "patternId": "Agentlinter_completeness_freshness-file-paths" + }, + { + "patternId": "Agentlinter_completeness_has-boundaries" + }, + { + "patternId": "Agentlinter_completeness_has-error-handling" + }, + { + "patternId": "Agentlinter_completeness_has-identity" + }, + { + "patternId": "Agentlinter_completeness_has-output-format" + }, + { + "patternId": "Agentlinter_completeness_has-priorities" + }, + { + "patternId": "Agentlinter_completeness_has-tools" + }, + { + "patternId": "Agentlinter_completeness_has-user-context" + }, + { + "patternId": "Agentlinter_completeness_has-workflow" + }, + { + "patternId": "Agentlinter_completeness_session-learning-hooks" + }, + { + "patternId": "Agentlinter_completeness_verification-criteria-required" + }, + { + "patternId": "Agentlinter_consistency_circular-dependency" + }, + { + "patternId": "Agentlinter_consistency_identity-alignment" + }, + { + "patternId": "Agentlinter_consistency_language-mixing" + }, + { + "patternId": "Agentlinter_consistency_naming-convention" + }, + { + "patternId": "Agentlinter_consistency_no-duplicate-instructions" + }, + { + "patternId": "Agentlinter_consistency_outdated-cross-references" + }, + { + "patternId": "Agentlinter_consistency_permission-conflict" + }, + { + "patternId": "Agentlinter_consistency_priority-conflict" + }, + { + "patternId": "Agentlinter_consistency_referenced-files-exist" + }, + { + "patternId": "Agentlinter_consistency_stale-date" + }, + { + "patternId": "Agentlinter_consistency_stale-file-reference" + }, + { + "patternId": "Agentlinter_consistency_stale-package-reference" + }, + { + "patternId": "Agentlinter_consistency_timezone-locale-drift" + }, + { + "patternId": "Agentlinter_consistency_tone-voice-alignment" + }, + { + "patternId": "Agentlinter_memory_has-context-window-awareness" + }, + { + "patternId": "Agentlinter_memory_has-file-based-notes" + }, + { + "patternId": "Agentlinter_memory_has-handoff-protocol" + }, + { + "patternId": "Agentlinter_memory_has-learning-loop" + }, + { + "patternId": "Agentlinter_memory_has-memory-strategy" + }, + { + "patternId": "Agentlinter_memory_has-state-tracking" + }, + { + "patternId": "Agentlinter_memory_no-mental-notes" + }, + { + "patternId": "Agentlinter_remote-ready_env-vars-documented" + }, + { + "patternId": "Agentlinter_remote-ready_model-settings-specified" + }, + { + "patternId": "Agentlinter_remote-ready_workspace-path-specified" + }, + { + "patternId": "Agentlinter_runtime_auth-mode" + }, + { + "patternId": "Agentlinter_runtime_config-exists" + }, + { + "patternId": "Agentlinter_runtime_config-secrets" + }, + { + "patternId": "Agentlinter_runtime_dm-policy" + }, + { + "patternId": "Agentlinter_runtime_gateway-bind" + }, + { + "patternId": "Agentlinter_runtime_group-policy" + }, + { + "patternId": "Agentlinter_runtime_token-strength" + }, + { + "patternId": "Agentlinter_security_api-key-exposure" + }, + { + "patternId": "Agentlinter_security_env-var-references" + }, + { + "patternId": "Agentlinter_security_has-injection-defense" + }, + { + "patternId": "Agentlinter_security_has-permission-boundaries" + }, + { + "patternId": "Agentlinter_security_no-injection-defense" + }, + { + "patternId": "Agentlinter_security_no-pii-exposure" + }, + { + "patternId": "Agentlinter_security_no-secrets" + }, + { + "patternId": "Agentlinter_security_prompt-injection-vulnerability" + }, + { + "patternId": "Agentlinter_skill-safety_dangerous-commands" + }, + { + "patternId": "Agentlinter_skill-safety_data-exfiltration" + }, + { + "patternId": "Agentlinter_skill-safety_excessive-permissions" + }, + { + "patternId": "Agentlinter_skill-safety_has-metadata" + }, + { + "patternId": "Agentlinter_skill-safety_injection-vectors" + }, + { + "patternId": "Agentlinter_skill-safety_sensitive-paths" + }, + { + "patternId": "Agentlinter_skill-safety_skill-description-when-to-use" + }, + { + "patternId": "Agentlinter_skill-safety_skill-name-match-dir" + }, + { + "patternId": "Agentlinter_structure_circular-import" + }, + { + "patternId": "Agentlinter_structure_dead-import" + }, + { + "patternId": "Agentlinter_structure_file-size" + }, + { + "patternId": "Agentlinter_structure_has-file-map" + }, + { + "patternId": "Agentlinter_structure_has-main-file" + }, + { + "patternId": "Agentlinter_structure_has-sections" + }, + { + "patternId": "Agentlinter_structure_has-version-or-update-date" + }, + { + "patternId": "Agentlinter_structure_heading-hierarchy" + }, + { + "patternId": "Agentlinter_structure_modular-files" + }, + { + "patternId": "Agentlinter_structure_no-empty-sections" + }, + { + "patternId": "Agentlinter_structure_position-risk-warning" + }, + { + "patternId": "Agentlinter_token-budget_compressible-padding" + }, + { + "patternId": "Agentlinter_token-budget_section-weight" + }, + { + "patternId": "Agentlinter_token-budget_total-tokens" + }, + { + "patternId": "Agentlinter_token-budget_under-150-tokens" + } + ] + }, + { + "toolId": "Prospector", + "patterns": [ + { + "patternId": "Prospector_dodgy" + }, + { + "patternId": "Prospector_mccabe" + }, + { + "patternId": "Prospector_profile-validator" + }, + { + "patternId": "Prospector_pycodestyle" + }, + { + "patternId": "Prospector_pydocstyle" + }, + { + "patternId": "Prospector_pyflakes" + } + ] + }, + { + "toolId": "psscriptanalyzer", + "patterns": [ + { + "patternId": "psscriptanalyzer_psalignassignmentstatement" + }, + { + "patternId": "psscriptanalyzer_psavoidassignmenttoautomaticvariable" + }, + { + "patternId": "psscriptanalyzer_psavoiddefaultvalueformandatoryparameter" + }, + { + "patternId": "psscriptanalyzer_psavoiddefaultvalueswitchparameter" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalaliases" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalfunctions" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalvars" + }, + { + "patternId": "psscriptanalyzer_psavoidinvokingemptymembers" + }, + { + "patternId": "psscriptanalyzer_psavoidshouldcontinuewithoutforce" + }, + { + "patternId": "psscriptanalyzer_psavoidusingcomputernamehardcoded" + }, + { + "patternId": "psscriptanalyzer_psavoidusingconverttosecurestringwithplaintext" + }, + { + "patternId": "psscriptanalyzer_psavoidusingdeprecatedmanifestfields" + }, + { + "patternId": "psscriptanalyzer_psavoidusingemptycatchblock" + }, + { + "patternId": "psscriptanalyzer_psavoidusinginvokeexpression" + }, + { + "patternId": "psscriptanalyzer_psavoidusingplaintextforpassword" + }, + { + "patternId": "psscriptanalyzer_psavoidusingpositionalparameters" + }, + { + "patternId": "psscriptanalyzer_psavoidusingusernameandpasswordparams" + }, + { + "patternId": "psscriptanalyzer_psavoidusingwmicmdlet" + }, + { + "patternId": "psscriptanalyzer_psavoidusingwritehost" + }, + { + "patternId": "psscriptanalyzer_psdscdscexamplespresent" + }, + { + "patternId": "psscriptanalyzer_psdscdsctestspresent" + }, + { + "patternId": "psscriptanalyzer_psdscreturncorrecttypesfordscfunctions" + }, + { + "patternId": "psscriptanalyzer_psdscstandarddscfunctionsinresource" + }, + { + "patternId": "psscriptanalyzer_psdscuseidenticalmandatoryparametersfordsc" + }, + { + "patternId": "psscriptanalyzer_psdscuseidenticalparametersfordsc" + }, + { + "patternId": "psscriptanalyzer_psmisleadingbacktick" + }, + { + "patternId": "psscriptanalyzer_psmissingmodulemanifestfield" + }, + { + "patternId": "psscriptanalyzer_psplaceclosebrace" + }, + { + "patternId": "psscriptanalyzer_psplaceopenbrace" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectcomparisonwithnull" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectusageofassignmentoperator" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectusageofredirectionoperator" + }, + { + "patternId": "psscriptanalyzer_psreservedcmdletchar" + }, + { + "patternId": "psscriptanalyzer_psreservedparams" + }, + { + "patternId": "psscriptanalyzer_psshouldprocess" + }, + { + "patternId": "psscriptanalyzer_psuseapprovedverbs" + }, + { + "patternId": "psscriptanalyzer_psusebomforunicodeencodedfile" + }, + { + "patternId": "psscriptanalyzer_psusecmdletcorrectly" + }, + { + "patternId": "psscriptanalyzer_psusecompatiblecmdlets" + }, + { + "patternId": "psscriptanalyzer_psuseliteralinitializerforhashtable" + }, + { + "patternId": "psscriptanalyzer_psuseoutputtypecorrectly" + }, + { + "patternId": "psscriptanalyzer_psusepscredentialtype" + }, + { + "patternId": "psscriptanalyzer_psuseshouldprocessforstatechangingfunctions" + }, + { + "patternId": "psscriptanalyzer_psusesupportsshouldprocess" + }, + { + "patternId": "psscriptanalyzer_psusetoexportfieldsinmanifest" + } + ] + } + ], + "exclude": [] +} diff --git a/.codacy/codacy.config.json b/.codacy/codacy.config.json new file mode 100644 index 0000000..40778e0 --- /dev/null +++ b/.codacy/codacy.config.json @@ -0,0 +1,2806 @@ +{ + "version": 1, + "metadata": { + "source": "auto", + "provider": null, + "organization": null, + "autoFilters": "Critical,High,Warning,Minor,AllSecurity,ErrorProne,Performance,BestPractice,UnusedCode,Compatibility,Complexity,Comprehensibility,CodeStyle,Documentation", + "repositoryId": null, + "repositoryName": null, + "createdAt": "2026-10-28T07:09:02.913Z", + "updatedAt": "2026-10-29T15:48:08.735Z", + "languages": [ + "Dockerfile", + "JSON", + "Markdown", + "Powershell", + "Python", + "Rust", + "Shell", + "YAML" + ] + }, + "tools": [ + { + "toolId": "jackson", + "patterns": [ + { + "patternId": "jackson_duplicate-keys" + }, + { + "patternId": "jackson_parse-error" + } + ] + }, + { + "toolId": "markdownlint", + "patterns": [ + { + "patternId": "markdownlint_MD001" + }, + { + "patternId": "markdownlint_MD003" + }, + { + "patternId": "markdownlint_MD004" + }, + { + "patternId": "markdownlint_MD005" + }, + { + "patternId": "markdownlint_MD007" + }, + { + "patternId": "markdownlint_MD010" + }, + { + "patternId": "markdownlint_MD011" + }, + { + "patternId": "markdownlint_MD012" + }, + { + "patternId": "markdownlint_MD014" + }, + { + "patternId": "markdownlint_MD018" + }, + { + "patternId": "markdownlint_MD019" + }, + { + "patternId": "markdownlint_MD020" + }, + { + "patternId": "markdownlint_MD021" + }, + { + "patternId": "markdownlint_MD022" + }, + { + "patternId": "markdownlint_MD023" + }, + { + "patternId": "markdownlint_MD024" + }, + { + "patternId": "markdownlint_MD025" + }, + { + "patternId": "markdownlint_MD026" + }, + { + "patternId": "markdownlint_MD027" + }, + { + "patternId": "markdownlint_MD028" + }, + { + "patternId": "markdownlint_MD029" + }, + { + "patternId": "markdownlint_MD030" + }, + { + "patternId": "markdownlint_MD032" + }, + { + "patternId": "markdownlint_MD033" + }, + { + "patternId": "markdownlint_MD034" + }, + { + "patternId": "markdownlint_MD035" + }, + { + "patternId": "markdownlint_MD036" + }, + { + "patternId": "markdownlint_MD037" + }, + { + "patternId": "markdownlint_MD038" + }, + { + "patternId": "markdownlint_MD039" + }, + { + "patternId": "markdownlint_MD042" + }, + { + "patternId": "markdownlint_MD044" + }, + { + "patternId": "markdownlint_MD045" + }, + { + "patternId": "markdownlint_MD046" + }, + { + "patternId": "markdownlint_MD048" + }, + { + "patternId": "markdownlint_MD049" + }, + { + "patternId": "markdownlint_MD050" + }, + { + "patternId": "markdownlint_MD051" + }, + { + "patternId": "markdownlint_MD052" + }, + { + "patternId": "markdownlint_MD053" + }, + { + "patternId": "markdownlint_MD054" + }, + { + "patternId": "markdownlint_MD055" + }, + { + "patternId": "markdownlint_MD056" + } + ] + }, + { + "toolId": "shellcheck", + "patterns": [ + { + "patternId": "shellcheck_SC2001" + }, + { + "patternId": "shellcheck_SC2002" + }, + { + "patternId": "shellcheck_SC2003" + }, + { + "patternId": "shellcheck_SC2004" + }, + { + "patternId": "shellcheck_SC2006" + }, + { + "patternId": "shellcheck_SC2015" + }, + { + "patternId": "shellcheck_SC2016" + }, + { + "patternId": "shellcheck_SC2020" + }, + { + "patternId": "shellcheck_SC2022" + }, + { + "patternId": "shellcheck_SC2024" + }, + { + "patternId": "shellcheck_SC2025" + }, + { + "patternId": "shellcheck_SC2026" + }, + { + "patternId": "shellcheck_SC2027" + }, + { + "patternId": "shellcheck_SC2028" + }, + { + "patternId": "shellcheck_SC2029" + }, + { + "patternId": "shellcheck_SC2031" + }, + { + "patternId": "shellcheck_SC2033" + }, + { + "patternId": "shellcheck_SC2034" + }, + { + "patternId": "shellcheck_SC2035" + }, + { + "patternId": "shellcheck_SC2036" + }, + { + "patternId": "shellcheck_SC2086" + }, + { + "patternId": "shellcheck_SC2148" + } + ] + }, + { + "toolId": "Hadolint", + "patterns": [ + { + "patternId": "Hadolint_DL3000" + }, + { + "patternId": "Hadolint_DL3001" + }, + { + "patternId": "Hadolint_DL3002" + }, + { + "patternId": "Hadolint_DL3003" + }, + { + "patternId": "Hadolint_DL3004" + }, + { + "patternId": "Hadolint_DL3006" + }, + { + "patternId": "Hadolint_DL3007" + }, + { + "patternId": "Hadolint_DL3008" + }, + { + "patternId": "Hadolint_DL3009" + }, + { + "patternId": "Hadolint_DL3010" + }, + { + "patternId": "Hadolint_DL3011" + }, + { + "patternId": "Hadolint_DL3012" + }, + { + "patternId": "Hadolint_DL3013" + }, + { + "patternId": "Hadolint_DL3014" + }, + { + "patternId": "Hadolint_DL3015" + }, + { + "patternId": "Hadolint_DL3020" + }, + { + "patternId": "Hadolint_DL3021" + }, + { + "patternId": "Hadolint_DL3022" + }, + { + "patternId": "Hadolint_DL3023" + }, + { + "patternId": "Hadolint_DL3024" + }, + { + "patternId": "Hadolint_DL4000" + }, + { + "patternId": "Hadolint_DL4001" + }, + { + "patternId": "Hadolint_DL4003" + }, + { + "patternId": "Hadolint_DL4004" + }, + { + "patternId": "Hadolint_DL4005" + }, + { + "patternId": "Hadolint_SC1000" + }, + { + "patternId": "Hadolint_SC1001" + }, + { + "patternId": "Hadolint_SC1007" + }, + { + "patternId": "Hadolint_SC1010" + }, + { + "patternId": "Hadolint_SC1018" + }, + { + "patternId": "Hadolint_SC1035" + }, + { + "patternId": "Hadolint_SC1045" + }, + { + "patternId": "Hadolint_SC1065" + }, + { + "patternId": "Hadolint_SC1066" + }, + { + "patternId": "Hadolint_SC1068" + }, + { + "patternId": "Hadolint_SC1077" + }, + { + "patternId": "Hadolint_SC1078" + }, + { + "patternId": "Hadolint_SC1079" + }, + { + "patternId": "Hadolint_SC1081" + }, + { + "patternId": "Hadolint_SC1083" + }, + { + "patternId": "Hadolint_SC1086" + }, + { + "patternId": "Hadolint_SC1087" + }, + { + "patternId": "Hadolint_SC1095" + }, + { + "patternId": "Hadolint_SC1097" + }, + { + "patternId": "Hadolint_SC1098" + }, + { + "patternId": "Hadolint_SC1099" + }, + { + "patternId": "Hadolint_SC2002" + }, + { + "patternId": "Hadolint_SC2015" + }, + { + "patternId": "Hadolint_SC2026" + }, + { + "patternId": "Hadolint_SC2028" + }, + { + "patternId": "Hadolint_SC2035" + }, + { + "patternId": "Hadolint_SC2046" + }, + { + "patternId": "Hadolint_SC2086" + }, + { + "patternId": "Hadolint_SC2140" + }, + { + "patternId": "Hadolint_SC2154" + }, + { + "patternId": "Hadolint_SC2164" + } + ] + }, + { + "toolId": "Ruff", + "patterns": [ + { + "patternId": "Ruff_B002_unary-prefix-increment-decrement" + }, + { + "patternId": "Ruff_B003_assignment-to-os-environ" + }, + { + "patternId": "Ruff_B004_unreliable-callable-check" + }, + { + "patternId": "Ruff_B005_strip-with-multi-characters" + }, + { + "patternId": "Ruff_B006_mutable-argument-default" + }, + { + "patternId": "Ruff_B007_unused-loop-control-variable" + }, + { + "patternId": "Ruff_B008_function-call-in-default-argument" + }, + { + "patternId": "Ruff_B009_get-attr-with-constant" + }, + { + "patternId": "Ruff_B010_set-attr-with-constant" + }, + { + "patternId": "Ruff_B011_assert-false" + }, + { + "patternId": "Ruff_B012_jump-statement-in-finally" + }, + { + "patternId": "Ruff_B013_redundant-tuple-in-exception-handler" + }, + { + "patternId": "Ruff_B014_duplicate-handler-exception" + }, + { + "patternId": "Ruff_B015_useless-comparison" + }, + { + "patternId": "Ruff_B016_raise-literal" + }, + { + "patternId": "Ruff_B017_assert-raises-exception" + }, + { + "patternId": "Ruff_B018_useless-expression" + }, + { + "patternId": "Ruff_B019_cached-instance-method" + }, + { + "patternId": "Ruff_B020_loop-variable-overrides-iterator" + }, + { + "patternId": "Ruff_B021_f-string-docstring" + }, + { + "patternId": "Ruff_B022_useless-contextlib-suppress" + }, + { + "patternId": "Ruff_B023_function-uses-loop-variable" + }, + { + "patternId": "Ruff_B024_abstract-base-class-without-abstract-method" + }, + { + "patternId": "Ruff_B025_duplicate-try-block-exception" + }, + { + "patternId": "Ruff_B026_star-arg-unpacking-after-keyword-arg" + }, + { + "patternId": "Ruff_B027_empty-method-without-abstract-decorator" + }, + { + "patternId": "Ruff_B028_no-explicit-stacklevel" + }, + { + "patternId": "Ruff_B029_except-with-empty-tuple" + }, + { + "patternId": "Ruff_B030_except-with-non-exception-classes" + }, + { + "patternId": "Ruff_B031_reuse-of-groupby-generator" + }, + { + "patternId": "Ruff_B032_unintentional-type-annotation" + }, + { + "patternId": "Ruff_B033_duplicate-value" + }, + { + "patternId": "Ruff_B034_re-sub-positional-args" + }, + { + "patternId": "Ruff_B035_static-key-dict-comprehension" + }, + { + "patternId": "Ruff_B039_mutable-contextvar-default" + }, + { + "patternId": "Ruff_B901_return-in-generator" + }, + { + "patternId": "Ruff_B903_class-as-data-structure" + }, + { + "patternId": "Ruff_B904_raise-without-from-inside-except" + }, + { + "patternId": "Ruff_B905_zip-without-explicit-strict" + }, + { + "patternId": "Ruff_B909_loop-iterator-mutation" + }, + { + "patternId": "Ruff_B911_batched-without-explicit-strict" + }, + { + "patternId": "Ruff_C901_complex-structure" + }, + { + "patternId": "Ruff_E101_mixed-spaces-and-tabs" + }, + { + "patternId": "Ruff_E111_indentation-with-invalid-multiple" + }, + { + "patternId": "Ruff_E112_no-indented-block" + }, + { + "patternId": "Ruff_E113_unexpected-indentation" + }, + { + "patternId": "Ruff_E114_indentation-with-invalid-multiple-comment" + }, + { + "patternId": "Ruff_E115_no-indented-block-comment" + }, + { + "patternId": "Ruff_E116_unexpected-indentation-comment" + }, + { + "patternId": "Ruff_E117_over-indented" + }, + { + "patternId": "Ruff_E201_whitespace-after-open-bracket" + }, + { + "patternId": "Ruff_E202_whitespace-before-close-bracket" + }, + { + "patternId": "Ruff_E203_whitespace-before-punctuation" + }, + { + "patternId": "Ruff_E204_whitespace-after-decorator" + }, + { + "patternId": "Ruff_E211_whitespace-before-parameters" + }, + { + "patternId": "Ruff_E221_multiple-spaces-before-operator" + }, + { + "patternId": "Ruff_E222_multiple-spaces-after-operator" + }, + { + "patternId": "Ruff_E223_tab-before-operator" + }, + { + "patternId": "Ruff_E224_tab-after-operator" + }, + { + "patternId": "Ruff_E225_missing-whitespace-around-operator" + }, + { + "patternId": "Ruff_E226_missing-whitespace-around-arithmetic-operator" + }, + { + "patternId": "Ruff_E227_missing-whitespace-around-bitwise-or-shift-operator" + }, + { + "patternId": "Ruff_E228_missing-whitespace-around-modulo-operator" + }, + { + "patternId": "Ruff_E231_missing-whitespace" + }, + { + "patternId": "Ruff_E241_multiple-spaces-after-comma" + }, + { + "patternId": "Ruff_E242_tab-after-comma" + }, + { + "patternId": "Ruff_E251_unexpected-spaces-around-keyword-parameter-equals" + }, + { + "patternId": "Ruff_E252_missing-whitespace-around-parameter-equals" + }, + { + "patternId": "Ruff_E261_too-few-spaces-before-inline-comment" + }, + { + "patternId": "Ruff_E262_no-space-after-inline-comment" + }, + { + "patternId": "Ruff_E265_no-space-after-block-comment" + }, + { + "patternId": "Ruff_E266_multiple-leading-hashes-for-block-comment" + }, + { + "patternId": "Ruff_E271_multiple-spaces-after-keyword" + }, + { + "patternId": "Ruff_E272_multiple-spaces-before-keyword" + }, + { + "patternId": "Ruff_E273_tab-after-keyword" + }, + { + "patternId": "Ruff_E274_tab-before-keyword" + }, + { + "patternId": "Ruff_E275_missing-whitespace-after-keyword" + }, + { + "patternId": "Ruff_E301_blank-line-between-methods" + }, + { + "patternId": "Ruff_E302_blank-lines-top-level" + }, + { + "patternId": "Ruff_E303_too-many-blank-lines" + }, + { + "patternId": "Ruff_E304_blank-line-after-decorator" + }, + { + "patternId": "Ruff_E305_blank-lines-after-function-or-class" + }, + { + "patternId": "Ruff_E306_blank-lines-before-nested-definition" + }, + { + "patternId": "Ruff_E401_multiple-imports-on-one-line" + }, + { + "patternId": "Ruff_E402_module-import-not-at-top-of-file" + }, + { + "patternId": "Ruff_E501_line-too-long" + }, + { + "patternId": "Ruff_E502_redundant-backslash" + }, + { + "patternId": "Ruff_E701_multiple-statements-on-one-line-colon" + }, + { + "patternId": "Ruff_E702_multiple-statements-on-one-line-semicolon" + }, + { + "patternId": "Ruff_E703_useless-semicolon" + }, + { + "patternId": "Ruff_E711_none-comparison" + }, + { + "patternId": "Ruff_E712_true-false-comparison" + }, + { + "patternId": "Ruff_E713_not-in-test" + }, + { + "patternId": "Ruff_E714_not-is-test" + }, + { + "patternId": "Ruff_E721_type-comparison" + }, + { + "patternId": "Ruff_E722_bare-except" + }, + { + "patternId": "Ruff_E731_lambda-assignment" + }, + { + "patternId": "Ruff_E741_ambiguous-variable-name" + }, + { + "patternId": "Ruff_E742_ambiguous-class-name" + }, + { + "patternId": "Ruff_E743_ambiguous-function-name" + }, + { + "patternId": "Ruff_E902_io-error" + }, + { + "patternId": "Ruff_FA100_future-rewritable-type-annotation" + }, + { + "patternId": "Ruff_FA102_future-required-type-annotation" + }, + { + "patternId": "Ruff_S101_assert" + }, + { + "patternId": "Ruff_S102_exec-builtin" + }, + { + "patternId": "Ruff_S103_bad-file-permissions" + }, + { + "patternId": "Ruff_S104_hardcoded-bind-all-interfaces" + }, + { + "patternId": "Ruff_S105_hardcoded-password-string" + }, + { + "patternId": "Ruff_S106_hardcoded-password-func-arg" + }, + { + "patternId": "Ruff_S107_hardcoded-password-default" + }, + { + "patternId": "Ruff_S108_hardcoded-temp-file" + }, + { + "patternId": "Ruff_S110_try-except-pass" + }, + { + "patternId": "Ruff_S112_try-except-continue" + }, + { + "patternId": "Ruff_S113_request-without-timeout" + }, + { + "patternId": "Ruff_S201_flask-debug-true" + }, + { + "patternId": "Ruff_S202_tarfile-unsafe-members" + }, + { + "patternId": "Ruff_S301_suspicious-pickle-usage" + }, + { + "patternId": "Ruff_S302_suspicious-marshal-usage" + }, + { + "patternId": "Ruff_S303_suspicious-insecure-hash-usage" + }, + { + "patternId": "Ruff_S304_suspicious-insecure-cipher-usage" + }, + { + "patternId": "Ruff_S305_suspicious-insecure-cipher-mode-usage" + }, + { + "patternId": "Ruff_S306_suspicious-mktemp-usage" + }, + { + "patternId": "Ruff_S307_suspicious-eval-usage" + }, + { + "patternId": "Ruff_S308_suspicious-mark-safe-usage" + }, + { + "patternId": "Ruff_S310_suspicious-url-open-usage" + }, + { + "patternId": "Ruff_S311_suspicious-non-cryptographic-random-usage" + }, + { + "patternId": "Ruff_S312_suspicious-telnet-usage" + }, + { + "patternId": "Ruff_S313_suspicious-xmlc-element-tree-usage" + }, + { + "patternId": "Ruff_S314_suspicious-xml-element-tree-usage" + }, + { + "patternId": "Ruff_S315_suspicious-xml-expat-reader-usage" + }, + { + "patternId": "Ruff_S316_suspicious-xml-expat-builder-usage" + }, + { + "patternId": "Ruff_S317_suspicious-xml-sax-usage" + }, + { + "patternId": "Ruff_S318_suspicious-xml-mini-dom-usage" + }, + { + "patternId": "Ruff_S319_suspicious-xml-pull-dom-usage" + }, + { + "patternId": "Ruff_S321_suspicious-ftp-lib-usage" + }, + { + "patternId": "Ruff_S323_suspicious-unverified-context-usage" + }, + { + "patternId": "Ruff_S324_hashlib-insecure-hash-function" + }, + { + "patternId": "Ruff_S401_suspicious-telnetlib-import" + }, + { + "patternId": "Ruff_S402_suspicious-ftplib-import" + }, + { + "patternId": "Ruff_S403_suspicious-pickle-import" + }, + { + "patternId": "Ruff_S404_suspicious-subprocess-import" + }, + { + "patternId": "Ruff_S405_suspicious-xml-etree-import" + }, + { + "patternId": "Ruff_S406_suspicious-xml-sax-import" + }, + { + "patternId": "Ruff_S407_suspicious-xml-expat-import" + }, + { + "patternId": "Ruff_S408_suspicious-xml-minidom-import" + }, + { + "patternId": "Ruff_S409_suspicious-xml-pulldom-import" + }, + { + "patternId": "Ruff_S411_suspicious-xmlrpc-import" + }, + { + "patternId": "Ruff_S412_suspicious-httpoxy-import" + }, + { + "patternId": "Ruff_S413_suspicious-pycrypto-import" + }, + { + "patternId": "Ruff_S415_suspicious-pyghmi-import" + }, + { + "patternId": "Ruff_S501_request-with-no-cert-validation" + }, + { + "patternId": "Ruff_S502_ssl-insecure-version" + }, + { + "patternId": "Ruff_S503_ssl-with-bad-defaults" + }, + { + "patternId": "Ruff_S504_ssl-with-no-version" + }, + { + "patternId": "Ruff_S505_weak-cryptographic-key" + }, + { + "patternId": "Ruff_S506_unsafe-yaml-load" + }, + { + "patternId": "Ruff_S507_ssh-no-host-key-verification" + }, + { + "patternId": "Ruff_S508_snmp-insecure-version" + }, + { + "patternId": "Ruff_S509_snmp-weak-cryptography" + }, + { + "patternId": "Ruff_S601_paramiko-call" + }, + { + "patternId": "Ruff_S602_subprocess-popen-with-shell-equals-true" + }, + { + "patternId": "Ruff_S603_subprocess-without-shell-equals-true" + }, + { + "patternId": "Ruff_S604_call-with-shell-equals-true" + }, + { + "patternId": "Ruff_S605_start-process-with-a-shell" + }, + { + "patternId": "Ruff_S606_start-process-with-no-shell" + }, + { + "patternId": "Ruff_S607_start-process-with-partial-path" + }, + { + "patternId": "Ruff_S608_hardcoded-sql-expression" + }, + { + "patternId": "Ruff_S609_unix-command-wildcard-injection" + }, + { + "patternId": "Ruff_S610_django-extra" + }, + { + "patternId": "Ruff_S611_django-raw-sql" + }, + { + "patternId": "Ruff_S612_logging-config-insecure-listen" + }, + { + "patternId": "Ruff_S701_jinja2-autoescape-false" + }, + { + "patternId": "Ruff_S702_mako-templates" + }, + { + "patternId": "Ruff_W191_tab-indentation" + }, + { + "patternId": "Ruff_W292_missing-newline-at-end-of-file" + }, + { + "patternId": "Ruff_W293_blank-line-with-whitespace" + }, + { + "patternId": "Ruff_W391_too-many-newlines-at-end-of-file" + }, + { + "patternId": "Ruff_W505_doc-line-too-long" + }, + { + "patternId": "Ruff_W605_invalid-escape-sequence" + } + ] + }, + { + "toolId": "Trivy", + "patterns": [ + { + "patternId": "Trivy_malicious_packages" + }, + { + "patternId": "Trivy_secret" + }, + { + "patternId": "Trivy_vulnerability_critical" + }, + { + "patternId": "Trivy_vulnerability_high" + }, + { + "patternId": "Trivy_vulnerability_medium" + }, + { + "patternId": "Trivy_vulnerability_minor" + } + ] + }, + { + "toolId": "Semgrep", + "patterns": [ + { + "patternId": "Semgrep_bash.curl.security.curl-eval.curl-eval" + }, + { + "patternId": "Semgrep_dockerfile.security.dockerd-socket-mount.dockerfile-dockerd-socket-mount" + }, + { + "patternId": "Semgrep_dockerfile.security.last-user-is-root.last-user-is-root" + }, + { + "patternId": "Semgrep_dockerfile.security.missing-user-entrypoint.missing-user-entrypoint" + }, + { + "patternId": "Semgrep_dockerfile.security.missing-user.missing-user" + }, + { + "patternId": "Semgrep_dockerfile.security.no-sudo-in-dockerfile.no-sudo-in-dockerfile" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-onfido-live-api-token.detected-onfido-live-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-stripe-restricted-api-key.detected-stripe-restricted-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-username-and-password-in-uri.detected-username-and-password-in-uri" + }, + { + "patternId": "Semgrep_generic.secrets.security.google-maps-apikeyleak.google-maps-apikeyleak" + }, + { + "patternId": "Semgrep_json.aws.security.public-s3-bucket.public-s3-bucket" + }, + { + "patternId": "Semgrep_json.aws.security.public-s3-policy-statement.public-s3-policy-statement" + }, + { + "patternId": "Semgrep_json.aws.security.wildcard-assume-role.wildcard-assume-role" + }, + { + "patternId": "Semgrep_python.cryptography.security.empty-aes-key.empty-aes-key" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms-arc4.insecure-cipher-algorithm-arc4" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms-blowfish.insecure-cipher-algorithm-blowfish" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms.insecure-cipher-algorithm-idea" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-mode-ecb.insecure-cipher-mode-ecb" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-hash-algorithms.insecure-hash-algorithm-sha1" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-hash-algorithms-md5.insecure-hash-algorithm-md5" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-dsa-key-size.insufficient-dsa-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-ec-key-size.insufficient-ec-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-rsa-key-size.insufficient-rsa-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.mode-without-authentication.crypto-mode-without-authentication" + }, + { + "patternId": "Semgrep_python_crypto_rule-HTTPConnectionPool" + }, + { + "patternId": "Semgrep_python.distributed.security.require-encryption" + }, + { + "patternId": "Semgrep_python_flask_rule-path-traversal-open" + }, + { + "patternId": "Semgrep_python_jwt_rule-jwt-none-alg" + }, + { + "patternId": "Semgrep_python.jwt.security.jwt-hardcode.jwt-python-hardcoded-secret" + }, + { + "patternId": "Semgrep_python.jwt.security.jwt-none-alg.jwt-python-none-alg" + }, + { + "patternId": "Semgrep_python.jwt.security.unverified-jwt-decode.unverified-jwt-decode" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-exec-tainted-env-args.dangerous-asyncio-exec-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-shell-tainted-env-args.dangerous-asyncio-shell-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-code-run-tainted-env-args.dangerous-interactive-code-run-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-os-exec-tainted-env-args.dangerous-os-exec-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-spawn-process-tainted-env-args.dangerous-spawn-process-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-subinterpreters-run-string-tainted-env-args.dangerous-subinterpreters-run-string-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-subprocess-use-tainted-env-args.dangerous-subprocess-use-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-system-call-tainted-env-args.dangerous-system-call-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-testcapi-run-in-subinterp-tainted-env-args.dangerous-testcapi-run-in-subinterp-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-file-permissions.insecure-file-permissions" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-session-http-in-with-context.request-session-http-in-with-context" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-session-with-http.request-session-with-http" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-with-http.request-with-http" + }, + { + "patternId": "Semgrep_python.lang.security.audit.logging.logger-credential-leak.python-logger-credential-disclosure" + }, + { + "patternId": "Semgrep_python.lang.security.audit.md5-used-as-password.md5-used-as-password" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.bind.avoid-bind-to-all-interfaces" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.disabled-cert-validation.disabled-cert-validation" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.http-not-https-connection.http-not-https-connection" + }, + { + "patternId": "Semgrep_python.lang.security.audit.ssl-wrap-socket-is-deprecated.ssl-wrap-socket-is-deprecated" + }, + { + "patternId": "Semgrep_python.lang.security.audit.subprocess-shell-true.subprocess-shell-true" + }, + { + "patternId": "Semgrep_python.lang.security.audit.weak-ssl-version.weak-ssl-version" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-code-run.dangerous-interactive-code-run" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-os-exec.dangerous-os-exec" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-spawn-process.dangerous-spawn-process" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-subinterpreters-run-string.dangerous-subinterpreters-run-string" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-subprocess-use.dangerous-subprocess-use" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-system-call.dangerous-system-call" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-testcapi-run-in-subinterp.dangerous-testcapi-run-in-subinterp" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.avoid-pyyaml-load.avoid-pyyaml-load" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.avoid-unsafe-ruamel.avoid-unsafe-ruamel" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.pickle.avoid-shelve" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-algorithms.insecure-hash-algorithm-sha1" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-algorithms-md5.insecure-hash-algorithm-md5" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-function.insecure-hash-function" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-uuid-version.insecure-uuid-version" + }, + { + "patternId": "Semgrep_python.lang.security.unverified-ssl-context.unverified-ssl-context" + }, + { + "patternId": "Semgrep_python.lang.security.use-defused-xml-parse.use-defused-xml-parse" + }, + { + "patternId": "Semgrep_python_pyramid_rule-pyramid-csrf-origin-check" + }, + { + "patternId": "Semgrep_rust.lang.security.args.args" + }, + { + "patternId": "Semgrep_rust.lang.security.args-os.args-os" + }, + { + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe" + }, + { + "patternId": "Semgrep_rust.lang.security.insecure-hashes.insecure-hashes" + }, + { + "patternId": "Semgrep_rust.lang.security.reqwest-accept-invalid.reqwest-accept-invalid" + }, + { + "patternId": "Semgrep_rust.lang.security.reqwest-set-sensitive.reqwest-set-sensitive" + }, + { + "patternId": "Semgrep_rust.lang.security.rustls-dangerous.rustls-dangerous" + }, + { + "patternId": "Semgrep_rust.lang.security.ssl-verify-none.ssl-verify-none" + }, + { + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir" + }, + { + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage" + }, + { + "patternId": "Semgrep_yaml.argo.security.argo-workflow-parameter-command-injection.argo-workflow-parameter-command-injection" + }, + { + "patternId": "Semgrep_yaml.docker-compose.security.privileged-service.privileged-service" + }, + { + "patternId": "Semgrep_yaml.openapi.security.openai-consequential-action-false.openai-consequential-action-false" + }, + { + "patternId": "Semgrep_yaml.openapi.security.use-of-basic-authentication.use-of-basic-authentication" + }, + { + "patternId": "Semgrep_yaml_spring_rule-SpringActuatorFullyEnabled" + } + ] + }, + { + "toolId": "spectral", + "patterns": [ + { + "patternId": "spectral_array-items" + }, + { + "patternId": "spectral_asyncapi-3-channel-no-empty-parameter" + }, + { + "patternId": "spectral_asyncapi-3-channel-no-query-nor-fragment" + }, + { + "patternId": "spectral_asyncapi-3-channel-no-trailing-slash" + }, + { + "patternId": "spectral_asyncapi-3-channel-servers" + }, + { + "patternId": "spectral_asyncapi-3-document-resolved" + }, + { + "patternId": "spectral_asyncapi-3-document-unresolved" + }, + { + "patternId": "spectral_asyncapi-3-headers-schema-type-object" + }, + { + "patternId": "spectral_asyncapi-3-operation-description" + }, + { + "patternId": "spectral_asyncapi-3-operation-security" + }, + { + "patternId": "spectral_asyncapi-3-payload-unsupported-schemaFormat" + }, + { + "patternId": "spectral_asyncapi-3-server-no-empty-variable" + }, + { + "patternId": "spectral_asyncapi-3-server-no-trailing-slash" + }, + { + "patternId": "spectral_asyncapi-3-tags" + }, + { + "patternId": "spectral_asyncapi-3-tags-uniqueness" + }, + { + "patternId": "spectral_asyncapi-channel-no-empty-parameter" + }, + { + "patternId": "spectral_asyncapi-channel-no-query-nor-fragment" + }, + { + "patternId": "spectral_asyncapi-channel-no-trailing-slash" + }, + { + "patternId": "spectral_asyncapi-channel-parameters" + }, + { + "patternId": "spectral_asyncapi-channel-servers" + }, + { + "patternId": "spectral_asyncapi-headers-schema-type-object" + }, + { + "patternId": "spectral_asyncapi-info-contact" + }, + { + "patternId": "spectral_asyncapi-info-contact-properties" + }, + { + "patternId": "spectral_asyncapi-info-description" + }, + { + "patternId": "spectral_asyncapi-info-license" + }, + { + "patternId": "spectral_asyncapi-latest-version" + }, + { + "patternId": "spectral_asyncapi-message-examples" + }, + { + "patternId": "spectral_asyncapi-message-messageId-uniqueness" + }, + { + "patternId": "spectral_asyncapi-operation-description" + }, + { + "patternId": "spectral_asyncapi-operation-operationId" + }, + { + "patternId": "spectral_asyncapi-operation-operationId-uniqueness" + }, + { + "patternId": "spectral_asyncapi-operation-security" + }, + { + "patternId": "spectral_asyncapi-payload" + }, + { + "patternId": "spectral_asyncapi-payload-default" + }, + { + "patternId": "spectral_asyncapi-payload-examples" + }, + { + "patternId": "spectral_asyncapi-payload-unsupported-schemaFormat" + }, + { + "patternId": "spectral_asyncapi-schema" + }, + { + "patternId": "spectral_asyncapi-schema-default" + }, + { + "patternId": "spectral_asyncapi-schema-examples" + }, + { + "patternId": "spectral_asyncapi-server-no-empty-variable" + }, + { + "patternId": "spectral_asyncapi-server-no-trailing-slash" + }, + { + "patternId": "spectral_asyncapi-servers" + }, + { + "patternId": "spectral_asyncapi-server-security" + }, + { + "patternId": "spectral_asyncapi-server-variables" + }, + { + "patternId": "spectral_asyncapi-tags" + }, + { + "patternId": "spectral_asyncapi-tags-uniqueness" + }, + { + "patternId": "spectral_asyncapi-unused-components-schema" + }, + { + "patternId": "spectral_asyncapi-unused-components-server" + }, + { + "patternId": "spectral_duplicated-entry-in-enum" + }, + { + "patternId": "spectral_info-contact" + }, + { + "patternId": "spectral_info-description" + }, + { + "patternId": "spectral_no-eval-in-markdown" + }, + { + "patternId": "spectral_no-$ref-siblings" + }, + { + "patternId": "spectral_no-script-tags-in-markdown" + }, + { + "patternId": "spectral_oas2-anyOf" + }, + { + "patternId": "spectral_oas2-api-host" + }, + { + "patternId": "spectral_oas2-api-schemes" + }, + { + "patternId": "spectral_oas2-discriminator" + }, + { + "patternId": "spectral_oas2-host-trailing-slash" + }, + { + "patternId": "spectral_oas2-oneOf" + }, + { + "patternId": "spectral_oas2-operation-formData-consume-check" + }, + { + "patternId": "spectral_oas2-operation-security-defined" + }, + { + "patternId": "spectral_oas2-schema" + }, + { + "patternId": "spectral_oas2-unused-definition" + }, + { + "patternId": "spectral_oas2-valid-media-example" + }, + { + "patternId": "spectral_oas2-valid-schema-example" + }, + { + "patternId": "spectral_oas3_1-callbacks-in-webhook" + }, + { + "patternId": "spectral_oas3_1-servers-in-webhook" + }, + { + "patternId": "spectral_oas3-api-servers" + }, + { + "patternId": "spectral_oas3-callbacks-in-callbacks" + }, + { + "patternId": "spectral_oas3-examples-value-or-externalValue" + }, + { + "patternId": "spectral_oas3-operation-security-defined" + }, + { + "patternId": "spectral_oas3-schema" + }, + { + "patternId": "spectral_oas3-server-trailing-slash" + }, + { + "patternId": "spectral_oas3-server-variables" + }, + { + "patternId": "spectral_oas3-unused-component" + }, + { + "patternId": "spectral_oas3-valid-media-example" + }, + { + "patternId": "spectral_oas3-valid-schema-example" + }, + { + "patternId": "spectral_openapi-tags-uniqueness" + }, + { + "patternId": "spectral_operation-description" + }, + { + "patternId": "spectral_operation-operationId" + }, + { + "patternId": "spectral_operation-operationId-unique" + }, + { + "patternId": "spectral_operation-operationId-valid-in-url" + }, + { + "patternId": "spectral_operation-parameters" + }, + { + "patternId": "spectral_operation-success-response" + }, + { + "patternId": "spectral_operation-tag-defined" + }, + { + "patternId": "spectral_operation-tags" + }, + { + "patternId": "spectral_path-declarations-must-exist" + }, + { + "patternId": "spectral_path-keys-no-trailing-slash" + }, + { + "patternId": "spectral_path-not-include-query" + }, + { + "patternId": "spectral_path-params" + }, + { + "patternId": "spectral_typed-enum" + } + ] + }, + { + "toolId": "Bandit", + "patterns": [ + { + "patternId": "Bandit_B101" + }, + { + "patternId": "Bandit_B102" + }, + { + "patternId": "Bandit_B103" + }, + { + "patternId": "Bandit_B104" + }, + { + "patternId": "Bandit_B105" + }, + { + "patternId": "Bandit_B106" + }, + { + "patternId": "Bandit_B107" + }, + { + "patternId": "Bandit_B108" + }, + { + "patternId": "Bandit_B110" + }, + { + "patternId": "Bandit_B112" + }, + { + "patternId": "Bandit_B202" + }, + { + "patternId": "Bandit_B301" + }, + { + "patternId": "Bandit_B302" + }, + { + "patternId": "Bandit_B303" + }, + { + "patternId": "Bandit_B304" + }, + { + "patternId": "Bandit_B305" + }, + { + "patternId": "Bandit_B306" + }, + { + "patternId": "Bandit_B307" + }, + { + "patternId": "Bandit_B309" + }, + { + "patternId": "Bandit_B310" + }, + { + "patternId": "Bandit_B311" + }, + { + "patternId": "Bandit_B312" + }, + { + "patternId": "Bandit_B313" + }, + { + "patternId": "Bandit_B314" + }, + { + "patternId": "Bandit_B315" + }, + { + "patternId": "Bandit_B316" + }, + { + "patternId": "Bandit_B317" + }, + { + "patternId": "Bandit_B318" + }, + { + "patternId": "Bandit_B319" + }, + { + "patternId": "Bandit_B321" + }, + { + "patternId": "Bandit_B322" + }, + { + "patternId": "Bandit_B323" + }, + { + "patternId": "Bandit_B324" + }, + { + "patternId": "Bandit_B325" + }, + { + "patternId": "Bandit_B401" + }, + { + "patternId": "Bandit_B402" + }, + { + "patternId": "Bandit_B403" + }, + { + "patternId": "Bandit_B404" + }, + { + "patternId": "Bandit_B405" + }, + { + "patternId": "Bandit_B406" + }, + { + "patternId": "Bandit_B407" + }, + { + "patternId": "Bandit_B408" + }, + { + "patternId": "Bandit_B409" + }, + { + "patternId": "Bandit_B411" + }, + { + "patternId": "Bandit_B412" + }, + { + "patternId": "Bandit_B415" + }, + { + "patternId": "Bandit_B502" + }, + { + "patternId": "Bandit_B503" + }, + { + "patternId": "Bandit_B504" + }, + { + "patternId": "Bandit_B505" + }, + { + "patternId": "Bandit_B602" + }, + { + "patternId": "Bandit_B603" + }, + { + "patternId": "Bandit_B604" + }, + { + "patternId": "Bandit_B605" + }, + { + "patternId": "Bandit_B606" + }, + { + "patternId": "Bandit_B607" + }, + { + "patternId": "Bandit_B608" + }, + { + "patternId": "Bandit_B609" + }, + { + "patternId": "Bandit_B612" + }, + { + "patternId": "Bandit_B613" + }, + { + "patternId": "Bandit_B614" + }, + { + "patternId": "Bandit_B615" + }, + { + "patternId": "Bandit_B704" + } + ] + }, + { + "toolId": "PyLintPython3", + "patterns": [ + { + "patternId": "PyLintPython3_C0123" + }, + { + "patternId": "PyLintPython3_C0200" + }, + { + "patternId": "PyLintPython3_E0100" + }, + { + "patternId": "PyLintPython3_E0101" + }, + { + "patternId": "PyLintPython3_E0102" + }, + { + "patternId": "PyLintPython3_E0103" + }, + { + "patternId": "PyLintPython3_E0104" + }, + { + "patternId": "PyLintPython3_E0105" + }, + { + "patternId": "PyLintPython3_E0106" + }, + { + "patternId": "PyLintPython3_E0107" + }, + { + "patternId": "PyLintPython3_E0108" + }, + { + "patternId": "PyLintPython3_E0110" + }, + { + "patternId": "PyLintPython3_E0112" + }, + { + "patternId": "PyLintPython3_E0113" + }, + { + "patternId": "PyLintPython3_E0114" + }, + { + "patternId": "PyLintPython3_E0115" + }, + { + "patternId": "PyLintPython3_E0117" + }, + { + "patternId": "PyLintPython3_E0202" + }, + { + "patternId": "PyLintPython3_E0203" + }, + { + "patternId": "PyLintPython3_E0211" + }, + { + "patternId": "PyLintPython3_E0236" + }, + { + "patternId": "PyLintPython3_E0238" + }, + { + "patternId": "PyLintPython3_E0239" + }, + { + "patternId": "PyLintPython3_E0240" + }, + { + "patternId": "PyLintPython3_E0241" + }, + { + "patternId": "PyLintPython3_E0301" + }, + { + "patternId": "PyLintPython3_E0302" + }, + { + "patternId": "PyLintPython3_E0601" + }, + { + "patternId": "PyLintPython3_E0603" + }, + { + "patternId": "PyLintPython3_E0604" + }, + { + "patternId": "PyLintPython3_E0701" + }, + { + "patternId": "PyLintPython3_E0702" + }, + { + "patternId": "PyLintPython3_E0704" + }, + { + "patternId": "PyLintPython3_E0710" + }, + { + "patternId": "PyLintPython3_E0711" + }, + { + "patternId": "PyLintPython3_E0712" + }, + { + "patternId": "PyLintPython3_E1003" + }, + { + "patternId": "PyLintPython3_E1102" + }, + { + "patternId": "PyLintPython3_E1111" + }, + { + "patternId": "PyLintPython3_E1120" + }, + { + "patternId": "PyLintPython3_E1121" + }, + { + "patternId": "PyLintPython3_E1123" + }, + { + "patternId": "PyLintPython3_E1124" + }, + { + "patternId": "PyLintPython3_E1125" + }, + { + "patternId": "PyLintPython3_E1126" + }, + { + "patternId": "PyLintPython3_E1127" + }, + { + "patternId": "PyLintPython3_E1132" + }, + { + "patternId": "PyLintPython3_E1200" + }, + { + "patternId": "PyLintPython3_E1201" + }, + { + "patternId": "PyLintPython3_E1205" + }, + { + "patternId": "PyLintPython3_E1206" + }, + { + "patternId": "PyLintPython3_E1300" + }, + { + "patternId": "PyLintPython3_E1301" + }, + { + "patternId": "PyLintPython3_E1302" + }, + { + "patternId": "PyLintPython3_E1303" + }, + { + "patternId": "PyLintPython3_E1304" + }, + { + "patternId": "PyLintPython3_E1305" + }, + { + "patternId": "PyLintPython3_E1306" + }, + { + "patternId": "PyLintPython3_R0202" + }, + { + "patternId": "PyLintPython3_R0203" + }, + { + "patternId": "PyLintPython3_W0101" + }, + { + "patternId": "PyLintPython3_W0102" + }, + { + "patternId": "PyLintPython3_W0104" + }, + { + "patternId": "PyLintPython3_W0105" + }, + { + "patternId": "PyLintPython3_W0106" + }, + { + "patternId": "PyLintPython3_W0107" + }, + { + "patternId": "PyLintPython3_W0108" + }, + { + "patternId": "PyLintPython3_W0109" + }, + { + "patternId": "PyLintPython3_W0120" + }, + { + "patternId": "PyLintPython3_W0122" + }, + { + "patternId": "PyLintPython3_W0124" + }, + { + "patternId": "PyLintPython3_W0150" + }, + { + "patternId": "PyLintPython3_W0199" + }, + { + "patternId": "PyLintPython3_W0221" + }, + { + "patternId": "PyLintPython3_W0222" + }, + { + "patternId": "PyLintPython3_W0233" + }, + { + "patternId": "PyLintPython3_W0404" + }, + { + "patternId": "PyLintPython3_W0410" + }, + { + "patternId": "PyLintPython3_W0601" + }, + { + "patternId": "PyLintPython3_W0602" + }, + { + "patternId": "PyLintPython3_W0604" + }, + { + "patternId": "PyLintPython3_W0611" + }, + { + "patternId": "PyLintPython3_W0612" + }, + { + "patternId": "PyLintPython3_W0622" + }, + { + "patternId": "PyLintPython3_W0702" + }, + { + "patternId": "PyLintPython3_W0705" + }, + { + "patternId": "PyLintPython3_W0711" + }, + { + "patternId": "PyLintPython3_W1300" + }, + { + "patternId": "PyLintPython3_W1301" + }, + { + "patternId": "PyLintPython3_W1302" + }, + { + "patternId": "PyLintPython3_W1303" + }, + { + "patternId": "PyLintPython3_W1305" + }, + { + "patternId": "PyLintPython3_W1306" + }, + { + "patternId": "PyLintPython3_W1307" + } + ] + }, + { + "toolId": "Checkov", + "patterns": [ + { + "patternId": "Checkov_CKV2_DOCKER_1" + }, + { + "patternId": "Checkov_CKV2_DOCKER_10" + }, + { + "patternId": "Checkov_CKV2_DOCKER_11" + }, + { + "patternId": "Checkov_CKV2_DOCKER_12" + }, + { + "patternId": "Checkov_CKV2_DOCKER_13" + }, + { + "patternId": "Checkov_CKV2_DOCKER_14" + }, + { + "patternId": "Checkov_CKV2_DOCKER_15" + }, + { + "patternId": "Checkov_CKV2_DOCKER_16" + }, + { + "patternId": "Checkov_CKV2_DOCKER_17" + }, + { + "patternId": "Checkov_CKV2_DOCKER_2" + }, + { + "patternId": "Checkov_CKV2_DOCKER_3" + }, + { + "patternId": "Checkov_CKV2_DOCKER_4" + }, + { + "patternId": "Checkov_CKV2_DOCKER_5" + }, + { + "patternId": "Checkov_CKV2_DOCKER_6" + }, + { + "patternId": "Checkov_CKV2_DOCKER_7" + }, + { + "patternId": "Checkov_CKV2_DOCKER_8" + }, + { + "patternId": "Checkov_CKV2_DOCKER_9" + }, + { + "patternId": "Checkov_CKV_BITBUCKET_1" + }, + { + "patternId": "Checkov_CKV_DOCKER_1" + }, + { + "patternId": "Checkov_CKV_DOCKER_10" + }, + { + "patternId": "Checkov_CKV_DOCKER_11" + }, + { + "patternId": "Checkov_CKV_DOCKER_2" + }, + { + "patternId": "Checkov_CKV_DOCKER_3" + }, + { + "patternId": "Checkov_CKV_DOCKER_4" + }, + { + "patternId": "Checkov_CKV_DOCKER_5" + }, + { + "patternId": "Checkov_CKV_DOCKER_6" + }, + { + "patternId": "Checkov_CKV_DOCKER_7" + }, + { + "patternId": "Checkov_CKV_DOCKER_8" + }, + { + "patternId": "Checkov_CKV_DOCKER_9" + }, + { + "patternId": "Checkov_CKV_GITHUB_1" + }, + { + "patternId": "Checkov_CKV_GITHUB_10" + }, + { + "patternId": "Checkov_CKV_GITHUB_11" + }, + { + "patternId": "Checkov_CKV_GITHUB_12" + }, + { + "patternId": "Checkov_CKV_GITHUB_13" + }, + { + "patternId": "Checkov_CKV_GITHUB_14" + }, + { + "patternId": "Checkov_CKV_GITHUB_15" + }, + { + "patternId": "Checkov_CKV_GITHUB_16" + }, + { + "patternId": "Checkov_CKV_GITHUB_17" + }, + { + "patternId": "Checkov_CKV_GITHUB_18" + }, + { + "patternId": "Checkov_CKV_GITHUB_19" + }, + { + "patternId": "Checkov_CKV_GITHUB_2" + }, + { + "patternId": "Checkov_CKV_GITHUB_20" + }, + { + "patternId": "Checkov_CKV_GITHUB_21" + }, + { + "patternId": "Checkov_CKV_GITHUB_22" + }, + { + "patternId": "Checkov_CKV_GITHUB_23" + }, + { + "patternId": "Checkov_CKV_GITHUB_26" + }, + { + "patternId": "Checkov_CKV_GITHUB_27" + }, + { + "patternId": "Checkov_CKV_GITHUB_28" + }, + { + "patternId": "Checkov_CKV_GITHUB_3" + }, + { + "patternId": "Checkov_CKV_GITHUB_4" + }, + { + "patternId": "Checkov_CKV_GITHUB_5" + }, + { + "patternId": "Checkov_CKV_GITHUB_6" + }, + { + "patternId": "Checkov_CKV_GITHUB_7" + }, + { + "patternId": "Checkov_CKV_GITHUB_8" + }, + { + "patternId": "Checkov_CKV_GITHUB_9" + }, + { + "patternId": "Checkov_CKV_GITLAB_1" + }, + { + "patternId": "Checkov_CKV_OPENAPI_1" + }, + { + "patternId": "Checkov_CKV_OPENAPI_10" + }, + { + "patternId": "Checkov_CKV_OPENAPI_11" + }, + { + "patternId": "Checkov_CKV_OPENAPI_12" + }, + { + "patternId": "Checkov_CKV_OPENAPI_13" + }, + { + "patternId": "Checkov_CKV_OPENAPI_14" + }, + { + "patternId": "Checkov_CKV_OPENAPI_15" + }, + { + "patternId": "Checkov_CKV_OPENAPI_16" + }, + { + "patternId": "Checkov_CKV_OPENAPI_17" + }, + { + "patternId": "Checkov_CKV_OPENAPI_18" + }, + { + "patternId": "Checkov_CKV_OPENAPI_19" + }, + { + "patternId": "Checkov_CKV_OPENAPI_2" + }, + { + "patternId": "Checkov_CKV_OPENAPI_20" + }, + { + "patternId": "Checkov_CKV_OPENAPI_21" + }, + { + "patternId": "Checkov_CKV_OPENAPI_3" + }, + { + "patternId": "Checkov_CKV_OPENAPI_4" + }, + { + "patternId": "Checkov_CKV_OPENAPI_5" + }, + { + "patternId": "Checkov_CKV_OPENAPI_6" + }, + { + "patternId": "Checkov_CKV_OPENAPI_7" + }, + { + "patternId": "Checkov_CKV_OPENAPI_8" + }, + { + "patternId": "Checkov_CKV_OPENAPI_9" + }, + { + "patternId": "Checkov_CKV_SECRET_1" + }, + { + "patternId": "Checkov_CKV_SECRET_11" + }, + { + "patternId": "Checkov_CKV_SECRET_12" + }, + { + "patternId": "Checkov_CKV_SECRET_13" + }, + { + "patternId": "Checkov_CKV_SECRET_14" + }, + { + "patternId": "Checkov_CKV_SECRET_15" + }, + { + "patternId": "Checkov_CKV_SECRET_16" + }, + { + "patternId": "Checkov_CKV_SECRET_17" + }, + { + "patternId": "Checkov_CKV_SECRET_18" + }, + { + "patternId": "Checkov_CKV_SECRET_19" + }, + { + "patternId": "Checkov_CKV_SECRET_2" + }, + { + "patternId": "Checkov_CKV_SECRET_3" + }, + { + "patternId": "Checkov_CKV_SECRET_4" + }, + { + "patternId": "Checkov_CKV_SECRET_5" + }, + { + "patternId": "Checkov_CKV_SECRET_6" + }, + { + "patternId": "Checkov_CKV_SECRET_7" + }, + { + "patternId": "Checkov_CKV_SECRET_8" + }, + { + "patternId": "Checkov_CKV_SECRET_9" + } + ] + }, + { + "toolId": "Lizard", + "patterns": [ + { + "patternId": "Lizard_file-nloc-medium", + "parameters": { + "threshold": "750" + } + }, + { + "patternId": "Lizard_nloc-medium", + "parameters": { + "threshold": "60" + } + }, + { + "patternId": "Lizard_parameter-count-medium" + }, + { + "patternId": "Lizard_nloc-critical", + "parameters": { + "threshold": "370" + } + }, + { + "patternId": "Lizard_ccn-critical", + "parameters": { + "threshold": "130" + } + }, + { + "patternId": "Lizard_ccn-medium" + }, + { + "patternId": "Lizard_parameter-count-critical" + }, + { + "patternId": "Lizard_file-nloc-critical", + "parameters": { + "threshold": "2890" + } + } + ] + }, + { + "toolId": "Agentlinter", + "patterns": [ + { + "patternId": "Agentlinter_blueprint_constraints-defined" + }, + { + "patternId": "Agentlinter_blueprint_coverage" + }, + { + "patternId": "Agentlinter_blueprint_identity-defined" + }, + { + "patternId": "Agentlinter_clarity_actionable-instructions" + }, + { + "patternId": "Agentlinter_clarity_action-without-context" + }, + { + "patternId": "Agentlinter_clarity_ambiguous-pronoun" + }, + { + "patternId": "Agentlinter_clarity_compound-instruction" + }, + { + "patternId": "Agentlinter_clarity_duplicate-content" + }, + { + "patternId": "Agentlinter_clarity_english-config-files" + }, + { + "patternId": "Agentlinter_clarity_escape-hatch-missing" + }, + { + "patternId": "Agentlinter_clarity_has-examples" + }, + { + "patternId": "Agentlinter_clarity_instruction-density" + }, + { + "patternId": "Agentlinter_clarity_naked-conditional" + }, + { + "patternId": "Agentlinter_clarity_no-contradictions" + }, + { + "patternId": "Agentlinter_clarity_no-vague-instructions" + }, + { + "patternId": "Agentlinter_clarity_obvious-statements" + }, + { + "patternId": "Agentlinter_clarity_priority-signal-missing" + }, + { + "patternId": "Agentlinter_clarity_sentence-complexity" + }, + { + "patternId": "Agentlinter_clarity_token-budget-range" + }, + { + "patternId": "Agentlinter_clarity_token-efficiency-score" + }, + { + "patternId": "Agentlinter_clarity_undefined-term" + }, + { + "patternId": "Agentlinter_claude-code_agent-focus" + }, + { + "patternId": "Agentlinter_claude-code_descriptive-ratio" + }, + { + "patternId": "Agentlinter_claude-code_hooks-structure" + }, + { + "patternId": "Agentlinter_claude-code_instruction-count" + }, + { + "patternId": "Agentlinter_claude-code_progressive-disclosure" + }, + { + "patternId": "Agentlinter_claude-code_relevance-trap" + }, + { + "patternId": "Agentlinter_claude-code_skills-vs-commands" + }, + { + "patternId": "Agentlinter_completeness_command-coverage" + }, + { + "patternId": "Agentlinter_completeness_freshness-file-paths" + }, + { + "patternId": "Agentlinter_completeness_has-boundaries" + }, + { + "patternId": "Agentlinter_completeness_has-error-handling" + }, + { + "patternId": "Agentlinter_completeness_has-identity" + }, + { + "patternId": "Agentlinter_completeness_has-output-format" + }, + { + "patternId": "Agentlinter_completeness_has-priorities" + }, + { + "patternId": "Agentlinter_completeness_has-tools" + }, + { + "patternId": "Agentlinter_completeness_has-user-context" + }, + { + "patternId": "Agentlinter_completeness_has-workflow" + }, + { + "patternId": "Agentlinter_completeness_session-learning-hooks" + }, + { + "patternId": "Agentlinter_completeness_verification-criteria-required" + }, + { + "patternId": "Agentlinter_consistency_circular-dependency" + }, + { + "patternId": "Agentlinter_consistency_identity-alignment" + }, + { + "patternId": "Agentlinter_consistency_language-mixing" + }, + { + "patternId": "Agentlinter_consistency_naming-convention" + }, + { + "patternId": "Agentlinter_consistency_no-duplicate-instructions" + }, + { + "patternId": "Agentlinter_consistency_outdated-cross-references" + }, + { + "patternId": "Agentlinter_consistency_permission-conflict" + }, + { + "patternId": "Agentlinter_consistency_priority-conflict" + }, + { + "patternId": "Agentlinter_consistency_referenced-files-exist" + }, + { + "patternId": "Agentlinter_consistency_stale-date" + }, + { + "patternId": "Agentlinter_consistency_stale-file-reference" + }, + { + "patternId": "Agentlinter_consistency_stale-package-reference" + }, + { + "patternId": "Agentlinter_consistency_timezone-locale-drift" + }, + { + "patternId": "Agentlinter_consistency_tone-voice-alignment" + }, + { + "patternId": "Agentlinter_memory_has-context-window-awareness" + }, + { + "patternId": "Agentlinter_memory_has-file-based-notes" + }, + { + "patternId": "Agentlinter_memory_has-handoff-protocol" + }, + { + "patternId": "Agentlinter_memory_has-learning-loop" + }, + { + "patternId": "Agentlinter_memory_has-memory-strategy" + }, + { + "patternId": "Agentlinter_memory_has-state-tracking" + }, + { + "patternId": "Agentlinter_memory_no-mental-notes" + }, + { + "patternId": "Agentlinter_remote-ready_env-vars-documented" + }, + { + "patternId": "Agentlinter_remote-ready_model-settings-specified" + }, + { + "patternId": "Agentlinter_remote-ready_workspace-path-specified" + }, + { + "patternId": "Agentlinter_runtime_auth-mode" + }, + { + "patternId": "Agentlinter_runtime_config-exists" + }, + { + "patternId": "Agentlinter_runtime_config-secrets" + }, + { + "patternId": "Agentlinter_runtime_dm-policy" + }, + { + "patternId": "Agentlinter_runtime_gateway-bind" + }, + { + "patternId": "Agentlinter_runtime_group-policy" + }, + { + "patternId": "Agentlinter_runtime_token-strength" + }, + { + "patternId": "Agentlinter_security_api-key-exposure" + }, + { + "patternId": "Agentlinter_security_env-var-references" + }, + { + "patternId": "Agentlinter_security_has-injection-defense" + }, + { + "patternId": "Agentlinter_security_has-permission-boundaries" + }, + { + "patternId": "Agentlinter_security_no-injection-defense" + }, + { + "patternId": "Agentlinter_security_no-pii-exposure" + }, + { + "patternId": "Agentlinter_security_no-secrets" + }, + { + "patternId": "Agentlinter_security_prompt-injection-vulnerability" + }, + { + "patternId": "Agentlinter_skill-safety_dangerous-commands" + }, + { + "patternId": "Agentlinter_skill-safety_data-exfiltration" + }, + { + "patternId": "Agentlinter_skill-safety_excessive-permissions" + }, + { + "patternId": "Agentlinter_skill-safety_has-metadata" + }, + { + "patternId": "Agentlinter_skill-safety_injection-vectors" + }, + { + "patternId": "Agentlinter_skill-safety_sensitive-paths" + }, + { + "patternId": "Agentlinter_skill-safety_skill-description-when-to-use" + }, + { + "patternId": "Agentlinter_skill-safety_skill-name-match-dir" + }, + { + "patternId": "Agentlinter_structure_circular-import" + }, + { + "patternId": "Agentlinter_structure_dead-import" + }, + { + "patternId": "Agentlinter_structure_file-size" + }, + { + "patternId": "Agentlinter_structure_has-file-map" + }, + { + "patternId": "Agentlinter_structure_has-main-file" + }, + { + "patternId": "Agentlinter_structure_has-sections" + }, + { + "patternId": "Agentlinter_structure_has-version-or-update-date" + }, + { + "patternId": "Agentlinter_structure_heading-hierarchy" + }, + { + "patternId": "Agentlinter_structure_modular-files" + }, + { + "patternId": "Agentlinter_structure_no-empty-sections" + }, + { + "patternId": "Agentlinter_structure_position-risk-warning" + }, + { + "patternId": "Agentlinter_token-budget_compressible-padding" + }, + { + "patternId": "Agentlinter_token-budget_section-weight" + }, + { + "patternId": "Agentlinter_token-budget_total-tokens" + }, + { + "patternId": "Agentlinter_token-budget_under-150-tokens" + } + ] + }, + { + "toolId": "Prospector", + "patterns": [ + { + "patternId": "Prospector_dodgy" + }, + { + "patternId": "Prospector_mccabe" + }, + { + "patternId": "Prospector_profile-validator" + }, + { + "patternId": "Prospector_pycodestyle" + }, + { + "patternId": "Prospector_pydocstyle" + }, + { + "patternId": "Prospector_pyflakes" + } + ] + }, + { + "toolId": "psscriptanalyzer", + "patterns": [ + { + "patternId": "psscriptanalyzer_psalignassignmentstatement" + }, + { + "patternId": "psscriptanalyzer_psavoidassignmenttoautomaticvariable" + }, + { + "patternId": "psscriptanalyzer_psavoiddefaultvalueformandatoryparameter" + }, + { + "patternId": "psscriptanalyzer_psavoiddefaultvalueswitchparameter" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalaliases" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalfunctions" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalvars" + }, + { + "patternId": "psscriptanalyzer_psavoidinvokingemptymembers" + }, + { + "patternId": "psscriptanalyzer_psavoidshouldcontinuewithoutforce" + }, + { + "patternId": "psscriptanalyzer_psavoidusingcomputernamehardcoded" + }, + { + "patternId": "psscriptanalyzer_psavoidusingconverttosecurestringwithplaintext" + }, + { + "patternId": "psscriptanalyzer_psavoidusingdeprecatedmanifestfields" + }, + { + "patternId": "psscriptanalyzer_psavoidusingemptycatchblock" + }, + { + "patternId": "psscriptanalyzer_psavoidusinginvokeexpression" + }, + { + "patternId": "psscriptanalyzer_psavoidusingplaintextforpassword" + }, + { + "patternId": "psscriptanalyzer_psavoidusingpositionalparameters" + }, + { + "patternId": "psscriptanalyzer_psavoidusingusernameandpasswordparams" + }, + { + "patternId": "psscriptanalyzer_psavoidusingwmicmdlet" + }, + { + "patternId": "psscriptanalyzer_psavoidusingwritehost" + }, + { + "patternId": "psscriptanalyzer_psdscdscexamplespresent" + }, + { + "patternId": "psscriptanalyzer_psdscdsctestspresent" + }, + { + "patternId": "psscriptanalyzer_psdscreturncorrecttypesfordscfunctions" + }, + { + "patternId": "psscriptanalyzer_psdscstandarddscfunctionsinresource" + }, + { + "patternId": "psscriptanalyzer_psdscuseidenticalmandatoryparametersfordsc" + }, + { + "patternId": "psscriptanalyzer_psdscuseidenticalparametersfordsc" + }, + { + "patternId": "psscriptanalyzer_psmisleadingbacktick" + }, + { + "patternId": "psscriptanalyzer_psmissingmodulemanifestfield" + }, + { + "patternId": "psscriptanalyzer_psplaceclosebrace" + }, + { + "patternId": "psscriptanalyzer_psplaceopenbrace" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectcomparisonwithnull" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectusageofassignmentoperator" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectusageofredirectionoperator" + }, + { + "patternId": "psscriptanalyzer_psreservedcmdletchar" + }, + { + "patternId": "psscriptanalyzer_psreservedparams" + }, + { + "patternId": "psscriptanalyzer_psshouldprocess" + }, + { + "patternId": "psscriptanalyzer_psuseapprovedverbs" + }, + { + "patternId": "psscriptanalyzer_psusebomforunicodeencodedfile" + }, + { + "patternId": "psscriptanalyzer_psusecmdletcorrectly" + }, + { + "patternId": "psscriptanalyzer_psusecompatiblecmdlets" + }, + { + "patternId": "psscriptanalyzer_psuseliteralinitializerforhashtable" + }, + { + "patternId": "psscriptanalyzer_psuseoutputtypecorrectly" + }, + { + "patternId": "psscriptanalyzer_psusepscredentialtype" + }, + { + "patternId": "psscriptanalyzer_psuseshouldprocessforstatechangingfunctions" + }, + { + "patternId": "psscriptanalyzer_psusesupportsshouldprocess" + }, + { + "patternId": "psscriptanalyzer_psusetoexportfieldsinmanifest" + } + ] + } + ] +} diff --git a/.codacy/tmp/codacy-baseline.json b/.codacy/tmp/codacy-baseline.json new file mode 100644 index 0000000..366f14d --- /dev/null +++ b/.codacy/tmp/codacy-baseline.json @@ -0,0 +1,4891 @@ +{ + "metadata": { + "startedAt": "2026-10-28T07:10:04.629Z", + "completedAt": "2026-10-28T07:11:38.571Z", + "durationMs": 93942, + "repositoryRoot": "/mnt/win/Repositories/GameModding/DataCenter/GregDesktopApps/gregApp.Modmanager", + "executionMode": "auto-install", + "phaseTimings": { + "availabilityMs": 2190, + "fileDiscoveryMs": 96, + "fileRoutingMs": 15, + "toolExecutionMs": 91521, + "installMs": 0, + "toolUpdateMs": 0 + } + }, + "capability": { + "ready": [ + { + "toolId": "jackson", + "displayName": "Jackson Linter", + "version": "1.0.0", + "installation": "bundled", + "runner": "local", + "filesRouted": 16, + "configSource": "codacy" + }, + { + "toolId": "markdownlint", + "displayName": "markdownlint", + "version": "0.41.1", + "installation": "bundled", + "runner": "local", + "filesRouted": 49, + "configSource": "codacy" + }, + { + "toolId": "shellcheck", + "displayName": "ShellCheck", + "version": "0.11.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 12, + "configSource": "codacy" + }, + { + "toolId": "Hadolint", + "displayName": "Hadolint", + "version": "2.14.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 3, + "configSource": "codacy" + }, + { + "toolId": "Ruff", + "displayName": "Ruff", + "version": "0.16.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 2, + "configSource": "codacy" + }, + { + "toolId": "Trivy", + "displayName": "Trivy", + "version": "0.72.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 371, + "configSource": "codacy" + }, + { + "toolId": "Semgrep", + "displayName": "Opengrep", + "version": "1.26.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 238, + "configSource": "codacy" + }, + { + "toolId": "spectral", + "displayName": "Spectral", + "version": "1.23.1", + "installation": "bundled", + "runner": "local", + "filesRouted": 35, + "configSource": "codacy" + }, + { + "toolId": "Bandit", + "displayName": "Bandit", + "version": "1.9.4", + "installation": "codacy", + "runner": "local", + "filesRouted": 2, + "configSource": "codacy" + }, + { + "toolId": "PyLintPython3", + "displayName": "Pylint", + "version": "4.0.5", + "installation": "codacy", + "runner": "local", + "filesRouted": 2, + "configSource": "codacy" + }, + { + "toolId": "Checkov", + "displayName": "Checkov", + "version": "3.3.8", + "installation": "codacy", + "runner": "local", + "filesRouted": 37, + "configSource": "codacy" + }, + { + "toolId": "Lizard", + "displayName": "Lizard", + "version": "1.23.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 187, + "configSource": "codacy" + }, + { + "toolId": "PMD7", + "displayName": "PMD 7", + "version": "7.26.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 1, + "configSource": "codacy" + }, + { + "toolId": "Agentlinter", + "displayName": "Agentlinter", + "version": "0.3.3", + "installation": "bundled", + "runner": "local", + "filesRouted": 4, + "configSource": "codacy" + }, + { + "toolId": "Prospector", + "displayName": "Prospector", + "version": "1.19.1", + "installation": "codacy", + "runner": "local", + "filesRouted": 2, + "configSource": "codacy" + } + ], + "unavailable": [ + { + "toolId": "psscriptanalyzer", + "displayName": "PSScriptAnalyzer", + "reason": "No local analyzer (configured on Codacy Cloud)", + "availableVia": "cloud" + }, + { + "toolId": "SonarCSharp", + "displayName": "SonarC#", + "reason": "No local analyzer (configured on Codacy Cloud)", + "availableVia": "cloud" + } + ], + "checkedAt": "2026-10-28T07:10:06.934Z" + }, + "issues": [ + { + "filePath": "docs/examples/manifests/07_steam_manifest.json", + "patternId": "jackson_parse-error", + "toolId": "jackson", + "line": 1, + "column": 1, + "message": "Unexpected end of JSON input", + "lineContent": "", + "category": "ErrorProne", + "severity": "Error" + }, + { + "filePath": ".github/PULL_REQUEST_TEMPLATE.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 7, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "## Types of changes\r", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/PULL_REQUEST_TEMPLATE.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 12, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "## Checklist:\r", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/PULL_REQUEST_TEMPLATE.md", + "patternId": "markdownlint_MD026", + "toolId": "markdownlint", + "line": 12, + "column": 13, + "message": "Trailing punctuation in heading: Punctuation: ':'", + "lineContent": "## Checklist:\r", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/PULL_REQUEST_TEMPLATE.md", + "patternId": "markdownlint_MD032", + "toolId": "markdownlint", + "line": 8, + "column": 1, + "message": "Lists should be surrounded by blank lines", + "lineContent": "- [ ] Bug fix (non-breaking change which fixes an issue)\r", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/PULL_REQUEST_TEMPLATE.md", + "patternId": "markdownlint_MD032", + "toolId": "markdownlint", + "line": 13, + "column": 1, + "message": "Lists should be surrounded by blank lines", + "lineContent": "- [ ] My code follows the code style of this project.\r", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".jules/de-mock.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 3, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "## 2026-06-29 - Initial Analysis", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".jules/de-mock.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 8, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "## 2026-06-29 - AuthApiClient Mock Replacement", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".jules/de-mock.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 13, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "## 2026-06-29 - InstallIntentClient Signature Verification", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Resources/Fonts/Vendored/README.md", + "patternId": "markdownlint_MD012", + "toolId": "markdownlint", + "line": 14, + "column": 1, + "message": "Multiple consecutive blank lines: Expected: 1; Actual: 2", + "lineContent": "", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 21, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Above", + "lineContent": "## [1.7.0] - 2026-09-28", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 23, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 108, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 135, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 191, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Removed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 200, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 204, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 211, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Changed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 221, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 232, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 237, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Changed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 242, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 248, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 263, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Changed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 269, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 278, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 285, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Changed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 290, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 297, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 303, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 309, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD032", + "toolId": "markdownlint", + "line": 20, + "column": 1, + "message": "Lists should be surrounded by blank lines", + "lineContent": " Coverage Reporter bei jedem Push/PR (Job `coverage` in `rust.yml`); benötigt das Geheimnis `CODACY_PROJECT_TOKEN`.", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "DESIGN.md", + "patternId": "markdownlint_MD001", + "toolId": "markdownlint", + "line": 295, + "column": 1, + "message": "Heading levels should only increment by one level at a time: Expected: h3; Actual: h6", + "lineContent": "###### Letzte Aktualisierung: 2026-05-05", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 396, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Community", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 626, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Sammlungen", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 826, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Downloads", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 1687, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Sicherheit", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 1894, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Sammlungen", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 45, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Premium-Funktionen", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 210, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Web-Funktionen", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 693, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# App-Funktionen", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 1406, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Backend-Funktionen", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 2041, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Manifeste, Paketformate und Upload-Workflows", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 2265, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Bereits vorhandene Manifesttypen der App", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 2345, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Empfohlene Manifest-Funktionsliste für die eigene Plattform", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 2363, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Empfohlener Upload- und Veröffentlichungsworkflow", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 2381, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Priorisierte Roadmap", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 2487, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Desktop-Implementierungstracking", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD025", + "toolId": "markdownlint", + "line": 2539, + "column": 1, + "message": "Multiple top-level headings in the same document", + "lineContent": "# Produktprinzipien", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD028", + "toolId": "markdownlint", + "line": 11, + "column": 1, + "message": "Blank line inside blockquote", + "lineContent": "", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD033", + "toolId": "markdownlint", + "line": 2124, + "column": 52, + "message": "Inline HTML: Element: vdf", + "lineContent": "- **Upload-Kanäle:** steamcmd +workshop_build_item ", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": "QUICKSTART.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 94, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "### \"Steam Disconnected\"", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "QUICKSTART.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 99, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "### \"Steam publish failed: FileNotFound\"", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "QUICKSTART.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 104, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "### \"Upload check is red\"", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "QUICKSTART.md", + "patternId": "markdownlint_MD022", + "toolId": "markdownlint", + "line": 108, + "column": 1, + "message": "Headings should be surrounded by blank lines: Expected: 1; Actual: 0; Below", + "lineContent": "### \"Workshop legal agreement\"", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "QUICKSTART.md", + "patternId": "markdownlint_MD032", + "toolId": "markdownlint", + "line": 95, + "column": 1, + "message": "Lists should be surrounded by blank lines", + "lineContent": "- Steam must be running **before** you start the Modmanager.", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "QUICKSTART.md", + "patternId": "markdownlint_MD032", + "toolId": "markdownlint", + "line": 100, + "column": 1, + "message": "Lists should be surrounded by blank lines", + "lineContent": "- Every file under `content/` and the preview image must exist and be readable.", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "QUICKSTART.md", + "patternId": "markdownlint_MD032", + "toolId": "markdownlint", + "line": 105, + "column": 1, + "message": "Lists should be surrounded by blank lines", + "lineContent": "- Open the editor: title, description, preview image, and `content/` folder", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "QUICKSTART.md", + "patternId": "markdownlint_MD032", + "toolId": "markdownlint", + "line": 109, + "column": 1, + "message": "Lists should be surrounded by blank lines", + "lineContent": "- Accept the Steam Workshop legal agreement once in the Steam client,", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "README.md", + "patternId": "markdownlint_MD026", + "toolId": "markdownlint", + "line": 156, + "column": 34, + "message": "Trailing punctuation in heading: Punctuation: '!'", + "lineContent": "## 🚀 Join the gregFramework Team!", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "build/scripts/macos/run-remote-manual-test.sh", + "patternId": "shellcheck_SC2029", + "toolId": "shellcheck", + "line": 45, + "column": 92, + "endColumn": 103, + "message": "Note that, unescaped, this expands on the client side.", + "lineContent": "ssh \"$MACOS_HOST\" \"command -v dotnet >/dev/null && command -v rsync >/dev/null && mkdir -p $REMOTE_DIR\"", + "category": "ErrorProne", + "severity": "Warning" + }, + { + "filePath": "build/scripts/macos/run-remote-manual-test.sh", + "patternId": "shellcheck_SC2029", + "toolId": "shellcheck", + "line": 54, + "column": 42, + "endColumn": 53, + "message": "Note that, unescaped, this expands on the client side.", + "lineContent": "ssh \"$MACOS_HOST\" \"set -euo pipefail; cd $REMOTE_DIR; dotnet restore GregModmanager.sln; dotnet build GregModmanager.sln --no-restore -c Release; dotnet test GregModmanager.sln --no-build -c Release --verbosity normal; dotnet publish src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj -c Release -r osx-$ARCH --self-contained true -o artifacts/manual-macos-osx-$ARCH\"", + "category": "ErrorProne", + "severity": "Warning" + }, + { + "filePath": "build/scripts/linux/build-rust-packages.sh", + "patternId": "shellcheck_SC2034", + "toolId": "shellcheck", + "line": 12, + "column": 1, + "endColumn": 7, + "message": "IS_PRE appears unused. Verify use (or export if used externally).", + "lineContent": "IS_PRE=\"${3:-false}\"", + "category": "ErrorProne", + "severity": "Warning" + }, + { + "filePath": ".devcontainer/Dockerfile", + "patternId": "Hadolint_DL3008", + "toolId": "Hadolint", + "line": 9, + "column": 1, + "message": "Pin versions in apt get install. Instead of `apt-get install ` use `apt-get install =`", + "lineContent": "RUN groupadd --gid \"$USER_GID\" \"$USERNAME\" \\", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "docker/Dockerfile.windows", + "patternId": "Hadolint_SC1001", + "toolId": "Hadolint", + "line": 20, + "column": 1, + "message": "This \\w will be a regular 'w' in this context.", + "lineContent": "RUN dotnet publish src\\GregModmanager.Avalonia\\GregModmanager.Avalonia.csproj `", + "category": "BestPractice", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 32, + "column": 89, + "endColumn": 95, + "message": "Line too long (94 > 88)", + "lineContent": " \".sh\", \".bash\", \".zsh\", \".cmd\", \".bat\", \".yml\", \".yaml\", \".json\", \".toml\", \".ini\", \".env\",", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_S603_subprocess-without-shell-equals-true", + "toolId": "Ruff", + "line": 39, + "column": 14, + "endColumn": 28, + "message": "`subprocess` call: check for execution of untrusted input", + "lineContent": " result = subprocess.run(", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_S607_start-process-with-partial-path", + "toolId": "Ruff", + "line": 40, + "column": 9, + "endColumn": 23, + "message": "Starting a process with a partial executable path", + "lineContent": " [\"git\", *args],", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 95, + "column": 89, + "endColumn": 106, + "message": "Line too long (105 > 88)", + "lineContent": " current_file, current_new_line = parse_diff_line(raw, current_file, current_new_line, file_lines)", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 100, + "column": 89, + "endColumn": 138, + "message": "Line too long (137 > 88)", + "lineContent": "def parse_diff_line(raw: str, current_file: str, current_new_line: int, file_lines: Dict[str, List[Tuple[int, str]]]) -> Tuple[str, int]:", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 161, + "column": 89, + "endColumn": 105, + "message": "Line too long (104 > 88)", + "lineContent": " secret=re.compile(r\"(secret|token|password|apikey|api[_-]?key|private[_-]?key)\", re.IGNORECASE),", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 162, + "column": 89, + "endColumn": 141, + "message": "Line too long (140 > 88)", + "lineContent": " secret_assignment=re.compile(r\"(secret|token|password|apikey|api[_-]?key|private[_-]?key)\\s*[:=]\\s*['\\\"][^'\\\"]{8,}\", re.IGNORECASE),", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 163, + "column": 89, + "endColumn": 133, + "message": "Line too long (132 > 88)", + "lineContent": " network=re.compile(r\"(curl\\s|wget\\s|http[s]?://|requests\\.|fetch\\(|http\\.get|HttpClient|Invoke-RestMethod)\", re.IGNORECASE),", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 164, + "column": 89, + "endColumn": 139, + "message": "Line too long (138 > 88)", + "lineContent": " system=re.compile(r\"(Process\\.Start|cmd\\.exe|powershell\\.exe|/bin/sh|subprocess\\.|Runtime\\.getRuntime\\(\\)\\.exec)\", re.IGNORECASE),", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 179, + "column": 89, + "endColumn": 118, + "message": "Line too long (117 > 88)", + "lineContent": "def analyze_added_lines(file_path: str, added_lines: List[Tuple[int, str]], patterns: ScanPatterns) -> List[Finding]:", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 194, + "column": 89, + "endColumn": 91, + "message": "Line too long (90 > 88)", + "lineContent": " findings.append(obfuscation_finding(file_path, added_lines, patterns.obfuscation))", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 199, + "column": 89, + "endColumn": 120, + "message": "Line too long (119 > 88)", + "lineContent": "def secret_exfiltration_finding(file_path: str, added_lines: List[Tuple[int, str]], patterns: ScanPatterns) -> Finding:", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 205, + "column": 89, + "endColumn": 132, + "message": "Line too long (131 > 88)", + "lineContent": " start_line=min(first_match_line(added_lines, patterns.secret_assignment), first_match_line(added_lines, patterns.network)),", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 207, + "column": 89, + "endColumn": 111, + "message": "Line too long (110 > 88)", + "lineContent": " \"Threat score: 9/10. This file contains both secret-related terms and network transfer patterns. \"", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 213, + "column": 89, + "endColumn": 107, + "message": "Line too long (106 > 88)", + "lineContent": "def network_finding(file_path: str, added_lines: List[Tuple[int, str]], pattern: Pattern[str]) -> Finding:", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 221, + "column": 89, + "endColumn": 97, + "message": "Line too long (96 > 88)", + "lineContent": " \"Threat score: 5/10. Network-related operations were introduced in recent changes. \"", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 227, + "column": 89, + "endColumn": 113, + "message": "Line too long (112 > 88)", + "lineContent": "def system_access_finding(file_path: str, added_lines: List[Tuple[int, str]], pattern: Pattern[str]) -> Finding:", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 236, + "column": 89, + "endColumn": 99, + "message": "Line too long (98 > 88)", + "lineContent": " \"Validate command safety and ensure no user-controlled command injection path exists.\"", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 241, + "column": 89, + "endColumn": 111, + "message": "Line too long (110 > 88)", + "lineContent": "def obfuscation_finding(file_path: str, added_lines: List[Tuple[int, str]], pattern: Pattern[str]) -> Finding:", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 286, + "column": 89, + "endColumn": 117, + "message": "Line too long (116 > 88)", + "lineContent": " return {\"name\": \"Malicious Code Scanner\", \"informationUri\": \"https://github.com\", \"rules\": list(rules.values())}", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 318, + "column": 89, + "endColumn": 146, + "message": "Line too long (145 > 88)", + "lineContent": "def write_scan_outputs(output: str, summary: str, days: int, commits: List[str], files: List[str], findings: List[Finding], sarif: dict) -> None:", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 325, + "column": 89, + "endColumn": 100, + "message": "Line too long (99 > 88)", + "lineContent": "def build_summary(days: int, commits: List[str], files: List[str], findings: List[Finding]) -> str:", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 332, + "column": 89, + "endColumn": 97, + "message": "Line too long (96 > 88)", + "lineContent": " \"Patterns checked: secret-exfiltration, suspicious-network, system-access, obfuscation\",", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 354, + "column": 89, + "endColumn": 94, + "message": "Line too long (93 > 88)", + "lineContent": " summary_lines.append(f\"- [{f.severity}] {f.rule_id} :: {f.file_path}:{f.start_line}\")", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 369, + "column": 89, + "endColumn": 90, + "message": "Line too long (89 > 88)", + "lineContent": " \"artifactLocation\": {\"uri\": \".github/scripts/malicious_scan.py\"},", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 382, + "column": 89, + "endColumn": 98, + "message": "Line too long (97 > 88)", + "lineContent": " write_scan_outputs(args.output, args.summary, args.days, commits, files, findings, sarif)", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 386, + "column": 89, + "endColumn": 104, + "message": "Line too long (103 > 88)", + "lineContent": " Path(args.output).write_text(json.dumps(make_error_sarif(message), indent=2), encoding=\"utf-8\")", + "category": "CodeStyle", + "severity": "Info" + }, + { + "filePath": "build/scripts/linux/patch-steamworks-symbols.py", + "patternId": "Ruff_E501_line-too-long", + "toolId": "Ruff", + "line": 24, + "column": 89, + "endColumn": 108, + "message": "Line too long (107 > 88)", + "lineContent": " b\"SteamAPI_SteamNetworkingSockets_SteamAPI_v012\": b\"SteamAPI_SteamNetworkingSockets_SteamAPI_v013\",", + "category": "CodeStyle", + "severity": "Info" + }, + { + "patternId": "Trivy_vulnerability_medium", + "message": "Insecure dependency cargo/rustls@0.23.45 (GHSA-c8m5-c952-6cm4: Rustls: Session Debug formatting exposes TLS master secrets and resumption PSKs) (update to 0.23.46)", + "category": "Security", + "severity": "Warning", + "sourceId": "GHSA-c8m5-c952-6cm4", + "filePath": "Cargo.lock", + "toolId": "Trivy", + "line": 5160, + "column": 1, + "lineContent": "[[package]]" + }, + { + "patternId": "Trivy_vulnerability_minor", + "message": "Insecure dependency cargo/rustls@0.23.45 (GHSA-h2v8-394m-p7vv: Rustls: Brotli certificate decompression can allocate an attacker-controlled amount of memory up to 1 GiB before authentication.) (update to 0.23.46)", + "category": "Security", + "severity": "Info", + "sourceId": "GHSA-h2v8-394m-p7vv", + "filePath": "Cargo.lock", + "toolId": "Trivy", + "line": 5160, + "column": 1, + "lineContent": "[[package]]" + }, + { + "patternId": "Trivy_vulnerability_minor", + "message": "Insecure dependency cargo/rustls@0.23.45 (GHSA-vp88-798v-h67f: rustls: ECH rejection can expose buffered application data to authenticated outer server before `ech_required` alert) (update to 0.23.46)", + "category": "Security", + "severity": "Info", + "sourceId": "GHSA-vp88-798v-h67f", + "filePath": "Cargo.lock", + "toolId": "Trivy", + "line": 5160, + "column": 1, + "lineContent": "[[package]]" + }, + { + "patternId": "Trivy_vulnerability_minor", + "message": "Insecure dependency cargo/rustls@0.23.45 (GHSA-w44r-93j7-qv28: rustls: An unauthenticated ServerHello poisons the per-name key-exchange record, so later ClientHellos carry only a classical X25519 share) (update to 0.23.46)", + "category": "Security", + "severity": "Info", + "sourceId": "GHSA-w44r-93j7-qv28", + "filePath": "Cargo.lock", + "toolId": "Trivy", + "line": 5160, + "column": 1, + "lineContent": "[[package]]" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 163, + "column": 60, + "endColumn": 104, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " var progress = new Progress(message => AppFileLog.Info($\"Runtime setup: {message}\"));", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 165, + "column": 13, + "endColumn": 83, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Info($\"Automatic runtime setup finished: {result.Message}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 193, + "column": 9, + "endColumn": 70, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Info($\"Workspace selected on first start: {path}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 324, + "column": 13, + "endColumn": 76, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Could not load profile avatar: {ex.Message}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 538, + "column": 13, + "endColumn": 51, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " System.Diagnostics.Process.Start(psi);", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 570, + "column": 17, + "endColumn": 31, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " FileName = exe,", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 574, + "column": 13, + "endColumn": 51, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " System.Diagnostics.Process.Start(psi);", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Program.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 71, + "column": 5, + "endColumn": 76, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\t\tAppFileLog.Error($\"UnhandledException (terminating={e.IsTerminating})\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Program.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 112, + "column": 25, + "endColumn": 79, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Info($\"CurrentDirectory set to: {baseDir}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Program.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 119, + "column": 13, + "endColumn": 74, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Info($\"SteamApiNativeLoader.TryPreload={steamOk}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Services/DialogService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 258, + "column": 17, + "endColumn": 80, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Could not copy dialog message: {ex.Message}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/Auth/AuthApiClient.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 81, + "column": 13, + "endColumn": 77, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Token exchange failed: {response.StatusCode}\");\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/Auth/SessionManager.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 105, + "column": 17, + "endColumn": 72, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Browser launch failed: {ex.Message}\");\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/HeadlessRunner.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 251, + "column": 5, + "endColumn": 68, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\t\tAppFileLog.Error($\"Headless publish failed: {outcome.Message}\");\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/Install/InstallIntentClient.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 48, + "column": 13, + "endColumn": 100, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Info($\"Received install intent: {intent.PackageId} (ID: {intent.IntentId})\");\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/Install/InstallIntentClient.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 53, + "column": 17, + "endColumn": 119, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Install intent validation failed for package {intent.PackageId}: {validationError}\");\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/Install/InstallIntentClient.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 55, + "column": 17, + "endColumn": 88, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Install intent validation failed: {validationError}\");\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/Install/InstallIntentClient.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 59, + "column": 13, + "endColumn": 124, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Info($\"Install intent validated successfully for package {intent.PackageId}. Queuing installation.\");\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/Install/InstallIntentClient.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 64, + "column": 13, + "endColumn": 86, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Info($\"Installation queued for package '{intent.PackageId}'.\");\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/ProtocolRegistryService.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 86, + "column": 13, + "endColumn": 47, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " Process.Start(psi)?.WaitForExit();", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/RalphSyncService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 21, + "column": 21, + "endColumn": 25, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\tFile.WriteAllText(path, JsonSerializer.Serialize(payload, AppJsonContext.Default.RalphTaskStatus));\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/ReproBundleService.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 177, + "column": 3, + "endColumn": 35, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": "\t\treturn Process.Start(startInfo);", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SafeProcess.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 25, + "column": 17, + "endColumn": 91, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Blocked attempt to open insecure or invalid URL: {url}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SafeProcess.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 48, + "column": 17, + "endColumn": 83, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Blocked attempt to open missing folder: {path}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SafeProcess.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 72, + "column": 17, + "endColumn": 100, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Blocked attempt to select missing file system entry: {filePath}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SafeProcess.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 105, + "column": 17, + "endColumn": 92, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Blocked attempt to launch missing executable: {exePath}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SafeProcess.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 143, + "column": 13, + "endColumn": 32, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " FileName = fileName,", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SafeProcess.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 152, + "column": 9, + "endColumn": 29, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " Process.Start(info);", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 52, + "column": 6, + "endColumn": 59, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\t\t\tAppFileLog.Warn($\"[Steam] {LastSteamConnectionHint}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 66, + "column": 8, + "endColumn": 68, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\t\t\t\t\tAppFileLog.Info($\"[Steam] SteamClient already initialized.\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 78, + "column": 5, + "endColumn": 100, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\t\tAppFileLog.Info($\"[Steam] Calling SteamClient.Init({SteamConstants.DataCenterAppId}, true)...\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 86, + "column": 6, + "endColumn": 100, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\t\t\tAppFileLog.Warn($\"[Steam] SteamApps interface version mismatch (non-fatal): {initEx.Message}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 99, + "column": 5, + "endColumn": 60, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\t\tAppFileLog.Info($\"[Steam] SteamClient.Init succeeded.\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 112, + "column": 7, + "endColumn": 71, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\t\t\t\tAppFileLog.Info($\"[Steam] SteamClient was already initialized.\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 148, + "column": 4, + "endColumn": 57, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\tAppFileLog.Warn($\"[Steam] {LastSteamConnectionHint}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 515, + "column": 52, + "endColumn": 62, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\tvar previewBytes = await File.ReadAllBytesAsync(absPreview, cancellationToken).ConfigureAwait(false);", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 517, + "column": 34, + "endColumn": 45, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\tawait File.WriteAllBytesAsync(tempPreview, previewBytes, cancellationToken).ConfigureAwait(false);", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 1029, + "column": 4, + "endColumn": 57, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": "\t\t\tAppFileLog.Warn($\"[Steam] {LastSteamConnectionHint}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/TelemetryService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 68, + "column": 29, + "endColumn": 118, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Info($\"Telemetry: Uploaded and deleted crash report {Path.GetFileName(file)}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/TelemetryService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 119, + "column": 13, + "endColumn": 97, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Telemetry: Could not serialize event '{eventName}': {ex.Message}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/TelemetryService.cs", + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "toolId": "Semgrep", + "line": 179, + "column": 17, + "endColumn": 100, + "message": "String interpolation in log message obscures the distinction between variables and the log message.", + "lineContent": " AppFileLog.Warn($\"Telemetry: Loki push failed with {response.StatusCode}: {error}\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 223, + "column": 32, + "endColumn": 36, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\tvar json = File.ReadAllText(path);\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 877, + "column": 37, + "endColumn": 41, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\t\ttry { bytes = File.ReadAllBytes(full); }\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 890, + "column": 34, + "endColumn": 41, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\t\t\t\tvar pb = File.ReadAllBytes(preview);\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 997, + "column": 21, + "endColumn": 25, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\tFile.WriteAllText(path, JsonSerializer.Serialize(metadata, AppJsonContext.Default.WorkshopMetadata));\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 593, + "column": 5, + "endColumn": 25, + "message": "temp_dir should not be used for security operations.", + "lineContent": " std::env::temp_dir().join(\"gregmodmanager-protocol\")", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe", + "toolId": "Semgrep", + "line": 2816, + "column": 25, + "endColumn": 48, + "message": "current_exe should not be used for security operations.", + "lineContent": " let message = match std::env::current_exe() {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 2964, + "column": 15, + "endColumn": 35, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(\"gregmodmanager-thumbs\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/main.rs", + "patternId": "Semgrep_rust.lang.security.args.args", + "toolId": "Semgrep", + "line": 34, + "column": 24, + "endColumn": 40, + "message": "args should not be used for security operations.", + "lineContent": " for arg in std::env::args().skip(1) {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/main.rs", + "patternId": "Semgrep_rust.lang.security.args.args", + "toolId": "Semgrep", + "line": 48, + "column": 16, + "endColumn": 32, + "message": "args should not be used for security operations.", + "lineContent": " for arg in std::env::args().skip(1) {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/shots.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 449, + "column": 15, + "endColumn": 35, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let tmp = std::env::temp_dir().join(format!(\"greg-sync-test-{}\", std::process::id()));", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-cli/src/main.rs", + "patternId": "Semgrep_rust.lang.security.args.args", + "toolId": "Semgrep", + "line": 73, + "column": 20, + "endColumn": 36, + "message": "args should not be used for security operations.", + "lineContent": " let code = run(std::env::args().collect());", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-core/src/docs/project_docs.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 272, + "column": 13, + "endColumn": 33, + "message": "temp_dir should not be used for security operations.", + "lineContent": " std::env::temp_dir().join(format!(\"greg-docs-test-{nanos}-{}\", std::process::id()));", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 622, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 640, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/discovery.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 109, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let base = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/game.rs", + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe", + "toolId": "Semgrep", + "line": 224, + "column": 38, + "endColumn": 61, + "message": "current_exe should not be used for security operations.", + "lineContent": " if let Ok(exe_dir) = std::env::current_exe() {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/installers.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 300, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/installers.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 329, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/local_content.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 220, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let base = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/native_config.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 71, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/packs.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 129, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/sync.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 198, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let base = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/templates.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 277, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-modstore/src/install.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 195, + "column": 24, + "endColumn": 44, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let artifact = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-modstore/src/install.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 442, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/instance.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 85, + "column": 5, + "endColumn": 25, + "message": "temp_dir should not be used for security operations.", + "lineContent": " std::env::temp_dir().join(format!(\"{app_name}.lock\"))", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/instance.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 166, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let path = std::env::temp_dir().join(\"gregtest-inst-missing-1.lock\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/paths.rs", + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe", + "toolId": "Semgrep", + "line": 15, + "column": 22, + "endColumn": 45, + "message": "current_exe should not be used for security operations.", + "lineContent": " if let Ok(exe) = std::env::current_exe() {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/paths.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 29, + "column": 5, + "endColumn": 25, + "message": "temp_dir should not be used for security operations.", + "lineContent": " std::env::temp_dir().join(\"gregModmanager-logs\")", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/prefs.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 31, + "column": 32, + "endColumn": 52, + "message": "temp_dir should not be used for security operations.", + "lineContent": " .unwrap_or_else(|| std::env::temp_dir().join(\"gregmodmanager-preferences.json\"));", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/workspace.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 360, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage", + "toolId": "Semgrep", + "line": 693, + "column": 28, + "endLine": 770, + "endColumn": 14, + "message": "Detected 'unsafe' usage, please audit for secure usage", + "lineContent": " let attached = unsafe {", + "multilineContent": [ + " let attached = unsafe {", + " let ugc = sys::SteamAPI_SteamUGC_v021();", + " if ugc.is_null() {", + " return Err(SteamError::Api(\"Steam UGC interface unavailable\".into()));", + " }", + " let handle = sys::SteamAPI_ISteamUGC_StartItemUpdate(ugc, self.app_id.0, file_id);", + " if handle == sys::k_UGCUpdateHandleInvalid {", + " return Err(SteamError::Api(\"Steam rejected the gallery update\".into()));", + " }", + " let mut attached = 0usize;", + " for file in &files {", + " let ok = sys::SteamAPI_ISteamUGC_AddItemPreviewFile(", + " ugc,", + " handle,", + " file.as_ptr(),", + " sys::EItemPreviewType::k_EItemPreviewType_Image,", + " );", + " if ok {", + " attached += 1;", + " } else {", + " log(\"Gallery attach rejected by Steam for one file.\");", + " }", + " }", + " if attached == 0 {", + " return Err(SteamError::Api(\"Steam attached no gallery files\".into()));", + " }", + " let note = CString::new(\"gallery\").expect(\"static cstring\");", + " let call = sys::SteamAPI_ISteamUGC_SubmitItemUpdate(ugc, handle, note.as_ptr());", + " if call == 0 {", + " return Err(SteamError::Api(\"gallery submit rejected\".into()));", + " }", + " let pipe = sys::SteamAPI_GetHSteamPipe();", + " let deadline = Instant::now() + Duration::from_secs(240);", + " loop {", + " if cancel.load(Ordering::Relaxed) {", + " return Err(SteamError::Cancelled);", + " }", + " self.client.run_callbacks();", + " let mut result: sys::SubmitItemUpdateResult_t = std::mem::zeroed();", + " let mut failed = false;", + " let ready = sys::SteamAPI_ManualDispatch_GetAPICallResult(", + " pipe,", + " call,", + " &mut result as *mut _ as *mut std::os::raw::c_void,", + " std::mem::size_of::() as std::os::raw::c_int,", + " sys::SubmitItemUpdateResult_t_k_iCallback as std::os::raw::c_int,", + " &mut failed,", + " );", + " if ready {", + " if failed {", + " return Err(SteamError::Api(", + " \"gallery submit failed (transport)\".into(),", + " ));", + " }", + " if result.m_eResult != sys::EResult::k_EResultOK {", + " return Err(SteamError::Api(format!(", + " \"gallery submit failed: {:?}\",", + " result.m_eResult", + " )));", + " }", + " // Packed FFI struct: unaligned read for the u64 field.", + " let returned_id =", + " std::ptr::addr_of!(result.m_nPublishedFileId).read_unaligned();", + " if returned_id != file_id {", + " return Err(SteamError::Api(format!(", + " \"gallery submit returned wrong item {returned_id}\"", + " )));", + " }", + " break attached;", + " }", + " if Instant::now() >= deadline {", + " return Err(SteamError::Timeout(", + " \"gallery submit produced no result\".into(),", + " ));", + " }", + " std::thread::sleep(Duration::from_millis(50));", + " }", + " };" + ], + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage", + "toolId": "Semgrep", + "line": 789, + "column": 13, + "endLine": 882, + "endColumn": 14, + "message": "Detected 'unsafe' usage, please audit for secure usage", + "lineContent": " unsafe {", + "multilineContent": [ + " unsafe {", + " let ugc = sys::SteamAPI_SteamUGC_v021();", + " if ugc.is_null() {", + " return Err(SteamError::Api(\"Steam UGC interface unavailable\".into()));", + " }", + " let mut id = file_id;", + " let handle =", + " sys::SteamAPI_ISteamUGC_CreateQueryUGCDetailsRequest(ugc, &mut id as *mut _, 1);", + " if handle == sys::k_UGCQueryHandleInvalid {", + " return Err(SteamError::Api(\"gallery query rejected\".into()));", + " }", + " let outcome: Result> = (|| {", + " if !sys::SteamAPI_ISteamUGC_SetReturnAdditionalPreviews(ugc, handle, true) {", + " return Err(SteamError::Api(\"gallery flag rejected\".into()));", + " }", + " let call = sys::SteamAPI_ISteamUGC_SendQueryUGCRequest(ugc, handle);", + " if call == 0 {", + " return Err(SteamError::Api(\"gallery query rejected\".into()));", + " }", + " let pipe = sys::SteamAPI_GetHSteamPipe();", + " let deadline = Instant::now() + Duration::from_secs(60);", + " loop {", + " if cancel.load(Ordering::Relaxed) {", + " return Err(SteamError::Cancelled);", + " }", + " self.client.run_callbacks();", + " let mut completed: sys::SteamUGCQueryCompleted_t = std::mem::zeroed();", + " let mut failed = false;", + " let ready = sys::SteamAPI_ManualDispatch_GetAPICallResult(", + " pipe,", + " call,", + " &mut completed as *mut _ as *mut std::os::raw::c_void,", + " std::mem::size_of::()", + " as std::os::raw::c_int,", + " sys::SteamUGCQueryCompleted_t_k_iCallback as std::os::raw::c_int,", + " &mut failed,", + " );", + " if ready {", + " if failed {", + " return Err(SteamError::Api(", + " \"gallery query failed (transport)\".into(),", + " ));", + " }", + " if completed.m_eResult != sys::EResult::k_EResultOK {", + " return Err(SteamError::Api(format!(", + " \"gallery query failed: {:?}\",", + " completed.m_eResult", + " )));", + " }", + " if completed.m_unNumResultsReturned < 1 {", + " return Err(SteamError::Api(format!(\"item {file_id} not found\")));", + " }", + " break;", + " }", + " if Instant::now() >= deadline {", + " return Err(SteamError::Timeout(", + " \"gallery query produced no result\".into(),", + " ));", + " }", + " std::thread::sleep(Duration::from_millis(50));", + " }", + " let count =", + " sys::SteamAPI_ISteamUGC_GetQueryUGCNumAdditionalPreviews(ugc, handle, 0);", + " let mut urls = Vec::new();", + " for index in 0..count {", + " let mut url_buf = [0 as c_char; 1024];", + " let mut name_buf = [0 as c_char; 256];", + " let mut preview_type = sys::EItemPreviewType::k_EItemPreviewType_Image;", + " let ok = sys::SteamAPI_ISteamUGC_GetQueryUGCAdditionalPreview(", + " ugc,", + " handle,", + " 0,", + " index,", + " url_buf.as_mut_ptr(),", + " url_buf.len() as u32,", + " name_buf.as_mut_ptr(),", + " name_buf.len() as u32,", + " &mut preview_type,", + " );", + " if !ok || preview_type != sys::EItemPreviewType::k_EItemPreviewType_Image {", + " continue;", + " }", + " let url = CStr::from_ptr(url_buf.as_ptr())", + " .to_string_lossy()", + " .into_owned();", + " if !url.trim().is_empty() {", + " urls.push(url);", + " }", + " }", + " Ok(urls)", + " })();", + " sys::SteamAPI_ISteamUGC_ReleaseQueryUGCRequest(ugc, handle);", + " outcome", + " }" + ], + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 683, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 835, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 864, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(\"greg-gallery-empty\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": "xtask/src/main.rs", + "patternId": "Semgrep_rust.lang.security.args.args", + "toolId": "Semgrep", + "line": 117, + "column": 20, + "endColumn": 36, + "message": "args should not be used for security operations.", + "lineContent": " let mut args = std::env::args().skip(1);", + "category": "Security", + "severity": "High" + }, + { + "filePath": "xtask/src/main.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 408, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let base = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Bandit_B404", + "toolId": "Bandit", + "line": 5, + "column": 1, + "endColumn": 18, + "message": "Consider possible security implications associated with the subprocess module. (CWE-78)", + "lineContent": "import subprocess", + "category": "Security", + "severity": "Info", + "confidence": 3 + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Bandit_B607", + "toolId": "Bandit", + "line": 39, + "column": 14, + "endLine": 46, + "endColumn": 6, + "message": "Starting a process with a partial executable path (CWE-78)", + "lineContent": " result = subprocess.run(", + "multilineContent": [ + " result = subprocess.run(", + " [\"git\", *args],", + " capture_output=True,", + " text=True,", + " encoding=\"utf-8\",", + " errors=\"replace\",", + " check=False,", + " )" + ], + "category": "Security", + "severity": "Warning", + "confidence": 3 + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Bandit_B603", + "toolId": "Bandit", + "line": 39, + "column": 14, + "endLine": 46, + "endColumn": 6, + "message": "subprocess call - check for execution of untrusted input. (CWE-78)", + "lineContent": " result = subprocess.run(", + "multilineContent": [ + " result = subprocess.run(", + " [\"git\", *args],", + " capture_output=True,", + " text=True,", + " encoding=\"utf-8\",", + " errors=\"replace\",", + " check=False,", + " )" + ], + "category": "Security", + "severity": "Warning", + "confidence": 3 + }, + { + "filePath": ".devcontainer/Dockerfile", + "patternId": "Checkov_CKV_DOCKER_2", + "toolId": "Checkov", + "line": 1, + "column": 1, + "endLine": 21, + "message": "Ensure that HEALTHCHECK instructions have been added to container images", + "lineContent": "# Avalonia desktop (net10 LTS): SDK 10 plus native X11/font/GL deps so the", + "multilineContent": [ + "# Avalonia desktop (net10 LTS): SDK 10 plus native X11/font/GL deps so the", + "# Modmanager builds and can at least smoke-run headless via xvfb.", + "FROM mcr.microsoft.com/dotnet/sdk:10.0-bookworm-slim", + "", + "ARG USERNAME=vscode", + "ARG USER_UID=1000", + "ARG USER_GID=1000", + "", + "RUN groupadd --gid \"$USER_GID\" \"$USERNAME\" \\", + " && useradd --uid \"$USER_UID\" --gid \"$USER_GID\" -m -s /bin/bash \"$USERNAME\" \\", + " && apt-get update \\", + " && apt-get install -y --no-install-recommends \\", + " git sudo xvfb \\", + " libice6 libsm6 libx11-6 libxkbcommon0 libfontconfig1 libfreetype6 \\", + " libgl1 libegl1 zlib1g dbus-x11 \\", + " && echo \"$USERNAME ALL=(root) NOPASSWD:ALL\" > \"/etc/sudoers.d/$USERNAME\" \\", + " && chmod 0440 \"/etc/sudoers.d/$USERNAME\" \\", + " && rm -rf /var/lib/apt/lists/*", + "", + "USER \"$USERNAME\"", + "RUN dotnet --list-sdks" + ], + "category": "BestPractice", + "severity": "Warning", + "suggestion": "https://docs.prismacloud.io/en/enterprise-edition/policy-reference/docker-policies/docker-policy-index/ensure-that-healthcheck-instructions-have-been-added-to-container-images" + }, + { + "filePath": "docker/Dockerfile", + "patternId": "Checkov_CKV_DOCKER_3", + "toolId": "Checkov", + "line": 1, + "column": 1, + "endLine": 54, + "message": "Ensure that a user for the container has been created", + "lineContent": "# syntax=docker/dockerfile:1.7", + "multilineContent": [ + "# syntax=docker/dockerfile:1.7", + "# Linux SDK container used for deterministic build/test and cross-RID publish.", + "FROM mcr.microsoft.com/dotnet/runtime:9.0-noble AS runtime9", + "", + "FROM mcr.microsoft.com/dotnet/sdk:10.0-noble AS restore", + "WORKDIR /src", + "", + "# The solution is built by SDK 10 (global.json) but testhost targets net10.0.", + "COPY --from=runtime9 /usr/share/dotnet/shared/Microsoft.NETCore.App/ /usr/share/dotnet/shared/Microsoft.NETCore.App/", + "", + "COPY global.json GregModmanager.sln ./", + "COPY src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj src/GregModmanager.Avalonia/", + "COPY src/GregModmanager.Core/GregModmanager.Core.csproj src/GregModmanager.Core/", + "COPY tests/GregModmanager.Tests/GregModmanager.Tests.csproj tests/GregModmanager.Tests/", + "", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet restore GregModmanager.sln", + "", + "FROM restore AS build", + "COPY . ./", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet build GregModmanager.sln --no-restore --configuration Release", + "", + "FROM build AS test", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet test GregModmanager.sln --no-build --configuration Release --verbosity normal", + "", + "# Cross-publish only: these Linux containers cannot execute Windows or macOS UI binaries.", + "FROM build AS publish-windows", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet publish src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj \\", + " --configuration Release --runtime win-x64 --self-contained true \\", + " --output /out/win-x64", + "", + "FROM scratch AS artifact-windows", + "COPY --from=publish-windows /out/ /", + "", + "FROM build AS publish-macos-x64", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet publish src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj \\", + " --configuration Release --runtime osx-x64 --self-contained true \\", + " --output /out/osx-x64", + "", + "FROM scratch AS artifact-macos-x64", + "COPY --from=publish-macos-x64 /out/ /", + "", + "FROM build AS publish-macos-arm64", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet publish src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj \\", + " --configuration Release --runtime osx-arm64 --self-contained true \\", + " --output /out/osx-arm64", + "", + "FROM scratch AS artifact-macos-arm64", + "COPY --from=publish-macos-arm64 /out/ /" + ], + "category": "Security", + "severity": "High", + "suggestion": "https://docs.prismacloud.io/en/enterprise-edition/policy-reference/docker-policies/docker-policy-index/ensure-that-a-user-for-the-container-has-been-created" + }, + { + "filePath": "docker/Dockerfile", + "patternId": "Checkov_CKV_DOCKER_2", + "toolId": "Checkov", + "line": 1, + "column": 1, + "endLine": 54, + "message": "Ensure that HEALTHCHECK instructions have been added to container images", + "lineContent": "# syntax=docker/dockerfile:1.7", + "multilineContent": [ + "# syntax=docker/dockerfile:1.7", + "# Linux SDK container used for deterministic build/test and cross-RID publish.", + "FROM mcr.microsoft.com/dotnet/runtime:9.0-noble AS runtime9", + "", + "FROM mcr.microsoft.com/dotnet/sdk:10.0-noble AS restore", + "WORKDIR /src", + "", + "# The solution is built by SDK 10 (global.json) but testhost targets net10.0.", + "COPY --from=runtime9 /usr/share/dotnet/shared/Microsoft.NETCore.App/ /usr/share/dotnet/shared/Microsoft.NETCore.App/", + "", + "COPY global.json GregModmanager.sln ./", + "COPY src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj src/GregModmanager.Avalonia/", + "COPY src/GregModmanager.Core/GregModmanager.Core.csproj src/GregModmanager.Core/", + "COPY tests/GregModmanager.Tests/GregModmanager.Tests.csproj tests/GregModmanager.Tests/", + "", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet restore GregModmanager.sln", + "", + "FROM restore AS build", + "COPY . ./", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet build GregModmanager.sln --no-restore --configuration Release", + "", + "FROM build AS test", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet test GregModmanager.sln --no-build --configuration Release --verbosity normal", + "", + "# Cross-publish only: these Linux containers cannot execute Windows or macOS UI binaries.", + "FROM build AS publish-windows", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet publish src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj \\", + " --configuration Release --runtime win-x64 --self-contained true \\", + " --output /out/win-x64", + "", + "FROM scratch AS artifact-windows", + "COPY --from=publish-windows /out/ /", + "", + "FROM build AS publish-macos-x64", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet publish src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj \\", + " --configuration Release --runtime osx-x64 --self-contained true \\", + " --output /out/osx-x64", + "", + "FROM scratch AS artifact-macos-x64", + "COPY --from=publish-macos-x64 /out/ /", + "", + "FROM build AS publish-macos-arm64", + "RUN --mount=type=cache,id=nuget,target=/root/.nuget/packages \\", + " dotnet publish src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj \\", + " --configuration Release --runtime osx-arm64 --self-contained true \\", + " --output /out/osx-arm64", + "", + "FROM scratch AS artifact-macos-arm64", + "COPY --from=publish-macos-arm64 /out/ /" + ], + "category": "BestPractice", + "severity": "Warning", + "suggestion": "https://docs.prismacloud.io/en/enterprise-edition/policy-reference/docker-policies/docker-policy-index/ensure-that-healthcheck-instructions-have-been-added-to-container-images" + }, + { + "filePath": ".devcontainer/Dockerfile", + "patternId": "Checkov_CKV2_DOCKER_1", + "toolId": "Checkov", + "line": 9, + "column": 1, + "endLine": 18, + "message": "Ensure that sudo isn't used", + "lineContent": "RUN groupadd --gid \"$USER_GID\" \"$USERNAME\" \\", + "multilineContent": [ + "RUN groupadd --gid \"$USER_GID\" \"$USERNAME\" \\", + " && useradd --uid \"$USER_UID\" --gid \"$USER_GID\" -m -s /bin/bash \"$USERNAME\" \\", + " && apt-get update \\", + " && apt-get install -y --no-install-recommends \\", + " git sudo xvfb \\", + " libice6 libsm6 libx11-6 libxkbcommon0 libfontconfig1 libfreetype6 \\", + " libgl1 libegl1 zlib1g dbus-x11 \\", + " && echo \"$USERNAME ALL=(root) NOPASSWD:ALL\" > \"/etc/sudoers.d/$USERNAME\" \\", + " && chmod 0440 \"/etc/sudoers.d/$USERNAME\" \\", + " && rm -rf /var/lib/apt/lists/*" + ], + "category": "Security", + "severity": "High", + "suggestion": "https://docs.prismacloud.io/en/enterprise-edition/policy-reference/docker-policies/docker-policy-index/ensure-docker-dont-use-sudo" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 66, + "column": 1, + "endLine": 149, + "message": "MainWindow::OnLoaded has a NLOC of 78 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Program.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 17, + "column": 1, + "endLine": 158, + "message": "Program::Main has a NLOC of 118 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Program.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 17, + "column": 1, + "endLine": 158, + "message": "Program::Main has a cyclomatic complexity of 26 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 443, + "column": 1, + "endLine": 479, + "message": "EditorPage::UpdateDocsHints has a cyclomatic complexity of 18 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 735, + "column": 1, + "endLine": 821, + "message": "EditorPage::OnAddScreenshot has a NLOC of 77 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1042, + "column": 1, + "endLine": 1109, + "message": "EditorPage::RunUploadFlowAsync has a NLOC of 61 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/Auth/AuthApiClient.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 37, + "column": 1, + "endLine": 89, + "message": "AuthApiClient::ExchangeCallbackCodeAsync has a cyclomatic complexity of 18 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/HeadlessRunner.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 16, + "column": 1, + "endLine": 94, + "message": "HeadlessRunner::TryHandle has a NLOC of 72 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/HeadlessRunner.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 202, + "column": 1, + "endLine": 278, + "message": "HeadlessRunner::RunPublishAsync has a NLOC of 62 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/KeepAChangelogParser.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 51, + "column": 1, + "endLine": 139, + "message": "ChangelogEntry::TryParseEntries has a NLOC of 75 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/MarkdownToSteamBbCode.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 38, + "column": 1, + "endLine": 318, + "message": "MarkdownToSteamBbCode::Convert has a NLOC of 228 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/MarkdownToSteamBbCode.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 38, + "column": 1, + "endLine": 318, + "message": "MarkdownToSteamBbCode::Convert has a cyclomatic complexity of 54 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/ModStoreUpdateService.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 49, + "column": 1, + "endLine": 113, + "message": "ModStoreUpdateService::InstallReleaseAsync has a cyclomatic complexity of 25 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamBbCodePreview.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 36, + "column": 1, + "endLine": 219, + "message": "SteamBbCodePreview::ParseContent has a NLOC of 173 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamBbCodePreview.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 36, + "column": 1, + "endLine": 219, + "message": "SteamBbCodePreview::ParseContent has a cyclomatic complexity of 41 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamModfixInstallerService.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 22, + "column": 1, + "endLine": 80, + "message": "SteamModfixInstallResult::EnsureCurrentAsync has a cyclomatic complexity of 17 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 33, + "column": 1, + "endLine": 125, + "message": "SteamWorkshopService::EnsureInitialized has a NLOC of 79 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 33, + "column": 1, + "endLine": 125, + "message": "SteamWorkshopService::EnsureInitialized has a cyclomatic complexity of 17 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 381, + "column": 1, + "endLine": 830, + "message": "SteamWorkshopService::PublishAsync has a NLOC of 363 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 381, + "column": 1, + "endLine": 830, + "message": "SteamWorkshopService::PublishAsync has a cyclomatic complexity of 128 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1189, + "column": 1, + "endLine": 1310, + "message": "SteamWorkshopService::ImportPublishedToWorkspaceAsync has a NLOC of 101 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 1189, + "column": 1, + "endLine": 1310, + "message": "SteamWorkshopService::ImportPublishedToWorkspaceAsync has a cyclomatic complexity of 25 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 1493, + "column": 1, + "endLine": 1509, + "message": "SteamWorkshopService::DetectImageExtension has a cyclomatic complexity of 22 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/UploadDependencyChecker.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 101, + "column": 1, + "endLine": 178, + "message": "UploadDependencyChecker::CheckMetadataFields has a NLOC of 76 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/UploadDependencyChecker.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 322, + "column": 1, + "endLine": 401, + "message": "UploadDependencyChecker::CheckProjectDocs has a NLOC of 76 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 387, + "column": 1, + "endLine": 506, + "message": "WorkspaceService::CreateSourceTemplates has a NLOC of 115 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 508, + "column": 1, + "endLine": 603, + "message": "WorkspaceService::BuildMetadataForTemplate has a NLOC of 94 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 605, + "column": 1, + "endLine": 669, + "message": "WorkspaceService::CreateVanillaObjectDecorationTemplate has a NLOC of 62 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 677, + "column": 1, + "endLine": 755, + "message": "WorkspaceService::CreateModdedGameMirrorLayout has a NLOC of 74 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1000, + "column": 1, + "endLine": 1075, + "message": "WorkspaceService::CreateUxmlTemplate has a NLOC of 69 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Steam/SteamApiNativeLoader.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 133, + "column": 1, + "endLine": 215, + "message": "SteamApiNativeLoader::EnumerateCandidatePaths has a NLOC of 76 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Steam/SteamApiNativeLoader.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 243, + "column": 1, + "endLine": 330, + "message": "SteamApiNativeLoader::EnumerateHeuristicGameRoots has a NLOC of 69 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 866, + "column": 1, + "endLine": 932, + "message": "push_editor has a NLOC of 67 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1101, + "column": 1, + "endLine": 1177, + "message": "editor_publish has a NLOC of 74 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1463, + "column": 1, + "endLine": 1558, + "message": "drain_browse has a NLOC of 96 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1747, + "column": 1, + "endLine": 1853, + "message": "drain_store has a NLOC of 105 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 2109, + "column": 1, + "endLine": 2254, + "message": "refresh_problems has a NLOC of 137 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 2316, + "column": 1, + "endLine": 2379, + "message": "packs_refresh has a NLOC of 63 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 2082, + "column": 1, + "endLine": 3068, + "message": "percent_encode_bug has a NLOC of 67 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 87, + "column": 1, + "endLine": 398, + "message": "wire has a NLOC of 300 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/main.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 87, + "column": 1, + "endLine": 398, + "message": "wire has a cyclomatic complexity of 50 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/shots.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 441, + "column": 1, + "endLine": 522, + "message": "project_sync_hashes_off_ui_thread has a NLOC of 76 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/state.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 136, + "column": 1, + "endLine": 279, + "message": "new has a NLOC of 133 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-cli/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 77, + "column": 1, + "endLine": 143, + "message": "run has a NLOC of 63 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-cli/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 275, + "column": 1, + "endLine": 346, + "message": "run_publish has a NLOC of 69 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/bbcode.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 10, + "column": 1, + "endLine": 243, + "message": "convert has a NLOC of 208 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/bbcode.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 10, + "column": 1, + "endLine": 243, + "message": "convert has a cyclomatic complexity of 47 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/bbcode.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 289, + "column": 1, + "endLine": 656, + "message": "is_horizontal_rule has a NLOC of 368 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/changelog.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 30, + "column": 1, + "endLine": 199, + "message": "normalize_version has a NLOC of 170 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 178, + "column": 1, + "endLine": 257, + "message": "check_project_docs has a NLOC of 79 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 368, + "column": 1, + "endLine": 494, + "message": "check_security_preflight has a NLOC of 121 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 368, + "column": 1, + "endLine": 494, + "message": "check_security_preflight has a cyclomatic complexity of 18 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/installers.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 101, + "column": 1, + "endLine": 243, + "message": "latest_github_asset has a NLOC of 143 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/installers.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 101, + "column": 1, + "endLine": 243, + "message": "latest_github_asset has a cyclomatic complexity of 18 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/packs.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 47, + "column": 1, + "endLine": 111, + "message": "apply_pack has a NLOC of 64 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/templates.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 15, + "column": 1, + "endLine": 56, + "message": "scaffold has a cyclomatic complexity of 16 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/templates.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 66, + "column": 1, + "endLine": 132, + "message": "metadata_for_template has a NLOC of 67 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-modstore/src/install.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 149, + "column": 1, + "endLine": 465, + "message": "install_release_inner has a NLOC of 292 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-platform/src/repro.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 13, + "column": 1, + "endLine": 77, + "message": "create_bundle has a cyclomatic complexity of 18 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 433, + "column": 1, + "endLine": 497, + "message": "page has a NLOC of 65 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 560, + "column": 1, + "endLine": 656, + "message": "submit has a NLOC of 97 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 560, + "column": 1, + "endLine": 656, + "message": "submit has a cyclomatic complexity of 17 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 670, + "column": 1, + "endLine": 773, + "message": "upload_gallery has a NLOC of 102 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 670, + "column": 1, + "endLine": 773, + "message": "upload_gallery has a cyclomatic complexity of 17 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 780, + "column": 1, + "endLine": 883, + "message": "additional_preview_urls has a NLOC of 103 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 780, + "column": 1, + "endLine": 883, + "message": "additional_preview_urls has a cyclomatic complexity of 16 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 99, + "column": 1, + "endLine": 239, + "message": "publish_inner has a NLOC of 131 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 99, + "column": 1, + "endLine": 239, + "message": "publish_inner has a cyclomatic complexity of 21 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 457, + "column": 1, + "endLine": 519, + "message": "import_to_workspace has a NLOC of 63 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "xtask/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 218, + "column": 1, + "endLine": 293, + "message": "dist has a NLOC of 68 (threshold: 60)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "xtask/src/main.rs", + "patternId": "Lizard_ccn-medium", + "toolId": "Lizard", + "line": 218, + "column": 1, + "endLine": 293, + "message": "dist has a cyclomatic complexity of 28 (threshold: 15)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 945 lines of code (threshold: 750)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 1227 lines of code (threshold: 750)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 954 lines of code (threshold: 750)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_file-nloc-critical", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 2893 lines of code (threshold: 2890)", + "lineContent": "", + "category": "Complexity", + "severity": "Error" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 818 lines of code (threshold: 750)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 774 lines of code (threshold: 750)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_no-vague-instructions", + "toolId": "Agentlinter", + "line": 14, + "column": 1, + "message": "Vague instruction: \"- Always use Orchestration of several Agents if possible to...\"", + "lineContent": "- Always use Orchestration of several Agents if possible to", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_has-examples", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No examples found. Adding examples (code blocks, sample outputs) helps the agent understand expectations.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_naked-conditional", + "toolId": "Agentlinter", + "line": 57, + "column": 1, + "message": "Vague conditional: \"- Preserve binary-size settings unless a measured, reviewed change requires othe\". Specify exact threshold or trigger.", + "lineContent": "- Preserve binary-size settings unless a measured, reviewed change requires otherwise.", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_compound-instruction", + "toolId": "Agentlinter", + "line": 34, + "column": 1, + "message": "Compound instruction with 3 actions in one bullet. Split into separate items.", + "lineContent": "- Work on a feature branch and open a pull request to `main`; do not push directly to `main` unless the maintainer explicitly requests it.", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_compound-instruction", + "toolId": "Agentlinter", + "line": 69, + "column": 1, + "message": "Compound instruction with 4 actions in one bullet. Split into separate items.", + "lineContent": "- Run the most relevant check available: `cargo fmt --check`, `cargo clippy -- -D warnings`, `cargo test`.", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "toolId": "Agentlinter", + "line": 12, + "column": 1, + "message": "Absolute rule without escape hatch: \"- MelonLoader plugins (`SubDirectoryFixer`, `gregPlugin.ModmanagerComp\"", + "lineContent": "- MelonLoader plugins (`SubDirectoryFixer`, `gregPlugin.ModmanagerCompanion`) stay .NET 6 — they load inside MelonLoader and are never rewritten in Rust. Frozen sources: `./.reference/modmanager-old/src/GregModmanager.Melons/`. If the Rust app must build them, shell out to the `dotnet` CLI via `xtask`.", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "toolId": "Agentlinter", + "line": 14, + "column": 1, + "message": "Absolute rule without escape hatch: \"- Always use Orchestration of several Agents if possible to\"", + "lineContent": "- Always use Orchestration of several Agents if possible to", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "toolId": "Agentlinter", + "line": 42, + "column": 1, + "message": "Absolute rule without escape hatch: \"- `greg-core` must not depend on UI crates (`slint`). If a required fi\"", + "lineContent": "- `greg-core` must not depend on UI crates (`slint`). If a required fix appears to need that dependency, stop and ask for maintainer confirmation.", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_sentence-complexity", + "toolId": "Agentlinter", + "line": 56, + "column": 1, + "message": "Overly complex sentence (51 words). Break into shorter instructions.", + "lineContent": "- Keep `xtask` commands and CI workflows aligned unless a PR intentionally stages a migration and explains the temporary divergence. `.forgejo/workflows/` (Forgejo Actions) and `.gitea/workflows/` (Gitea Actions) must stay byte-identical — the `parity` job fails the run on drift. GitHub is a read-only archive mirror — no CI lives in `.github/`.", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_undefined-term", + "toolId": "Agentlinter", + "line": 12, + "column": 1, + "message": "Undefined acronym \"NET\" — define on first use or add to glossary.", + "lineContent": "- MelonLoader plugins (`SubDirectoryFixer`, `gregPlugin.ModmanagerCompanion`) stay .NET 6 — they load inside MelonLoader and are never rewritten in Rust. Frozen sources: `./.reference/modmanager-old/src/GregModmanager.Melons/`. If the Rust app must build them, shell out to the `dotnet` CLI via `xtask`.", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_undefined-term", + "toolId": "Agentlinter", + "line": 27, + "column": 1, + "message": "Undefined acronym \"MSRV\" — define on first use or add to glossary.", + "lineContent": "- Target language: latest stable Rust (rustup toolchain); MSRV is \"latest stable\" unless the maintainer pins one.", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_consistency_referenced-files-exist", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Referenced file \"RUST_GRAPH.md\" not found in workspace.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "ErrorProne", + "severity": "High" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_consistency_referenced-files-exist", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Referenced file \"EXTERNAL_DEPENDENCIES.md\" not found in workspace.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "ErrorProne", + "severity": "High" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_consistency_outdated-cross-references", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Referenced section \"RUST_GRAPH.md\" not found in any file.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "TOOLS.md", + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "toolId": "Agentlinter", + "line": 30, + "column": 1, + "message": "Absolute rule without escape hatch: \"- Telemetry must respect `AppSettings.TelemetryEnabled`.\"", + "lineContent": "- Telemetry must respect `AppSettings.TelemetryEnabled`.", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "TOOLS.md", + "patternId": "Agentlinter_clarity_undefined-term", + "toolId": "Agentlinter", + "line": 37, + "column": 1, + "message": "Undefined acronym \"LCOV\" — define on first use or add to glossary.", + "lineContent": " als workspace-weites LCOV-Report erzeugt und über den", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "TOOLS.md", + "patternId": "Agentlinter_consistency_referenced-files-exist", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Referenced file \"EXTERNAL_DEPENDENCIES.md\" not found in workspace.", + "lineContent": "# TOOLS.md — Build, CI, and Operations", + "category": "ErrorProne", + "severity": "High" + }, + { + "filePath": "SOUL.md", + "patternId": "Agentlinter_clarity_priority-signal-missing", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "10 instruction items with no priority signals. The agent can't distinguish critical from optional.", + "lineContent": "# SOUL.md — Collaboration Defaults", + "category": "Documentation", + "severity": "Info" + }, + { + "filePath": "USER.md", + "patternId": "Agentlinter_clarity_priority-signal-missing", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "20 instruction items with no priority signals. The agent can't distinguish critical from optional.", + "lineContent": "# USER.md — Project Context", + "category": "Documentation", + "severity": "Info" + }, + { + "filePath": "USER.md", + "patternId": "Agentlinter_clarity_undefined-term", + "toolId": "Agentlinter", + "line": 8, + "column": 1, + "message": "Undefined acronym \"NET\" — define on first use or add to glossary.", + "lineContent": "- Desktop target: .NET 9.", + "category": "Comprehensibility", + "severity": "Info" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-memory-strategy", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No memory strategy defined. The agent will lose all context between sessions.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-file-based-notes", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No file-based memory system (daily notes, logs). Consider structured note-taking for long-term knowledge.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_no-mental-notes", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Memory strategy exists but missing explicit 'write it down' principle. Mental notes don't survive restarts.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-context-window-awareness", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No context window awareness. The agent should know how to handle long conversations and context overflow.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-state-tracking", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No task/state tracking mechanism. The agent can't resume work from where it left off.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-learning-loop", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No learning loop defined. The agent doesn't know how to improve over time from past interactions.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_runtime_config-exists", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No runtime config (clawdbot.json / openclaw.json) found. Runtime checks skipped.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Prospector_bandit", + "toolId": "Prospector", + "line": 5, + "column": 1, + "endColumn": 18, + "message": "Consider possible security implications associated with the subprocess module. (B404)", + "lineContent": "import subprocess", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Prospector_bandit", + "toolId": "Prospector", + "line": 39, + "column": 14, + "endLine": 46, + "endColumn": 6, + "message": "subprocess call - check for execution of untrusted input. (B603)", + "lineContent": " result = subprocess.run(", + "multilineContent": [ + " result = subprocess.run(", + " [\"git\", *args],", + " capture_output=True,", + " text=True,", + " encoding=\"utf-8\",", + " errors=\"replace\",", + " check=False,", + " )" + ], + "category": "Security", + "severity": "High" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Prospector_bandit", + "toolId": "Prospector", + "line": 39, + "column": 14, + "endLine": 46, + "endColumn": 6, + "message": "Starting a process with a partial executable path (B607)", + "lineContent": " result = subprocess.run(", + "multilineContent": [ + " result = subprocess.run(", + " [\"git\", *args],", + " capture_output=True,", + " text=True,", + " encoding=\"utf-8\",", + " errors=\"replace\",", + " check=False,", + " )" + ], + "category": "Security", + "severity": "High" + } + ], + "errors": [ + { + "toolId": "Trivy", + "phase": "toolInvoke", + "kind": "NetworkError", + "message": "OSV.dev API call failed: OSV API returned HTTP 400: Bad Request. Malicious package detection skipped.", + "level": "warning" + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `$` was unexpected", + "level": "warning", + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `$` was unexpected", + "level": "warning", + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/HeadlessRunner.cs", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `] { handleObj, (uint)0, j, null, null, imagePreviewTypeValue…` was unexpected", + "level": "warning", + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Steam/SteamUgcPreviews.cs", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `USER \"$USERNAME\" RUN dotnet --list-sdks` was unexpected", + "level": "warning", + "filePath": ".devcontainer/Dockerfile", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `namespace SubDirectoryFixer;` was unexpected", + "level": "warning", + "filePath": ".reference/modmanager-old/src/GregModmanager.Melons/SubDirectoryFixer/SubDirectoryFixerPlugin.cs", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "Syntax error", + "message": "Syntax error missing element", + "level": "warning", + "filePath": "docs/examples/manifests/07_steam_manifest.json", + "fileNotAnalyzed": true + } + ], + "toolResults": [ + { + "toolId": "jackson", + "status": "success", + "issueCount": 1, + "errorCount": 0, + "durationMs": 40, + "filesAnalyzed": 16 + }, + { + "toolId": "markdownlint", + "status": "success", + "issueCount": 59, + "errorCount": 0, + "durationMs": 596, + "filesAnalyzed": 49 + }, + { + "toolId": "shellcheck", + "status": "success", + "issueCount": 3, + "errorCount": 0, + "durationMs": 367, + "filesAnalyzed": 12 + }, + { + "toolId": "Hadolint", + "status": "success", + "issueCount": 2, + "errorCount": 0, + "durationMs": 60, + "filesAnalyzed": 3 + }, + { + "toolId": "Ruff", + "status": "success", + "issueCount": 28, + "errorCount": 0, + "durationMs": 54, + "filesAnalyzed": 2 + }, + { + "toolId": "Trivy", + "status": "success", + "issueCount": 4, + "errorCount": 1, + "durationMs": 65858, + "filesAnalyzed": 371 + }, + { + "toolId": "Semgrep", + "status": "success", + "issueCount": 79, + "errorCount": 6, + "durationMs": 15568, + "filesAnalyzed": 238 + }, + { + "toolId": "spectral", + "status": "success", + "issueCount": 0, + "errorCount": 0, + "durationMs": 384, + "filesAnalyzed": 35 + }, + { + "toolId": "Bandit", + "status": "success", + "issueCount": 3, + "errorCount": 0, + "durationMs": 143, + "filesAnalyzed": 2 + }, + { + "toolId": "PyLintPython3", + "status": "success", + "issueCount": 0, + "errorCount": 0, + "durationMs": 1578, + "filesAnalyzed": 2 + }, + { + "toolId": "Checkov", + "status": "success", + "issueCount": 4, + "errorCount": 0, + "durationMs": 3545, + "filesAnalyzed": 37 + }, + { + "toolId": "Lizard", + "status": "success", + "issueCount": 77, + "errorCount": 0, + "durationMs": 633, + "filesAnalyzed": 187 + }, + { + "toolId": "PMD7", + "status": "success", + "issueCount": 0, + "errorCount": 0, + "durationMs": 792, + "filesAnalyzed": 1 + }, + { + "toolId": "Agentlinter", + "status": "success", + "issueCount": 27, + "errorCount": 0, + "durationMs": 1305, + "filesAnalyzed": 4 + }, + { + "toolId": "Prospector", + "status": "success", + "issueCount": 3, + "errorCount": 0, + "durationMs": 588, + "filesAnalyzed": 2 + } + ], + "patternSummary": { + "groups": [ + { + "severity": "Error", + "severityLabel": "CRITICAL", + "category": "Security", + "categoryLabel": "Security", + "patterns": [ + { + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "title": "Avoid OS Command Injection", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "Error", + "issueCount": 7, + "fileCount": 4, + "noisy": false + } + ], + "totalIssues": 7, + "totalPatterns": 1 + }, + { + "severity": "Error", + "severityLabel": "CRITICAL", + "category": "ErrorProne", + "categoryLabel": "Error Prone", + "patterns": [ + { + "patternId": "jackson_parse-error", + "title": "Prohibit Invalid JSON Files", + "toolId": "jackson", + "toolDisplayName": "Jackson Linter", + "category": "ErrorProne", + "severity": "Error", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 1, + "totalPatterns": 1 + }, + { + "severity": "Error", + "severityLabel": "CRITICAL", + "category": "Complexity", + "categoryLabel": "Complexity", + "patterns": [ + { + "patternId": "Lizard_file-nloc-critical", + "title": "Limit File Length (Critical)", + "toolId": "Lizard", + "toolDisplayName": "Lizard", + "category": "Complexity", + "severity": "Error", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 1, + "totalPatterns": 1 + }, + { + "severity": "High", + "severityLabel": "HIGH", + "category": "Security", + "categoryLabel": "Security", + "patterns": [ + { + "patternId": "Semgrep_csharp.lang.best-practice.structured-logging.structured-logging", + "title": "Enforce Structured Logging Instead of String Interpolation", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 31, + "fileCount": 10, + "noisy": false + }, + { + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "title": "Avoid Using temp_dir for Security Operations", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 25, + "fileCount": 18, + "noisy": false + }, + { + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "title": "Avoid Unsafe Path.Combine Usage Without Sanitization", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 7, + "fileCount": 3, + "noisy": false + }, + { + "patternId": "Semgrep_rust.lang.security.args.args", + "title": "Avoid Using args for Security Operations", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 4, + "fileCount": 3, + "noisy": false + }, + { + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe", + "title": "Avoid Using current_exe for Security Operations", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 3, + "fileCount": 3, + "noisy": false + }, + { + "patternId": "Prospector_bandit", + "title": "Detect Common Security Issues in Python Code", + "toolId": "Prospector", + "toolDisplayName": "Prospector", + "category": "Security", + "severity": "High", + "issueCount": 3, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage", + "title": "Avoid Unsafe Usage", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 2, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Ruff_S603_subprocess-without-shell-equals-true", + "title": "Avoid subprocess calls without shell=True", + "toolId": "Ruff", + "toolDisplayName": "Ruff", + "category": "Security", + "severity": "High", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Ruff_S607_start-process-with-partial-path", + "title": "Avoid Starting Process With Partial Executable Path", + "toolId": "Ruff", + "toolDisplayName": "Ruff", + "category": "Security", + "severity": "High", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Checkov_CKV_DOCKER_3", + "title": "Ensure Container User Is Created", + "toolId": "Checkov", + "toolDisplayName": "Checkov", + "category": "Security", + "severity": "High", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Checkov_CKV2_DOCKER_1", + "title": "Avoid Using sudo in Docker Configurations", + "toolId": "Checkov", + "toolDisplayName": "Checkov", + "category": "Security", + "severity": "High", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 79, + "totalPatterns": 11 + }, + { + "severity": "High", + "severityLabel": "HIGH", + "category": "ErrorProne", + "categoryLabel": "Error Prone", + "patterns": [ + { + "patternId": "Agentlinter_consistency_referenced-files-exist", + "title": "Ensure referenced files exist", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "ErrorProne", + "severity": "High", + "issueCount": 3, + "fileCount": 2, + "noisy": false + } + ], + "totalIssues": 3, + "totalPatterns": 1 + }, + { + "severity": "Warning", + "severityLabel": "WARNING", + "category": "Security", + "categoryLabel": "Security", + "patterns": [ + { + "patternId": "Trivy_vulnerability_medium", + "title": "Detect Insecure Dependencies (Medium Severity)", + "toolId": "Trivy", + "toolDisplayName": "Trivy", + "category": "Security", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Bandit_B607", + "title": "Avoid starting a process with a partial executable path", + "toolId": "Bandit", + "toolDisplayName": "Bandit", + "category": "Security", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Bandit_B603", + "title": "Check subprocess usage without shell=True", + "toolId": "Bandit", + "toolDisplayName": "Bandit", + "category": "Security", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 3, + "totalPatterns": 3 + }, + { + "severity": "Warning", + "severityLabel": "WARNING", + "category": "ErrorProne", + "categoryLabel": "Error Prone", + "patterns": [ + { + "patternId": "shellcheck_SC2029", + "title": "Avoid Unescaped Client-Side Expansion in SSH Commands", + "toolId": "shellcheck", + "toolDisplayName": "ShellCheck", + "category": "ErrorProne", + "severity": "Warning", + "issueCount": 2, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "shellcheck_SC2034", + "title": "Avoid Unused Variables", + "toolId": "shellcheck", + "toolDisplayName": "ShellCheck", + "category": "ErrorProne", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 3, + "totalPatterns": 2 + }, + { + "severity": "Warning", + "severityLabel": "WARNING", + "category": "BestPractice", + "categoryLabel": "Best Practice", + "patterns": [ + { + "patternId": "markdownlint_MD024", + "title": "Avoid Multiple Headings with the Same Content", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 25, + "fileCount": 2, + "noisy": false + }, + { + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "title": "Require escape hatch for absolute rules", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 4, + "fileCount": 2, + "noisy": false + }, + { + "patternId": "Checkov_CKV_DOCKER_2", + "title": "Ensure HEALTHCHECK Instructions Are Added to Container Images", + "toolId": "Checkov", + "toolDisplayName": "Checkov", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 2, + "fileCount": 2, + "noisy": false + }, + { + "patternId": "Hadolint_DL3008", + "title": "Enforce Pinning Versions in apt-get install", + "toolId": "Hadolint", + "toolDisplayName": "Hadolint", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_clarity_naked-conditional", + "title": "Avoid naked conditionals — require specific, measurable triggers", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-memory-strategy", + "title": "Require explicit memory/continuity strategy", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-file-based-notes", + "title": "Require file-based notes for persistent memory", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_no-mental-notes", + "title": "Avoid relying on mental notes; write things down", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-context-window-awareness", + "title": "Ensure agent is aware of context window limitations", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-state-tracking", + "title": "Ensure agent tracks current task state", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-learning-loop", + "title": "Ensure agent learns from past interactions", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_runtime_config-exists", + "title": "Require agent runtime config file", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 40, + "totalPatterns": 12 + }, + { + "severity": "Warning", + "severityLabel": "WARNING", + "category": "Complexity", + "categoryLabel": "Complexity", + "patterns": [ + { + "patternId": "Lizard_nloc-medium", + "title": "Limit Function Length (Medium)", + "toolId": "Lizard", + "toolDisplayName": "Lizard", + "category": "Complexity", + "severity": "Warning", + "issueCount": 49, + "fileCount": 26, + "noisy": false + }, + { + "patternId": "Lizard_ccn-medium", + "title": "Limit Function Cyclomatic Complexity (Medium)", + "toolId": "Lizard", + "toolDisplayName": "Lizard", + "category": "Complexity", + "severity": "Warning", + "issueCount": 22, + "fileCount": 17, + "noisy": false + }, + { + "patternId": "Lizard_file-nloc-medium", + "title": "Limit File Length (Medium)", + "toolId": "Lizard", + "toolDisplayName": "Lizard", + "category": "Complexity", + "severity": "Warning", + "issueCount": 5, + "fileCount": 5, + "noisy": false + } + ], + "totalIssues": 76, + "totalPatterns": 3 + }, + { + "severity": "Info", + "severityLabel": "MINOR", + "category": "Security", + "categoryLabel": "Security", + "patterns": [ + { + "patternId": "Trivy_vulnerability_minor", + "title": "Detect Insecure Dependencies (Minor Severity)", + "toolId": "Trivy", + "toolDisplayName": "Trivy", + "category": "Security", + "severity": "Info", + "issueCount": 3, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Bandit_B404", + "title": "Consider security implications of importing subprocess module", + "toolId": "Bandit", + "toolDisplayName": "Bandit", + "category": "Security", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 4, + "totalPatterns": 2 + }, + { + "severity": "Info", + "severityLabel": "MINOR", + "category": "BestPractice", + "categoryLabel": "Best Practice", + "patterns": [ + { + "patternId": "markdownlint_MD025", + "title": "Enforce Single Top-Level Heading in Markdown Document", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "BestPractice", + "severity": "Info", + "issueCount": 11, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "markdownlint_MD001", + "title": "Enforce Incremental Heading Levels", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "BestPractice", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "markdownlint_MD033", + "title": "Disallow Inline HTML in Markdown", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "BestPractice", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Hadolint_SC1001", + "title": "Avoid Unnecessary Escape Sequences in Shell Scripts", + "toolId": "Hadolint", + "toolDisplayName": "Hadolint", + "category": "BestPractice", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 14, + "totalPatterns": 4 + }, + { + "severity": "Info", + "severityLabel": "MINOR", + "category": "Comprehensibility", + "categoryLabel": "Comprehensibility", + "patterns": [ + { + "patternId": "Agentlinter_clarity_undefined-term", + "title": "Define acronyms and jargon on first use", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "Comprehensibility", + "severity": "Info", + "issueCount": 4, + "fileCount": 3, + "noisy": false + }, + { + "patternId": "Agentlinter_clarity_compound-instruction", + "title": "Avoid compound instructions in bullet points", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "Comprehensibility", + "severity": "Info", + "issueCount": 2, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "markdownlint_MD028", + "title": "Avoid Blank Line Inside Blockquote", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "Comprehensibility", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_clarity_no-vague-instructions", + "title": "Avoid vague instructions; require specific, actionable guidance", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "Comprehensibility", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_clarity_has-examples", + "title": "Require examples in documentation", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "Comprehensibility", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_clarity_sentence-complexity", + "title": "Keep instructions short and simple", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "Comprehensibility", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_consistency_outdated-cross-references", + "title": "Ensure section references point to existing sections", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "Comprehensibility", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 11, + "totalPatterns": 7 + }, + { + "severity": "Info", + "severityLabel": "MINOR", + "category": "CodeStyle", + "categoryLabel": "Code Style", + "patterns": [ + { + "patternId": "Ruff_E501_line-too-long", + "title": "Enforce Line Length Limit", + "toolId": "Ruff", + "toolDisplayName": "Ruff", + "category": "CodeStyle", + "severity": "Info", + "issueCount": 26, + "fileCount": 2, + "noisy": false + }, + { + "patternId": "markdownlint_MD022", + "title": "Enforce Headings Surrounded by Blank Lines", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "CodeStyle", + "severity": "Info", + "issueCount": 10, + "fileCount": 4, + "noisy": false + }, + { + "patternId": "markdownlint_MD032", + "title": "Enforce Lists Surrounded by Blank Lines", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "CodeStyle", + "severity": "Info", + "issueCount": 7, + "fileCount": 3, + "noisy": false + }, + { + "patternId": "markdownlint_MD026", + "title": "Avoid Trailing Punctuation in Headings", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "CodeStyle", + "severity": "Info", + "issueCount": 2, + "fileCount": 2, + "noisy": false + }, + { + "patternId": "markdownlint_MD012", + "title": "Disallow Multiple Consecutive Blank Lines", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "CodeStyle", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 46, + "totalPatterns": 5 + }, + { + "severity": "Info", + "severityLabel": "MINOR", + "category": "Documentation", + "categoryLabel": "Documentation", + "patterns": [ + { + "patternId": "Agentlinter_clarity_priority-signal-missing", + "title": "Require explicit priority signals in rule-heavy files", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "Documentation", + "severity": "Info", + "issueCount": 2, + "fileCount": 2, + "noisy": false + } + ], + "totalIssues": 2, + "totalPatterns": 1 + } + ], + "totalIssues": 290, + "totalPatterns": 54, + "noisyPatternCount": 0, + "noisyThreshold": 500 + }, + "skippedFiles": [ + { + "filePath": ".codacy/tmp/codacy-remote-config.json", + "sizeBytes": 220518 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Resources/Fonts/Vendored/JetBrainsMono/JetBrainsMono-Bold.ttf", + "sizeBytes": 274098 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Resources/Fonts/Vendored/JetBrainsMono/JetBrainsMono-Medium.ttf", + "sizeBytes": 270318 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Resources/Fonts/Vendored/JetBrainsMono/JetBrainsMono-Regular.ttf", + "sizeBytes": 270226 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/libsteam_api.so", + "sizeBytes": 386864 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/libsteam_api64.so", + "sizeBytes": 386864 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/steam_api64.dll", + "sizeBytes": 262946 + } + ] +} \ No newline at end of file diff --git a/.codacy/tmp/codacy-cloud-overview.err b/.codacy/tmp/codacy-cloud-overview.err new file mode 100644 index 0000000..e7e7a9f --- /dev/null +++ b/.codacy/tmp/codacy-cloud-overview.err @@ -0,0 +1 @@ +Error: Could not determine provider from git remote URL 'ssh://***@git.datacentermods.com:22222/teamGreg/gregModmanager.git'. Supported providers: github.com (gh), gitlab.com (gl), bitbucket.org (bb). diff --git a/.codacy/tmp/codacy-cloud-overview.json b/.codacy/tmp/codacy-cloud-overview.json new file mode 100644 index 0000000..718c048 --- /dev/null +++ b/.codacy/tmp/codacy-cloud-overview.json @@ -0,0 +1,243 @@ +{ + "overview": { + "categories": [ + { + "name": "BestPractice", + "total": 48 + }, + { + "name": "Performance", + "total": 1 + }, + { + "name": "Security", + "total": 73 + }, + { + "name": "ErrorProne", + "total": 14 + }, + { + "name": "Complexity", + "total": 90 + } + ], + "levels": [ + { + "name": "High", + "total": 73 + }, + { + "name": "Warning", + "total": 141 + }, + { + "name": "Error", + "total": 12 + } + ], + "languages": [ + { + "name": "CSharp", + "total": 91 + }, + { + "name": "Dockerfile", + "total": 1 + }, + { + "name": "Shell", + "total": 12 + }, + { + "name": "Rust", + "total": 85 + }, + { + "name": "Markdown", + "total": 20 + }, + { + "name": "YAML", + "total": 17 + } + ], + "tags": [ + { + "name": "readability", + "total": 1 + }, + { + "name": "security", + "total": 24 + }, + { + "name": "clarity", + "total": 1 + }, + { + "name": "documentation", + "total": 1 + }, + { + "name": "headings", + "total": 8 + }, + { + "name": "fwk:github-actions", + "total": 17 + }, + { + "name": "filesystem", + "total": 7 + } + ], + "patterns": [ + { + "id": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "title": "Avoid Shell Injection in GitHub Actions run Steps", + "total": 2 + }, + { + "id": "shellcheck_SC2034", + "title": "Avoid Unused Variables", + "total": 1 + }, + { + "id": "SonarCSharp_S2760", + "title": "Avoid Sequential Tests Checking the Same Condition", + "total": 1 + }, + { + "id": "Semgrep_rust.lang.security.args.args", + "title": "Avoid Using args for Security Operations", + "total": 3 + }, + { + "id": "shellcheck_SC2086", + "title": "Enforce Double Quoting to Prevent Globbing and Word Splitting", + "total": 2 + }, + { + "id": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage", + "title": "Avoid Unsafe Usage", + "total": 2 + }, + { + "id": "Agentlinter_clarity_naked-conditional", + "title": "Avoid naked conditionals — require specific, measurable triggers", + "total": 1 + }, + { + "id": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "title": "Avoid Unsafe Path.Combine Usage Without Sanitization", + "total": 7 + }, + { + "id": "Semgrep_rust.lang.security.current-exe.current-exe", + "title": "Avoid Using current_exe for Security Operations", + "total": 3 + }, + { + "id": "Lizard_nloc-medium", + "title": "Limit Function Length (Medium)", + "total": 79 + }, + { + "id": "Agentlinter_consistency_referenced-files-exist", + "title": "Ensure referenced files exist", + "total": 3 + }, + { + "id": "SonarCSharp_S3898", + "title": "Implement IEquatable on Value Types", + "total": 1 + }, + { + "id": "SonarCSharp_S2339", + "title": "Avoid Using Public Constant Members", + "total": 6 + }, + { + "id": "Hadolint_DL3008", + "title": "Enforce Pinning Versions in apt-get install", + "total": 1 + }, + { + "id": "shellcheck_SC2015", + "title": "Avoid Using `A && B || C` as if-Then-Else", + "total": 9 + }, + { + "id": "SonarCSharp_S2486", + "title": "Avoid Ignoring Generic Exceptions", + "total": 9 + }, + { + "id": "SonarCSharp_S6444", + "title": "Specify a timeout for regular expressions", + "total": 4 + }, + { + "id": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "title": "Enforce Pinning of Third-Party GitHub Actions to Full Commit SHA", + "total": 15 + }, + { + "id": "markdownlint_MD024", + "title": "Avoid Multiple Headings with the Same Content", + "total": 8 + }, + { + "id": "SonarCSharp_S2360", + "title": "Avoid Using Optional Parameters", + "total": 20 + }, + { + "id": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "title": "Avoid Using temp_dir for Security Operations", + "total": 22 + }, + { + "id": "SonarCSharp_S1172", + "title": "Remove Unused Method Parameters", + "total": 2 + }, + { + "id": "Lizard_file-nloc-medium", + "title": "Limit File Length (Medium)", + "total": 11 + }, + { + "id": "Semgrep_csharp_injection_rule-CommandInjection", + "title": "Avoid OS Command Injection", + "total": 6 + }, + { + "id": "Agentlinter_clarity_escape-hatch-missing", + "title": "Require escape hatch for absolute rules", + "total": 8 + } + ], + "authors": [ + { + "name": "marvinleede@gmail.com", + "total": 181 + }, + { + "name": "52848568+mleem97@users.noreply.github.com", + "total": 14 + } + ], + "potentialFalsePositives": [ + { + "name": "equalOrAboveThreshold", + "total": 0 + }, + { + "name": "belowThreshold", + "total": 226 + } + ] + } +} diff --git a/.codacy/tmp/codacy-discover.json b/.codacy/tmp/codacy-discover.json new file mode 100644 index 0000000..76409cf --- /dev/null +++ b/.codacy/tmp/codacy-discover.json @@ -0,0 +1,89 @@ +{ + "filePatterns": [ + "*.axaml", + "*.cs", + "*.csproj", + "*.csx", + "*.desktop", + "*.dll", + "*.hcl", + "*.iss", + "*.json", + "*.lock", + "*.log", + "*.manifest", + "*.md", + "*.ps1", + "*.py", + "*.resx", + "*.rs", + "*.sh", + "*.slint", + "*.sln", + "*.so", + "*.svg", + "*.toml", + "*.ttf", + "*.txt", + "*.windows", + "*.wxs", + "*.xml", + "*.yaml", + "*.yml" + ], + "notableFiles": [ + ".devcontainer/Dockerfile", + ".dockerignore", + ".reference/modmanager-old/GregModmanager.sln", + ".reference/modmanager-old/src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj", + ".reference/modmanager-old/src/GregModmanager.Core/GregModmanager.Core.csproj", + ".reference/modmanager-old/src/GregModmanager.Melons/SubDirectoryFixer/SubDirectoryFixer.csproj", + ".reference/modmanager-old/tests/GregModmanager.Tests/GregModmanager.Tests.csproj", + "AGENTS.md", + "CHANGELOG.md", + "CONTRIBUTING.md", + "Cargo.lock", + "Cargo.toml", + "LICENSE", + "README.md", + "crates/greg-app/Cargo.toml", + "crates/greg-cli/Cargo.toml", + "crates/greg-core/Cargo.toml", + "crates/greg-loader/Cargo.toml", + "crates/greg-modstore/Cargo.toml", + "crates/greg-platform/Cargo.toml", + "crates/greg-steam/Cargo.toml", + "docker/Dockerfile", + "xtask/Cargo.toml" + ], + "languages": [ + "CSharp", + "Dockerfile", + "JSON", + "Markdown", + "Powershell", + "Python", + "Rust", + "Shell", + "XML", + "YAML" + ], + "frameworks": [], + "libraries": [ + { + "name": "xunit", + "key": "xunit", + "displayName": "xUnit", + "kind": "library", + "source": "manifest", + "manifestFile": ".reference/modmanager-old/tests/GregModmanager.Tests/GregModmanager.Tests.csproj", + "version": "2.9.3", + "ecosystem": "nuget" + } + ], + "metadata": { + "repositoryRoot": "/mnt/win/Repositories/GameModding/DataCenter/GregDesktopApps/gregApp.Modmanager", + "totalFiles": 372, + "scannedAt": "2026-10-28T07:05:06.090Z" + } +} diff --git a/.codacy/tmp/codacy-remote-config.json b/.codacy/tmp/codacy-remote-config.json new file mode 100644 index 0000000..5e79982 --- /dev/null +++ b/.codacy/tmp/codacy-remote-config.json @@ -0,0 +1,6298 @@ +{ + "version": 1, + "metadata": { + "source": "remote", + "provider": "gh", + "organization": "mleem97", + "repositoryId": "887456", + "repositoryName": "gregModmanager", + "createdAt": "2026-10-28T07:05:51.166Z", + "updatedAt": "2026-10-28T07:05:51.166Z", + "languages": [ + "CSharp", + "Dockerfile", + "JSON", + "Markdown", + "Powershell", + "Python", + "Rust", + "Shell", + "XML", + "YAML" + ] + }, + "tools": [ + { + "toolId": "Prospector", + "patterns": [ + { + "patternId": "Prospector_profile-validator" + }, + { + "patternId": "Prospector_mccabe" + }, + { + "patternId": "Prospector_pyflakes" + }, + { + "patternId": "Prospector_dodgy" + } + ] + }, + { + "toolId": "PyLintPython3", + "patterns": [ + { + "patternId": "PyLintPython3_E0203" + }, + { + "patternId": "PyLintPython3_E0102" + }, + { + "patternId": "PyLintPython3_E1102" + }, + { + "patternId": "PyLintPython3_E1121" + }, + { + "patternId": "PyLintPython3_W1301" + }, + { + "patternId": "PyLintPython3_E0241" + }, + { + "patternId": "PyLintPython3_C0123" + }, + { + "patternId": "PyLintPython3_W0101" + }, + { + "patternId": "PyLintPython3_E0107" + }, + { + "patternId": "PyLintPython3_E0202" + }, + { + "patternId": "PyLintPython3_E1003" + }, + { + "patternId": "PyLintPython3_E0302" + }, + { + "patternId": "PyLintPython3_E1306" + }, + { + "patternId": "PyLintPython3_E0113" + }, + { + "patternId": "PyLintPython3_E0301" + }, + { + "patternId": "PyLintPython3_W0711" + }, + { + "patternId": "PyLintPython3_E0108" + }, + { + "patternId": "PyLintPython3_E0604" + }, + { + "patternId": "PyLintPython3_W0102" + }, + { + "patternId": "PyLintPython3_E0603" + }, + { + "patternId": "PyLintPython3_W0150" + }, + { + "patternId": "PyLintPython3_E0240" + }, + { + "patternId": "PyLintPython3_E0101" + }, + { + "patternId": "PyLintPython3_E0110" + }, + { + "patternId": "PyLintPython3_E0112" + }, + { + "patternId": "PyLintPython3_E0117" + }, + { + "patternId": "PyLintPython3_E0211" + }, + { + "patternId": "PyLintPython3_E1303" + }, + { + "patternId": "PyLintPython3_W0123" + }, + { + "patternId": "PyLintPython3_E0106" + }, + { + "patternId": "PyLintPython3_E1300" + }, + { + "patternId": "PyLintPython3_W1305" + }, + { + "patternId": "PyLintPython3_E0105" + }, + { + "patternId": "PyLintPython3_E1200" + }, + { + "patternId": "PyLintPython3_W0109" + }, + { + "patternId": "PyLintPython3_W1306" + }, + { + "patternId": "PyLintPython3_E0236" + }, + { + "patternId": "PyLintPython3_E0712" + }, + { + "patternId": "PyLintPython3_E0710" + }, + { + "patternId": "PyLintPython3_E1301" + }, + { + "patternId": "PyLintPython3_E0104" + }, + { + "patternId": "PyLintPython3_E0702" + }, + { + "patternId": "PyLintPython3_E1132" + }, + { + "patternId": "PyLintPython3_W0221" + }, + { + "patternId": "PyLintPython3_E0701" + }, + { + "patternId": "PyLintPython3_E1206" + }, + { + "patternId": "PyLintPython3_E0238" + }, + { + "patternId": "PyLintPython3_E1126" + }, + { + "patternId": "PyLintPython3_E0114" + }, + { + "patternId": "PyLintPython3_W0702" + }, + { + "patternId": "PyLintPython3_E0100" + }, + { + "patternId": "PyLintPython3_W0106" + }, + { + "patternId": "PyLintPython3_E0601" + }, + { + "patternId": "PyLintPython3_W1307" + }, + { + "patternId": "PyLintPython3_E1302" + }, + { + "patternId": "PyLintPython3_E1125" + }, + { + "patternId": "PyLintPython3_W0622" + }, + { + "patternId": "PyLintPython3_E1111" + }, + { + "patternId": "PyLintPython3_E1305" + }, + { + "patternId": "PyLintPython3_E0103" + }, + { + "patternId": "PyLintPython3_W0410" + }, + { + "patternId": "PyLintPython3_E0115" + }, + { + "patternId": "PyLintPython3_W0611" + }, + { + "patternId": "PyLintPython3_E1304" + }, + { + "patternId": "PyLintPython3_E1123" + }, + { + "patternId": "PyLintPython3_W0233" + }, + { + "patternId": "PyLintPython3_W1303" + }, + { + "patternId": "PyLintPython3_W0199" + }, + { + "patternId": "PyLintPython3_W0705" + }, + { + "patternId": "PyLintPython3_E1124" + }, + { + "patternId": "PyLintPython3_E0704" + }, + { + "patternId": "PyLintPython3_W0601" + }, + { + "patternId": "PyLintPython3_E0239" + }, + { + "patternId": "PyLintPython3_E1120" + }, + { + "patternId": "PyLintPython3_W1302" + }, + { + "patternId": "PyLintPython3_W0222" + }, + { + "patternId": "PyLintPython3_E0711" + }, + { + "patternId": "PyLintPython3_W1300" + }, + { + "patternId": "PyLintPython3_E1205" + }, + { + "patternId": "PyLintPython3_E1201" + }, + { + "patternId": "PyLintPython3_W0122" + }, + { + "patternId": "PyLintPython3_E1127" + } + ] + }, + { + "toolId": "psscriptanalyzer", + "patterns": [ + { + "patternId": "psscriptanalyzer_psavoiddefaultvalueformandatoryparameter" + }, + { + "patternId": "psscriptanalyzer_psavoidusinginvokeexpression" + }, + { + "patternId": "psscriptanalyzer_psusecompatiblecmdlets" + }, + { + "patternId": "psscriptanalyzer_psavoidusingdeprecatedmanifestfields" + }, + { + "patternId": "psscriptanalyzer_psavoidusingwritehost" + }, + { + "patternId": "psscriptanalyzer_psavoidusingwmicmdlet" + }, + { + "patternId": "psscriptanalyzer_psuseliteralinitializerforhashtable" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectusageofredirectionoperator" + }, + { + "patternId": "psscriptanalyzer_psdscreturncorrecttypesfordscfunctions" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectusageofassignmentoperator" + }, + { + "patternId": "psscriptanalyzer_psusebomforunicodeencodedfile" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalfunctions" + }, + { + "patternId": "psscriptanalyzer_psavoidusingusernameandpasswordparams" + }, + { + "patternId": "psscriptanalyzer_psavoidshouldcontinuewithoutforce" + }, + { + "patternId": "psscriptanalyzer_psmissingmodulemanifestfield" + }, + { + "patternId": "psscriptanalyzer_psavoidusingemptycatchblock" + }, + { + "patternId": "psscriptanalyzer_psreservedcmdletchar" + }, + { + "patternId": "psscriptanalyzer_psshouldprocess" + }, + { + "patternId": "psscriptanalyzer_psavoidusingconverttosecurestringwithplaintext" + }, + { + "patternId": "psscriptanalyzer_psavoidusingcomputernamehardcoded" + }, + { + "patternId": "psscriptanalyzer_pspossibleincorrectcomparisonwithnull" + }, + { + "patternId": "psscriptanalyzer_psusecmdletcorrectly" + }, + { + "patternId": "psscriptanalyzer_psusepscredentialtype" + }, + { + "patternId": "psscriptanalyzer_psdscstandarddscfunctionsinresource" + }, + { + "patternId": "psscriptanalyzer_psavoidinvokingemptymembers" + }, + { + "patternId": "psscriptanalyzer_psdscuseidenticalmandatoryparametersfordsc" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalaliases" + }, + { + "patternId": "psscriptanalyzer_psdscuseidenticalparametersfordsc" + }, + { + "patternId": "psscriptanalyzer_psuseshouldprocessforstatechangingfunctions" + }, + { + "patternId": "psscriptanalyzer_psavoidglobalvars" + }, + { + "patternId": "psscriptanalyzer_psusetoexportfieldsinmanifest" + }, + { + "patternId": "psscriptanalyzer_psavoidusingplaintextforpassword" + }, + { + "patternId": "psscriptanalyzer_psusesupportsshouldprocess" + }, + { + "patternId": "psscriptanalyzer_psreservedparams" + }, + { + "patternId": "psscriptanalyzer_psavoiddefaultvalueswitchparameter" + }, + { + "patternId": "psscriptanalyzer_psavoidassignmenttoautomaticvariable" + } + ] + }, + { + "toolId": "Semgrep", + "patterns": [ + { + "patternId": "Semgrep_python.lang.security.insecure-uuid-version.insecure-uuid-version" + }, + { + "patternId": "Semgrep_kotlin.gradle.security.build-gradle-password-hardcoded.build-gradle-password-hardcoded" + }, + { + "patternId": "Semgrep_javascript.node-crypto.security.create-de-cipher-no-iv.create-de-cipher-no-iv" + }, + { + "patternId": "Semgrep_javascript.node-crypto.security.gcm-no-tag-length.gcm-no-tag-length" + }, + { + "patternId": "Semgrep_go.lang.security.reverseproxy-director.reverseproxy-director" + }, + { + "patternId": "Semgrep_php.lang.security.injection.tainted-callable.tainted-callable" + }, + { + "patternId": "Semgrep_php.lang.security.injection.tainted-exec.tainted-exec" + }, + { + "patternId": "Semgrep_yaml.openapi.security.openai-consequential-action-false.openai-consequential-action-false" + }, + { + "patternId": "Semgrep_javascript.node-crypto.security.aead-no-final.aead-no-final" + }, + { + "patternId": "Semgrep_dockerfile.security.dockerd-socket-mount.dockerfile-dockerd-socket-mount" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-onfido-live-api-token.detected-onfido-live-api-token" + }, + { + "patternId": "Semgrep_codacy.python.i18n.no-hardcoded-strftime" + }, + { + "patternId": "Semgrep_codacy.cpp.i18n.no-hardcoded-strftime" + }, + { + "patternId": "Semgrep_codacy.java.i18n.no-hardcoded-decimal-format" + }, + { + "patternId": "Semgrep_codacy.java.i18n.no-hardcoded-date-format" + }, + { + "patternId": "Semgrep_codacy.bash.security.hard-coded-password" + }, + { + "patternId": "Semgrep_codacy.k8s.ingress.nginx.retirement.ingress-resource" + }, + { + "patternId": "Semgrep_codacy.k8s.ingress.nginx.retirement.ingress-class" + }, + { + "patternId": "Semgrep_codacy.k8s.ingress.nginx.retirement.workload" + }, + { + "patternId": "Semgrep_codacy.csharp.security.sql-injection.dynamic-query" + }, + { + "patternId": "Semgrep_codacy.csharp.best-practice.misleading-exception-class-name" + }, + { + "patternId": "Semgrep_codacy.python.openai.import-without-guardrails" + }, + { + "patternId": "Semgrep_codacy.python.openai.non-guardrails-client-usage" + }, + { + "patternId": "Semgrep_codacy.python.openai.non-guardrails-direct-call" + }, + { + "patternId": "Semgrep_kotlin_pathtraversal_rule-FilePathTraversal" + }, + { + "patternId": "Semgrep_codacy.generic.security.detect-invisible-unicode" + }, + { + "patternId": "Semgrep_codacy.java.security.flexible-search-sql-injection" + }, + { + "patternId": "Semgrep_yaml_spring_rule-SpringActuatorFullyEnabled" + }, + { + "patternId": "Semgrep_properties_spring_rule-SpringActuatorFullyEnabled" + }, + { + "patternId": "Semgrep_java_deserialization_rule-InsecureDeserialization" + }, + { + "patternId": "Semgrep_generic_injection_rule-BiDiTrojanSource" + }, + { + "patternId": "Semgrep_codacy.javascript.security.hard-coded-password" + }, + { + "patternId": "Semgrep_codacy.java.security.hard-coded-password" + }, + { + "patternId": "Semgrep_codacy.generic.plsql.resource-injection" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.system.systemdebug.system-debug" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.sharing.specifysharinglevel.specify-sharing-level" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.injection.apexsoqlinjectionunescapedparam.soql-injection-unescaped-param" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.injection.apexsoqlinjectionfromunescapedurlparam.soql-injection-unescaped-url-param" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.endpoints.namedcredentialsstringmatch.named-credentials-string-match" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.endpoints.namedcredentialsconstantmatch.named-credentials-constant-match" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.endpoints.insecurehttprequest.insecure-http-request" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.encryption.badcrypto.bad-crypto" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.dml.apexcsrfstaticconstructor.apex-csrf-static-constructor" + }, + { + "patternId": "Semgrep_apex.lang.security.ncino.dml.apexcsrfconstructor.apex-csrf-constructor" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.harness-api-key.harness-api-key" + }, + { + "patternId": "Semgrep_codacy.generic.plsql.find-all-passwords" + }, + { + "patternId": "Semgrep_ai.typescript.detect-vercel-ai.detect-vercel-ai" + }, + { + "patternId": "Semgrep_ai.typescript.detect-promptfoo.detect-promptfoo" + }, + { + "patternId": "Semgrep_ai.typescript.detect-openai.detect-openai" + }, + { + "patternId": "Semgrep_ai.typescript.detect-mistral.detect-mistral" + }, + { + "patternId": "Semgrep_ai.typescript.detect-gemini.detect-gemini" + }, + { + "patternId": "Semgrep_ai.typescript.detect-anthropic.detect-anthropic" + }, + { + "patternId": "Semgrep_ai.swift.detect-gemini.detect-gemini" + }, + { + "patternId": "Semgrep_ai.swift.detect-apple-core-ml.detect-apple-core-ml" + }, + { + "patternId": "Semgrep_ai.python.detect-tensorflow.detect-tensorflow" + }, + { + "patternId": "Semgrep_ai.python.detect-pytorch.detect-pytorch" + }, + { + "patternId": "Semgrep_ai.python.detect-openai.detect-openai" + }, + { + "patternId": "Semgrep_ai.python.detect-mistral.detect-mistral" + }, + { + "patternId": "Semgrep_ai.python.detect-langchain.detect-langchain" + }, + { + "patternId": "Semgrep_ai.python.detect-huggingface.detect-huggingface" + }, + { + "patternId": "Semgrep_ai.python.detect-gemini.detect-gemini" + }, + { + "patternId": "Semgrep_ai.python.detect-anthropic.detect-anthropic" + }, + { + "patternId": "Semgrep_ai.kotlin.detect-gemini.detect-gemini" + }, + { + "patternId": "Semgrep_ai.go.detect-openai.detect-openai" + }, + { + "patternId": "Semgrep_ai.go.detect-gemini.detect-gemini" + }, + { + "patternId": "Semgrep_ai.dart.detect-gemini.detect-gemini" + }, + { + "patternId": "Semgrep_ai.csharp.detect-openai.detect-openai" + }, + { + "patternId": "Semgrep_codacy.generic.plsql.empty-strings" + }, + { + "patternId": "Semgrep_yaml.openapi.security.use-of-basic-authentication.use-of-basic-authentication" + }, + { + "patternId": "Semgrep_rules_lgpl_swift_other_rule-ios-dtls1-used" + }, + { + "patternId": "Semgrep_rules_lgpl_java_webview_rule-webview-debugging" + }, + { + "patternId": "Semgrep_rules_lgpl_java_webview_rule-ignore-ssl-certificate-errors" + }, + { + "patternId": "Semgrep_python_pyramid_rule-pyramid-csrf-origin-check" + }, + { + "patternId": "Semgrep_python_flask_rule-tainted-sql-string" + }, + { + "patternId": "Semgrep_python_flask_rule-path-traversal-open" + }, + { + "patternId": "Semgrep_python_flask_rule-flask-open-redirect" + }, + { + "patternId": "Semgrep_python_crypto_rule-HTTPConnectionPool" + }, + { + "patternId": "Semgrep_python.twilio.security.twiml-injection.twiml-injection" + }, + { + "patternId": "Semgrep_php_file_rule-file-inclusion" + }, + { + "patternId": "Semgrep_php_exec_rule-exec-use" + }, + { + "patternId": "Semgrep_php_eval_rule-eval-use" + }, + { + "patternId": "Semgrep_php_backticks_rule-backticks-use" + }, + { + "patternId": "Semgrep_php_assert_rule-assert-use" + }, + { + "patternId": "Semgrep_php.lang.security.injection.printed-request.printed-request" + }, + { + "patternId": "Semgrep_kotlin_xxe_rule-XMLStreamRdr" + }, + { + "patternId": "Semgrep_kotlin_xxe_rule-XMLRdr" + }, + { + "patternId": "Semgrep_kotlin_xxe_rule-SaxParserXXE" + }, + { + "patternId": "Semgrep_kotlin_xss_rule-XSSReqParamToServletWriter" + }, + { + "patternId": "Semgrep_kotlin_xss_rule-WicketXSS" + }, + { + "patternId": "Semgrep_kotlin_xpathi_rule-XpathInjection" + }, + { + "patternId": "Semgrep_kotlin_xml_rule-XsltTransform" + }, + { + "patternId": "Semgrep_kotlin_xml_rule-SAMLIgnoreComments" + }, + { + "patternId": "Semgrep_kotlin_templateinjection_rule-TemplateInjection" + }, + { + "patternId": "Semgrep_kotlin_strings_rule-NormalizeAfterValidation" + }, + { + "patternId": "Semgrep_kotlin_strings_rule-ModifyAfterValidation" + }, + { + "patternId": "Semgrep_kotlin_strings_rule-FormatStringManipulation" + }, + { + "patternId": "Semgrep_kotlin_strings_rule-BadHexConversion" + }, + { + "patternId": "Semgrep_kotlin_ssrf_rule-SSRF" + }, + { + "patternId": "Semgrep_kotlin_smtp_rule-InsecureSmtp" + }, + { + "patternId": "Semgrep_kotlin_script_rule-ScriptInjection" + }, + { + "patternId": "Semgrep_kotlin_perm_rule-OverlyPermissiveFilePermissionInline" + }, + { + "patternId": "Semgrep_kotlin_perm_rule-DangerousPermissions" + }, + { + "patternId": "Semgrep_kotlin_password_rule-EmptyDBPassword" + }, + { + "patternId": "Semgrep_kotlin_password_rule-ConstantDBPassword" + }, + { + "patternId": "Semgrep_kotlin_inject_rule-SqlInjection" + }, + { + "patternId": "Semgrep_kotlin_inject_rule-SpotbugsPathTraversalAbsolute" + }, + { + "patternId": "Semgrep_kotlin_inject_rule-FileDisclosure" + }, + { + "patternId": "Semgrep_kotlin_inject_rule-CommandInjection" + }, + { + "patternId": "Semgrep_kotlin_file_rule-FilenameUtils" + }, + { + "patternId": "Semgrep_kotlin_endpoint_rule-WeakHostNameVerification" + }, + { + "patternId": "Semgrep_kotlin_endpoint_rule-UnvalidatedRedirect" + }, + { + "patternId": "Semgrep_kotlin_csrf_rule-SpringCSRFDisabled" + }, + { + "patternId": "Semgrep_kotlin_crypto_rule-WeakTLSProtocolVersion" + }, + { + "patternId": "Semgrep_kotlin_crypto_rule-WeakTLSProtocol" + }, + { + "patternId": "Semgrep_kotlin_crypto_rule-NullCipher" + }, + { + "patternId": "Semgrep_kotlin_crypto_rule-CipherPaddingOracle" + }, + { + "patternId": "Semgrep_kotlin_crypto_rule-CipherIntegrity" + }, + { + "patternId": "Semgrep_kotlin_crypto_rule-CipherECBMode" + }, + { + "patternId": "Semgrep_kotlin_cors_rule-PermissiveCORSInjection" + }, + { + "patternId": "Semgrep_kotlin_cookie_rule-RequestParamToHeader" + }, + { + "patternId": "Semgrep_kotlin_cookie_rule-HttpResponseSplitting" + }, + { + "patternId": "Semgrep_javascript_crypto_rule-NodeLibcurlSSLVerificationDisable" + }, + { + "patternId": "Semgrep_java_xxe_rule-XMLInputFactoryExternalEntitiesEnabled" + }, + { + "patternId": "Semgrep_java_xxe_rule-DocumentBuilderFactoryDisallowDoctypeDeclMissing" + }, + { + "patternId": "Semgrep_java_xxe_rule-DisallowDoctypeDeclFalse" + }, + { + "patternId": "Semgrep_java_traversal_rule-RelativePathTraversal" + }, + { + "patternId": "Semgrep_java_inject_rule-EnvInjection" + }, + { + "patternId": "Semgrep_java_inject_rule-DangerousGroovyShell" + }, + { + "patternId": "Semgrep_java_file_rule_rule-FilePathTraversalHttpServlet" + }, + { + "patternId": "Semgrep_java_endpoint_rule-ManuallyConstructedURLs" + }, + { + "patternId": "Semgrep_java_deserialization_rule-SnakeYamlConstructor" + }, + { + "patternId": "Semgrep_java_deserialization_rule-ServerDangerousObjectDeserialization" + }, + { + "patternId": "Semgrep_java_deserialization_rule-InsecureJmsDeserialization" + }, + { + "patternId": "Semgrep_java_csrf_rule-UnrestrictedRequestMapping" + }, + { + "patternId": "Semgrep_java_crypto_rule-WeakTLSProtocol-SSLContext" + }, + { + "patternId": "Semgrep_java_crypto_rule-WeakTLSProtocol-DefaultHttpClient" + }, + { + "patternId": "Semgrep_java_crypto_rule-UseOfRC4" + }, + { + "patternId": "Semgrep_java_crypto_rule-UseOfRC2" + }, + { + "patternId": "Semgrep_java_crypto_rule-UnirestHTTPRequest" + }, + { + "patternId": "Semgrep_java_crypto_rule-TelnetRequest" + }, + { + "patternId": "Semgrep_java_crypto_rule-TLSUnsafeRenegotiation" + }, + { + "patternId": "Semgrep_java_crypto_rule-SpringHTTPRequestRestTemplate" + }, + { + "patternId": "Semgrep_java_crypto_rule-SpringFTPRequest" + }, + { + "patternId": "Semgrep_java_crypto_rule-HttpGetHTTPRequest" + }, + { + "patternId": "Semgrep_java_crypto_rule-HttpComponentsRequest" + }, + { + "patternId": "Semgrep_java_crypto_rule-HTTPUrlConnectionHTTPRequest" + }, + { + "patternId": "Semgrep_java_crypto_rule-DisallowOldTLSVersion" + }, + { + "patternId": "Semgrep_go.gorilla.security.audit.session-cookie-samesitenone.session-cookie-samesitenone" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.new-relic-insert-key.new-relic-insert-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.intra42-client-secret.intra42-client-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.cloudflare-origin-ca-key.cloudflare-origin-ca-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.cloudflare-global-api-key.cloudflare-global-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.cloudflare-api-key.cloudflare-api-key" + }, + { + "patternId": "Semgrep_codacy.csharp.security.hard-coded-password" + }, + { + "patternId": "Semgrep_python_jwt_rule-jwt-none-alg" + }, + { + "patternId": "Semgrep_java_inject_rule-FileDisclosureSpringFramework" + }, + { + "patternId": "Semgrep_java_inject_rule-FileDisclosureRequestDispatcher" + }, + { + "patternId": "Semgrep_java_endpoint_rule-X509TrustManager" + }, + { + "patternId": "Semgrep_java_endpoint_rule-HostnameVerifier" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.facebook-secret.facebook-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.facebook-page-access-token.facebook-page-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.facebook-access-token.facebook-access-token" + }, + { + "patternId": "Semgrep_ruby_xss_rule-ManualTemplateCreation" + }, + { + "patternId": "Semgrep_ruby_xss_rule-AvoidRenderText" + }, + { + "patternId": "Semgrep_ruby_xss_rule-AvoidRenderInline" + }, + { + "patternId": "Semgrep_ruby_xss_rule-AvoidLinkTo" + }, + { + "patternId": "Semgrep_ruby_ssl_rule-SSLModeNoVerify" + }, + { + "patternId": "Semgrep_ruby_sql_rule-CheckSQL" + }, + { + "patternId": "Semgrep_ruby_reflection_rule-CheckUnsafeReflectionMethods" + }, + { + "patternId": "Semgrep_ruby_reflection_rule-CheckUnsafeReflection" + }, + { + "patternId": "Semgrep_ruby_redirect_rule-CheckRedirectTo" + }, + { + "patternId": "Semgrep_ruby_mass_assignment_rule-UnprotectedMassAssign" + }, + { + "patternId": "Semgrep_ruby_mass_assignment_rule-ModelAttrAccessible" + }, + { + "patternId": "Semgrep_ruby_injection_rule-DangerousExec" + }, + { + "patternId": "Semgrep_ruby_injection_rule-BadSend" + }, + { + "patternId": "Semgrep_ruby_injection_rule-AvoidTaintedShellCall" + }, + { + "patternId": "Semgrep_ruby_http_rule-AvoidTaintedHTTPRequest" + }, + { + "patternId": "Semgrep_ruby_ftp_rule-AvoidTaintedFTPCall" + }, + { + "patternId": "Semgrep_ruby_find_rule-CheckUnscopedFind" + }, + { + "patternId": "Semgrep_ruby_file_rule-CheckSendFile" + }, + { + "patternId": "Semgrep_ruby_file_rule-CheckRenderLocalFileInclude" + }, + { + "patternId": "Semgrep_ruby_file_rule-AvoidTaintedFileAccess" + }, + { + "patternId": "Semgrep_ruby_eval_rule-NoEval" + }, + { + "patternId": "Semgrep_ruby_escaping_rule-JSONEntityEscape" + }, + { + "patternId": "Semgrep_ruby_deserialization_rule-BadDeserializationYAML" + }, + { + "patternId": "Semgrep_ruby_deserialization_rule-BadDeserializationEnv" + }, + { + "patternId": "Semgrep_ruby_deserialization_rule-BadDeserialization" + }, + { + "patternId": "Semgrep_ruby_csrf_rule-MissingCSRFProtection" + }, + { + "patternId": "Semgrep_ruby_crypto_rule-WeakHashesSHA1" + }, + { + "patternId": "Semgrep_ruby_crypto_rule-WeakHashesMD5" + }, + { + "patternId": "Semgrep_ruby_cookie_rule-CookieSerialization" + }, + { + "patternId": "Semgrep_javascript.jwt-simple.security.jwt-simple-noverify.jwt-simple-noverify" + }, + { + "patternId": "Semgrep_java_xxe_rule-TransformerfactoryDTDNotDisabled" + }, + { + "patternId": "Semgrep_java_xxe_rule-SAXParserFactoryDisallowDoctypeDeclMissing" + }, + { + "patternId": "Semgrep_java_xxe_rule-ExternalParameterEntitiesTrue" + }, + { + "patternId": "Semgrep_java_xxe_rule-ExternalGeneralEntitiesTrue" + }, + { + "patternId": "Semgrep_java_crypto_rule-GCMNonceReuse" + }, + { + "patternId": "Semgrep_python_django_rule-django-raw-used" + }, + { + "patternId": "Semgrep_php.lang.security.base-convert-loses-precision.base-convert-loses-precision" + }, + { + "patternId": "Semgrep_java_crypto_rule_JwtNoneAlgorithm" + }, + { + "patternId": "Semgrep_csharp_xss_rule-ScriptXss" + }, + { + "patternId": "Semgrep_csharp_xss_rule-HtmlElementXss" + }, + { + "patternId": "Semgrep_csharp_injection_rule-XmlReaderXXEInjection" + }, + { + "patternId": "Semgrep_csharp_injection_rule-XmlDocumentXXEInjection" + }, + { + "patternId": "Semgrep_python_ssh_rule-ssh-nohost-key-verification" + }, + { + "patternId": "Semgrep_java_crypto_rule_JwtDecodeWithoutVerify" + }, + { + "patternId": "Semgrep_go_filesystem_rule-httprootdir" + }, + { + "patternId": "Semgrep_go_filesystem_rule-fileread" + }, + { + "patternId": "Semgrep_go.lang.security.injection.open-redirect.open-redirect" + }, + { + "patternId": "Semgrep_scala_smtp_rule-InsecureSmtp" + }, + { + "patternId": "Semgrep_scala_script_rule-SpelView" + }, + { + "patternId": "Semgrep_scala_script_rule-ScriptInjection" + }, + { + "patternId": "Semgrep_scala_endpoint_rule-UnencryptedSocket" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_xss_rule-xss-serialize-javascript" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_xss_rule-xss-disable-mustache-escape" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_xss_rule-squirrelly-autoescape" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_xss_rule-handlebars-safestring" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_xss_rule-express-xss" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_xml_rule-xxe-expat" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_xml_rule-node-xxe" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_xml_rule-node-xpath-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_traversal_rule-zip-path-overwrite" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_traversal_rule-tar-path-overwrite" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_traversal_rule-join-resolve-path-traversal" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_traversal_rule-generic-path-traversal" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_traversal_rule-express-lfr-warning" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_traversal_rule-express-lfr" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_traversal_rule-admzip-path-overwrite" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_ssrf_rule-wkhtmltopdf-ssrf" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_ssrf_rule-puppeteer-ssrf" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_ssrf_rule-playwright-ssrf" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_ssrf_rule-phantom-ssrf" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_ssrf_rule-node-ssrf" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_redirect_rule-express-open-redirect2" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_redirect_rule-express-open-redirect" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_jwt_rule-node-jwt-none-algorithm" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_jwt_rule-jwt-express-hardcoded" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_jwt_rule-hardcoded-jwt-secret" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_headers_rule-host-header-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_headers_rule-generic-header-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_exec_rule-shelljs-os-command-exec" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-yaml-deserialize" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-vm2-context-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-vm2-code-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-vm-runinnewcontext-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-vm-runincontext-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-vm-compilefunction-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-vm-code-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-server-side-template-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-serializetojs-deserialize" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-sandbox-code-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-node-deserialize" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-grpc-insecure-connection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-eval-require" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_eval_rule-eval-nodejs" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_electronjs_rule-electron-nodejs-integration" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_electronjs_rule-electron-disable-websecurity" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_database_rule-sequelize-tls-cert-validation" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_database_rule-sequelize-tls" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_database_rule-node-sqli-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_database_rule-node-nosqli-js-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_database_rule-node-nosqli-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_database_rule-node-knex-sqli-injection" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_crypto_rule-node-weak-crypto" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_crypto_rule-node-tls-reject" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_crypto_rule-node-timing-attack" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_crypto_rule-node-sha1" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_crypto_rule-node-md5" + }, + { + "patternId": "Semgrep_rules_lgpl_javascript_crypto_rule-node-insecure-random-generator" + }, + { + "patternId": "Semgrep_python_ssl_rule-ssl-with-bad-version" + }, + { + "patternId": "Semgrep_python_files_rule-tarfile-unsafe-members" + }, + { + "patternId": "Semgrep_python_exec_rule-subprocess-shell-TRUE" + }, + { + "patternId": "Semgrep_python_exec_rule-subprocess-call-array" + }, + { + "patternId": "Semgrep_python_exec_rule-start-process-with-no-shell" + }, + { + "patternId": "Semgrep_go_unsafe_rule-unsafe" + }, + { + "patternId": "Semgrep_go_subproc_rule-subproc" + }, + { + "patternId": "Semgrep_go_sql_rule-concat-sqli" + }, + { + "patternId": "Semgrep_go_injection_rule-template-injection" + }, + { + "patternId": "Semgrep_go_injection_rule-ssrf" + }, + { + "patternId": "Semgrep_go_filesystem_rule-ziparchive" + }, + { + "patternId": "Semgrep_go_filesystem_rule-decompression-bomb" + }, + { + "patternId": "Semgrep_go_crypto_rule-tlsversion" + }, + { + "patternId": "Semgrep_go_crypto_rule-insecure-ignore-host-key" + }, + { + "patternId": "Semgrep_go_crypto_rule-badtlssettings" + }, + { + "patternId": "Semgrep_go_blocklist_rule-blocklist-sha1" + }, + { + "patternId": "Semgrep_go_blocklist_rule-blocklist-rc4" + }, + { + "patternId": "Semgrep_go_blocklist_rule-blocklist-md5" + }, + { + "patternId": "Semgrep_go_blocklist_rule-blocklist-des" + }, + { + "patternId": "Semgrep_csharp_path_rule-PathTraversal" + }, + { + "patternId": "Semgrep_c_tmpfile_rule-tmpnam-tempnam" + }, + { + "patternId": "Semgrep_c_tmpfile_rule-mktemp" + }, + { + "patternId": "Semgrep_c_race_rule-readlink" + }, + { + "patternId": "Semgrep_c_format_rule-syslog" + }, + { + "patternId": "Semgrep_c_format_rule-snprintf-vsnprintf" + }, + { + "patternId": "Semgrep_c_format_rule-printf-vprintf" + }, + { + "patternId": "Semgrep_c_format_rule-fprintf-vfprintf" + }, + { + "patternId": "Semgrep_c_crypto_rule-EVP-rc4-40-EVP-rc2-40-cbc" + }, + { + "patternId": "Semgrep_c_crypto_rule-EVP-des-ecb-EVP-des-cbc" + }, + { + "patternId": "Semgrep_c_buffer_rule-strcpy" + }, + { + "patternId": "Semgrep_c_buffer_rule-memcpy-CopyMemory" + }, + { + "patternId": "Semgrep_c_buffer_rule-gets--getts" + }, + { + "patternId": "Semgrep_python.fastapi.security.wildcard-cors.wildcard-cors" + }, + { + "patternId": "Semgrep_java_script_rule-SpringSpelExpressionParser" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.skip-tls-verify-service.skip-tls-verify-service" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.skip-tls-verify-cluster.skip-tls-verify-cluster" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.secrets-in-config-file.secrets-in-config-file" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.seccomp-confinement-disabled.seccomp-confinement-disabled" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.run-as-non-root-unsafe-value.run-as-non-root-unsafe-value" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.privileged-container.privileged-container" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.legacy-api-clusterrole-excessive-permissions.legacy-api-clusterrole-excessive-permissions" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.exposing-docker-socket-hostpath.exposing-docker-socket-hostpath" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.allow-privilege-escalation.allow-privilege-escalation" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.allow-privilege-escalation-true.allow-privilege-escalation-true" + }, + { + "patternId": "Semgrep_yaml.kubernetes.security.allow-privilege-escalation-no-securitycontext.allow-privilege-escalation-no-securitycontext" + }, + { + "patternId": "Semgrep_yaml.github-actions.security.workflow-run-target-code-checkout.workflow-run-target-code-checkout" + }, + { + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha" + }, + { + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection" + }, + { + "patternId": "Semgrep_yaml.github-actions.security.pull-request-target-code-checkout.pull-request-target-code-checkout" + }, + { + "patternId": "Semgrep_yaml.github-actions.security.github-script-injection.github-script-injection" + }, + { + "patternId": "Semgrep_yaml.github-actions.security.curl-eval.curl-eval" + }, + { + "patternId": "Semgrep_yaml.github-actions.security.allowed-unsecure-commands.allowed-unsecure-commands" + }, + { + "patternId": "Semgrep_yaml.docker-compose.security.privileged-service.privileged-service" + }, + { + "patternId": "Semgrep_yaml.docker-compose.security.exposing-docker-socket-volume.exposing-docker-socket-volume" + }, + { + "patternId": "Semgrep_yaml.argo.security.argo-workflow-parameter-command-injection.argo-workflow-parameter-command-injection" + }, + { + "patternId": "Semgrep_typescript.react.security.react-insecure-request.react-insecure-request" + }, + { + "patternId": "Semgrep_typescript.react.security.audit.react-unsanitized-property.react-unsanitized-property" + }, + { + "patternId": "Semgrep_typescript.react.security.audit.react-unsanitized-method.react-unsanitized-method" + }, + { + "patternId": "Semgrep_typescript.react.security.audit.react-dangerouslysetinnerhtml.react-dangerouslysetinnerhtml" + }, + { + "patternId": "Semgrep_typescript.nestjs.security.audit.nestjs-open-redirect.nestjs-open-redirect" + }, + { + "patternId": "Semgrep_typescript.aws-cdk.security.awscdk-codebuild-project-public.awscdk-codebuild-project-public" + }, + { + "patternId": "Semgrep_typescript.aws-cdk.security.awscdk-bucket-grantpublicaccessmethod.awscdk-bucket-grantpublicaccessmethod" + }, + { + "patternId": "Semgrep_typescript.aws-cdk.security.audit.awscdk-sqs-unencryptedqueue.awscdk-sqs-unencryptedqueue" + }, + { + "patternId": "Semgrep_typescript.aws-cdk.security.audit.awscdk-bucket-enforcessl.aws-cdk-bucket-enforcessl" + }, + { + "patternId": "Semgrep_typescript.aws-cdk.security.audit.awscdk-bucket-encryption.awscdk-bucket-encryption" + }, + { + "patternId": "Semgrep_typescript.angular.security.audit.angular-domsanitizer.angular-bypasssecuritytrust" + }, + { + "patternId": "Semgrep_terraform.lang.security.s3-unencrypted-bucket.s3-unencrypted-bucket" + }, + { + "patternId": "Semgrep_terraform.lang.security.s3-public-rw-bucket.s3-public-rw-bucket" + }, + { + "patternId": "Semgrep_terraform.lang.security.rds-public-access.rds-public-access" + }, + { + "patternId": "Semgrep_terraform.lang.security.rds-insecure-password-storage-in-source-code.rds-insecure-password-storage-in-source-code" + }, + { + "patternId": "Semgrep_terraform.lang.security.iam.no-iam-priv-esc-roles.no-iam-priv-esc-roles" + }, + { + "patternId": "Semgrep_terraform.lang.security.iam.no-iam-priv-esc-other-users.no-iam-priv-esc-other-users" + }, + { + "patternId": "Semgrep_terraform.lang.security.iam.no-iam-priv-esc-funcs.no-iam-priv-esc-funcs" + }, + { + "patternId": "Semgrep_terraform.lang.security.iam.no-iam-admin-privileges.no-iam-admin-privileges" + }, + { + "patternId": "Semgrep_terraform.lang.security.ec2-imdsv1-optional.ec2-imdsv1-optional" + }, + { + "patternId": "Semgrep_terraform.gcp.security.gcp-sql-public-database.gcp-sql-public-database" + }, + { + "patternId": "Semgrep_terraform.gcp.security.gcp-sql-database-require-ssl.gcp-sql-database-require-ssl" + }, + { + "patternId": "Semgrep_terraform.gcp.security.gcp-dns-key-specs-rsasha1.gcp-dns-key-specs-rsasha1" + }, + { + "patternId": "Semgrep_terraform.gcp.security.gcp-cloud-storage-logging.gcp-cloud-storage-logging" + }, + { + "patternId": "Semgrep_terraform.azure.security.storage.storage-use-secure-tls-policy.storage-use-secure-tls-policy" + }, + { + "patternId": "Semgrep_terraform.azure.security.storage.storage-enforce-https.storage-enforce-https" + }, + { + "patternId": "Semgrep_terraform.azure.security.keyvault.keyvault-purge-enabled.keyvault-purge-enabled" + }, + { + "patternId": "Semgrep_terraform.azure.security.keyvault.keyvault-ensure-secret-expires.keyvault-ensure-secret-expires" + }, + { + "patternId": "Semgrep_terraform.azure.security.keyvault.keyvault-ensure-key-expires.keyvault-ensure-key-expires" + }, + { + "patternId": "Semgrep_terraform.azure.security.azure-mysql-mintls-version.azure-mysql-mintls-version" + }, + { + "patternId": "Semgrep_terraform.azure.security.azure-mysql-encryption-enabled.azure-mysql-encryption-enabled" + }, + { + "patternId": "Semgrep_terraform.azure.security.azure-mssql-service-mintls-version.azure-mssql-service-mintls-version" + }, + { + "patternId": "Semgrep_terraform.azure.security.azure-key-no-expiration-date.azure-key-no-expiration-date" + }, + { + "patternId": "Semgrep_terraform.azure.security.appservice.azure-appservice-min-tls-version.azure-appservice-min-tls-version" + }, + { + "patternId": "Semgrep_terraform.azure.security.appservice.azure-appservice-https-only.azure-appservice-https-only" + }, + { + "patternId": "Semgrep_terraform.azure.security.appservice.azure-appservice-detailed-errormessages-enabled.azure-appservice-detailed-errormessages-enabled" + }, + { + "patternId": "Semgrep_terraform.azure.security.appservice.appservice-use-secure-tls-policy.appservice-use-secure-tls-policy" + }, + { + "patternId": "Semgrep_terraform.azure.security.appservice.appservice-require-client-cert.appservice-require-client-cert" + }, + { + "patternId": "Semgrep_terraform.azure.security.appservice.appservice-enable-https-only.appservice-enable-https-only" + }, + { + "patternId": "Semgrep_terraform.azure.security.appservice.appservice-enable-http2.appservice-enable-http2" + }, + { + "patternId": "Semgrep_terraform.azure.security.appservice.appservice-authentication-enabled.appservice-authentication-enabled" + }, + { + "patternId": "Semgrep_terraform.aws.security.wildcard-assume-role.wildcard-assume-role" + }, + { + "patternId": "Semgrep_terraform.aws.security.unrestricted-github-oidc-policy.unrestricted-github-oidc-policy" + }, + { + "patternId": "Semgrep_terraform.aws.security.insecure-load-balancer-tls-version.insecure-load-balancer-tls-version" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-subnet-has-public-ip-address.aws-subnet-has-public-ip-address" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-sqs-queue-policy-wildcard-principal.aws-sqs-queue-policy-wildcard-principal" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-rds-backup-no-retention.aws-rds-backup-no-retention" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-provisioner-exec.aws-provisioner-exec" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-provider-static-credentials.aws-provider-static-credentials" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-lambda-x-ray-tracing-not-active.aws-lambda-x-ray-tracing-not-active" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-lambda-permission-unrestricted-source-arn.aws-lambda-permission-unrestricted-source-arn" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-lambda-environment-credentials.aws-lambda-environment-credentials" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-kms-no-rotation.aws-kms-no-rotation" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-kms-key-wildcard-principal.aws-kms-key-wildcard-principal" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-kinesis-stream-unencrypted.aws-kinesis-stream-unencrypted" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-insecure-redshift-ssl-configuration.aws-insecure-redshift-ssl-configuration" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-insecure-api-gateway-tls-version.aws-insecure-api-gateway-tls-version" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-iam-admin-policy.aws-iam-admin-policy" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-iam-admin-policy-ssoadmin.aws-iam-admin-policy-ssoadmin" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-glacier-vault-any-principal.aws-glacier-vault-any-principal" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-elasticsearch-nodetonode-encryption.aws-elasticsearch-nodetonode-encryption-not-enabled" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-elasticsearch-insecure-tls-version.aws-elasticsearch-insecure-tls-version" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-efs-filesystem-encrypted-with-cmk.aws-efs-filesystem-encrypted-with-cmk" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-ecr-repository-wildcard-principal.aws-ecr-repository-wildcard-principal" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-ecr-mutable-image-tags.aws-ecr-mutable-image-tags" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-ec2-launch-template-metadata-service-v1-enabled.aws-ec2-launch-template-metadata-service-v1-enabled" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-ec2-has-public-ip.aws-ec2-has-public-ip" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-ebs-volume-unencrypted.aws-ebs-volume-unencrypted" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-ebs-unencrypted.aws-ebs-unencrypted" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-ebs-snapshot-encrypted-with-cmk.aws-ebs-snapshot-encrypted-with-cmk" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-dynamodb-table-unencrypted.aws-dynamodb-table-unencrypted" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-documentdb-auditing-disabled.aws-documentdb-auditing-disabled" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-db-instance-no-logging.aws-db-instance-no-logging" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-config-aggregator-not-all-regions.aws-config-aggregator-not-all-regions" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-codebuild-project-unencrypted.aws-codebuild-project-unencrypted" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-cloudwatch-log-group-no-retention.aws-cloudwatch-log-group-no-retention" + }, + { + "patternId": "Semgrep_terraform.aws.security.aws-cloudfront-insecure-tls.aws-insecure-cloudfront-distribution-tls-version" + }, + { + "patternId": "Semgrep_terraform.aws.correctness.subscription-filter-missing-depends.subscription-filter-missing-depends" + }, + { + "patternId": "Semgrep_swift.webview.webview-js-window.swift-webview-config-allows-js-open-windows" + }, + { + "patternId": "Semgrep_swift.lang.storage.sensitive-storage-userdefaults.swift-user-defaults" + }, + { + "patternId": "Semgrep_scala_xxe_rule-XPathXXE" + }, + { + "patternId": "Semgrep_scala_xxe_rule-XMLStreamRdr" + }, + { + "patternId": "Semgrep_scala_xxe_rule-XMLRdr" + }, + { + "patternId": "Semgrep_scala_xxe_rule-Trans" + }, + { + "patternId": "Semgrep_scala_xxe_rule-SaxParserXXE" + }, + { + "patternId": "Semgrep_scala_xxe_rule-Document" + }, + { + "patternId": "Semgrep_scala_xss_rule-XSSServlet" + }, + { + "patternId": "Semgrep_scala_xss_rule-XSSReqParamToServletWriter" + }, + { + "patternId": "Semgrep_scala_xss_rule-WicketXSS" + }, + { + "patternId": "Semgrep_scala_xss_rule-MVCApi" + }, + { + "patternId": "Semgrep_scala_xpathi_rule-XpathInjection" + }, + { + "patternId": "Semgrep_scala_xml_rule-XsltTransform" + }, + { + "patternId": "Semgrep_scala_xml_rule-SAMLIgnoreComments" + }, + { + "patternId": "Semgrep_scala_xml_rule-ApacheXmlRpc" + }, + { + "patternId": "Semgrep_scala_unsafe_rule-InformationExposure" + }, + { + "patternId": "Semgrep_scala_templateinjection_rule-TemplateInjection" + }, + { + "patternId": "Semgrep_scala_strings_rule-NormalizeAfterValidation" + }, + { + "patternId": "Semgrep_scala_strings_rule-ModifyAfterValidation" + }, + { + "patternId": "Semgrep_scala_strings_rule-ImproperUnicode" + }, + { + "patternId": "Semgrep_scala_strings_rule-FormatStringManipulation" + }, + { + "patternId": "Semgrep_scala_strings_rule-BadHexConversion" + }, + { + "patternId": "Semgrep_scala_ssrf_rule-SSRF" + }, + { + "patternId": "Semgrep_scala_ssrf_rule-PlaySSRF" + }, + { + "patternId": "Semgrep_scala_perm_rule-OverlyPermissiveFilePermissionObj" + }, + { + "patternId": "Semgrep_scala_perm_rule-OverlyPermissiveFilePermissionInline" + }, + { + "patternId": "Semgrep_scala_perm_rule-DangerousPermissions" + }, + { + "patternId": "Semgrep_scala_password_rule-HardcodePassword" + }, + { + "patternId": "Semgrep_scala_inject_rule-SqlInjection" + }, + { + "patternId": "Semgrep_scala_inject_rule-SpotbugsPathTraversalRelative" + }, + { + "patternId": "Semgrep_scala_inject_rule-SpotbugsPathTraversalAbsolute" + }, + { + "patternId": "Semgrep_scala_inject_rule-PathTraversalOut" + }, + { + "patternId": "Semgrep_scala_inject_rule-OgnlInjection" + }, + { + "patternId": "Semgrep_scala_inject_rule-LDAPInjection" + }, + { + "patternId": "Semgrep_scala_inject_rule-FileDisclosure" + }, + { + "patternId": "Semgrep_scala_inject_rule-CustomInjectionSQLString" + }, + { + "patternId": "Semgrep_scala_inject_rule-CustomInjection" + }, + { + "patternId": "Semgrep_scala_inject_rule-CommandInjection" + }, + { + "patternId": "Semgrep_scala_inject_rule-BeanPropertyInjection" + }, + { + "patternId": "Semgrep_scala_inject_rule-AWSQueryInjection" + }, + { + "patternId": "Semgrep_scala_file_rule-FileUploadFileName" + }, + { + "patternId": "Semgrep_scala_endpoint_rule-WeakHostNameVerification" + }, + { + "patternId": "Semgrep_scala_crypto_rule-WeakTLSProtocol" + }, + { + "patternId": "Semgrep_scala_crypto_rule-CipherPaddingOracle" + }, + { + "patternId": "Semgrep_scala_crypto_rule-CipherIntegrity" + }, + { + "patternId": "Semgrep_scala_cors_rule-PermissiveCORSInjection" + }, + { + "patternId": "Semgrep_scala_cors_rule-PermissiveCORS" + }, + { + "patternId": "Semgrep_scala_cookie_rule-RequestParamToHeader" + }, + { + "patternId": "Semgrep_scala_cookie_rule-RequestParamToCookie" + }, + { + "patternId": "Semgrep_scala_cookie_rule-HttpResponseSplitting" + }, + { + "patternId": "Semgrep_scala.slick.security.scala-slick-sql-non-literal.scala-slick-sql-non-literal" + }, + { + "patternId": "Semgrep_scala.slick.security.scala-slick-overridesql-literal.scala-slick-overridesql-literal" + }, + { + "patternId": "Semgrep_scala.scala-jwt.security.jwt-hardcode.scala-jwt-hardcoded-secret" + }, + { + "patternId": "Semgrep_scala.play.security.webservice-ssrf.webservice-ssrf" + }, + { + "patternId": "Semgrep_scala.play.security.tainted-sql-from-http-request.tainted-sql-from-http-request" + }, + { + "patternId": "Semgrep_scala.play.security.tainted-slick-sqli.tainted-slick-sqli" + }, + { + "patternId": "Semgrep_scala.play.security.tainted-html-response.tainted-html-response" + }, + { + "patternId": "Semgrep_scala.play.security.conf-insecure-cookie-settings.conf-insecure-cookie-settings" + }, + { + "patternId": "Semgrep_scala.play.security.conf-csrf-headers-bypass.conf-csrf-headers-bypass" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.xmlinputfactory-dtd-enabled.xmlinputfactory-dtd-enabled" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.scalajs-eval.scalajs-eval" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.scalaj-http-ssrf.scalaj-http-ssrf" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.scalac-debug.scalac-debug" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.scala-dangerous-process-run.scala-dangerous-process-run" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.sax-dtd-enabled.sax-dtd-enabled" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.rsa-padding-set.rsa-padding-set" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.path-traversal-fromfile.path-traversal-fromfile" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.io-source-ssrf.io-source-ssrf" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.insecure-random.insecure-random" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.documentbuilder-dtd-enabled.documentbuilder-dtd-enabled" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.dispatch-ssrf.dispatch-ssrf" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.dangerous-shell-run.dangerous-shell-run" + }, + { + "patternId": "Semgrep_scala.lang.security.audit.dangerous-seq-run.dangerous-seq-run" + }, + { + "patternId": "Semgrep_scala.lang.correctness.positive-number-index-of.positive-number-index-of" + }, + { + "patternId": "Semgrep_scala.jwt-scala.security.jwt-scala-hardcode.jwt-scala-hardcode" + }, + { + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage" + }, + { + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir" + }, + { + "patternId": "Semgrep_rust.lang.security.ssl-verify-none.ssl-verify-none" + }, + { + "patternId": "Semgrep_rust.lang.security.rustls-dangerous.rustls-dangerous" + }, + { + "patternId": "Semgrep_rust.lang.security.reqwest-set-sensitive.reqwest-set-sensitive" + }, + { + "patternId": "Semgrep_rust.lang.security.reqwest-accept-invalid.reqwest-accept-invalid" + }, + { + "patternId": "Semgrep_rust.lang.security.insecure-hashes.insecure-hashes" + }, + { + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe" + }, + { + "patternId": "Semgrep_rust.lang.security.args.args" + }, + { + "patternId": "Semgrep_rust.lang.security.args-os.args-os" + }, + { + "patternId": "Semgrep_ruby.rails.security.injection.tainted-url-host.tainted-url-host" + }, + { + "patternId": "Semgrep_ruby.rails.security.injection.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_ruby.rails.security.injection.raw-html-format.raw-html-format" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-validation-regex.check-validation-regex" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-unscoped-find.check-unscoped-find" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-unsafe-reflection.check-unsafe-reflection" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-unsafe-reflection-methods.check-unsafe-reflection-methods" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-sql.check-sql" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-send-file.check-send-file" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-secrets.check-secrets" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-reverse-tabnabbing.check-reverse-tabnabbing" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-render-local-file-include.check-render-local-file-include" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-regex-dos.check-regex-dos" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-redirect-to.check-redirect-to" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-rails-session-secret-handling.check-rails-session-secret-handling" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-rails-secret-yaml.check-rails-secret-yaml" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-permit-attributes-high.check-permit-attributes-high" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-http-verb-confusion.check-http-verb-confusion" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-dynamic-render-local-file-include.check-dynamic-render-local-file-include" + }, + { + "patternId": "Semgrep_ruby.rails.security.brakeman.check-before-filter.check-before-filter" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xxe.xml-external-entities-enabled.xml-external-entities-enabled" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.templates.var-in-href.var-in-href" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.templates.unquoted-attribute.unquoted-attribute" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.templates.dangerous-link-to.dangerous-link-to" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.templates.avoid-raw.avoid-raw" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.templates.avoid-html-safe.avoid-html-safe" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.avoid-render-text.avoid-render-text" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.avoid-render-dynamic-path.avoid-render-dynamic-path" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.avoid-redirect.avoid-redirect" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.avoid-raw.avoid-raw" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.avoid-link-to.avoid-link-to" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.avoid-html-safe.avoid-html-safe" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.xss.avoid-content-tag.avoid-content-tag" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.sqli.ruby-pg-sqli.ruby-pg-sqli" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.rails-skip-forgery-protection.rails-skip-forgery-protection" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.avoid-tainted-shell-call.avoid-tainted-shell-call" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.avoid-tainted-http-request.avoid-tainted-http-request" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.avoid-tainted-ftp-call.avoid-tainted-ftp-call" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.avoid-tainted-file-access.avoid-tainted-file-access" + }, + { + "patternId": "Semgrep_ruby.rails.security.audit.avoid-session-manipulation.avoid-session-manipulation" + }, + { + "patternId": "Semgrep_ruby.lang.security.weak-hashes-sha1.weak-hashes-sha1" + }, + { + "patternId": "Semgrep_ruby.lang.security.weak-hashes-md5.weak-hashes-md5" + }, + { + "patternId": "Semgrep_ruby.lang.security.ssl-mode-no-verify.ssl-mode-no-verify" + }, + { + "patternId": "Semgrep_ruby.lang.security.no-send.bad-send" + }, + { + "patternId": "Semgrep_ruby.lang.security.no-eval.ruby-eval" + }, + { + "patternId": "Semgrep_ruby.lang.security.model-attributes-attr-accessible.model-attributes-attr-accessible" + }, + { + "patternId": "Semgrep_ruby.lang.security.model-attr-accessible.model-attr-accessible" + }, + { + "patternId": "Semgrep_ruby.lang.security.missing-csrf-protection.missing-csrf-protection" + }, + { + "patternId": "Semgrep_ruby.lang.security.md5-used-as-password.md5-used-as-password" + }, + { + "patternId": "Semgrep_ruby.lang.security.insufficient-rsa-key-size.insufficient-rsa-key-size" + }, + { + "patternId": "Semgrep_ruby.lang.security.hardcoded-secret-rsa-passphrase.hardcoded-secret-rsa-passphrase" + }, + { + "patternId": "Semgrep_ruby.lang.security.hardcoded-http-auth-in-controller.hardcoded-http-auth-in-controller" + }, + { + "patternId": "Semgrep_ruby.lang.security.force-ssl-false.force-ssl-false" + }, + { + "patternId": "Semgrep_ruby.lang.security.divide-by-zero.divide-by-zero" + }, + { + "patternId": "Semgrep_ruby.lang.security.dangerous-subshell.dangerous-subshell" + }, + { + "patternId": "Semgrep_ruby.lang.security.dangerous-open3-pipeline.dangerous-open3-pipeline" + }, + { + "patternId": "Semgrep_ruby.lang.security.dangerous-open.dangerous-open" + }, + { + "patternId": "Semgrep_ruby.lang.security.dangerous-exec.dangerous-exec" + }, + { + "patternId": "Semgrep_ruby.lang.security.cookie-serialization.cookie-serialization" + }, + { + "patternId": "Semgrep_ruby.lang.security.bad-deserialization.bad-deserialization" + }, + { + "patternId": "Semgrep_ruby.lang.security.bad-deserialization-yaml.bad-deserialization-yaml" + }, + { + "patternId": "Semgrep_ruby.lang.security.bad-deserialization-env.bad-deserialization-env" + }, + { + "patternId": "Semgrep_ruby.jwt.security.jwt-none-alg.ruby-jwt-none-alg" + }, + { + "patternId": "Semgrep_ruby.jwt.security.jwt-hardcode.ruby-jwt-hardcoded-secret" + }, + { + "patternId": "Semgrep_ruby.jwt.security.jwt-exposed-credentials.ruby-jwt-exposed-credentials" + }, + { + "patternId": "Semgrep_ruby.jwt.security.audit.jwt-decode-without-verify.ruby-jwt-decode-without-verify" + }, + { + "patternId": "Semgrep_ruby.aws-lambda.security.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_ruby.aws-lambda.security.tainted-deserialization.tainted-deserialization" + }, + { + "patternId": "Semgrep_ruby.aws-lambda.security.sequel-sqli.sequel-sqli" + }, + { + "patternId": "Semgrep_ruby.aws-lambda.security.pg-sqli.pg-sqli" + }, + { + "patternId": "Semgrep_ruby.aws-lambda.security.mysql2-sqli.mysql2-sqli" + }, + { + "patternId": "Semgrep_ruby.aws-lambda.security.activerecord-sqli.activerecord-sqli" + }, + { + "patternId": "Semgrep_python_ssl_rule-unverified-context" + }, + { + "patternId": "Semgrep_python_ssl_rule-req-no-certvalid" + }, + { + "patternId": "Semgrep_python_sql_rule-hardcoded-sql-expression" + }, + { + "patternId": "Semgrep_python_log_rule-logging-config-insecure-listen" + }, + { + "patternId": "Semgrep_python_exec_rule-exec-used" + }, + { + "patternId": "Semgrep_python_eval_rule-eval" + }, + { + "patternId": "Semgrep_python_escaping_rule-use-of-mako-templates" + }, + { + "patternId": "Semgrep_python_escaping_rule-jinja2-autoescape-false" + }, + { + "patternId": "Semgrep_python_escaping_rule-django" + }, + { + "patternId": "Semgrep_python_django_rule-django-rawsql-used" + }, + { + "patternId": "Semgrep_python_django_rule-django-extra-used" + }, + { + "patternId": "Semgrep_python_deserialization_rule-yaml-load" + }, + { + "patternId": "Semgrep_python_deserialization_rule-shelve" + }, + { + "patternId": "Semgrep_python_deserialization_rule-pickle" + }, + { + "patternId": "Semgrep_python_deserialization_rule-marshal" + }, + { + "patternId": "Semgrep_python_deserialization_rule-dill" + }, + { + "patternId": "Semgrep_python_deserialization_rule-cpickle" + }, + { + "patternId": "Semgrep_python_crypto_rule-hash-md5" + }, + { + "patternId": "Semgrep_python_crypto_rule-hash-md2" + }, + { + "patternId": "Semgrep_python_crypto_rule-crypto-hazmat-cipher-arc4" + }, + { + "patternId": "Semgrep_python_crypto_rule-crypto-hash-sha1" + }, + { + "patternId": "Semgrep_python_crypto_rule-crypto-hash-md5" + }, + { + "patternId": "Semgrep_python_crypto_rule-crypto-cipher-xor" + }, + { + "patternId": "Semgrep_python_crypto_rule-crypto-cipher-rc4" + }, + { + "patternId": "Semgrep_python_crypto_rule-crypto-cipher-rc2" + }, + { + "patternId": "Semgrep_python_crypto_rule-crypto-cipher-des" + }, + { + "patternId": "Semgrep_python.sqlalchemy.security.sqlalchemy-sql-injection.sqlalchemy-sql-injection" + }, + { + "patternId": "Semgrep_python.sqlalchemy.security.sqlalchemy-execute-raw-query.sqlalchemy-execute-raw-query" + }, + { + "patternId": "Semgrep_python.sqlalchemy.security.audit.avoid-sqlalchemy-text.avoid-sqlalchemy-text" + }, + { + "patternId": "Semgrep_python.sh.security.string-concat.string-concat" + }, + { + "patternId": "Semgrep_python.requests.security.disabled-cert-validation.disabled-cert-validation" + }, + { + "patternId": "Semgrep_python.pyramid.security.sqlalchemy-sql-injection.pyramid-sqlalchemy-sql-injection" + }, + { + "patternId": "Semgrep_python.pyramid.security.direct-use-of-response.pyramid-direct-use-of-response" + }, + { + "patternId": "Semgrep_python.pyramid.security.csrf-check-disabled-globally.pyramid-csrf-check-disabled-globally" + }, + { + "patternId": "Semgrep_python.pyramid.audit.set-cookie-secure-unsafe-value.pyramid-set-cookie-secure-unsafe-value" + }, + { + "patternId": "Semgrep_python.pyramid.audit.set-cookie-secure-unsafe-default.pyramid-set-cookie-secure-unsafe-default" + }, + { + "patternId": "Semgrep_python.pyramid.audit.set-cookie-samesite-unsafe-value.pyramid-set-cookie-samesite-unsafe-value" + }, + { + "patternId": "Semgrep_python.pyramid.audit.set-cookie-samesite-unsafe-default.pyramid-set-cookie-samesite-unsafe-default" + }, + { + "patternId": "Semgrep_python.pyramid.audit.set-cookie-httponly-unsafe-value.pyramid-set-cookie-httponly-unsafe-value" + }, + { + "patternId": "Semgrep_python.pyramid.audit.set-cookie-httponly-unsafe-default.pyramid-set-cookie-httponly-unsafe-default" + }, + { + "patternId": "Semgrep_python.pyramid.audit.csrf-origin-check-disabled.pyramid-csrf-origin-check-disabled" + }, + { + "patternId": "Semgrep_python.pyramid.audit.csrf-origin-check-disabled-globally.pyramid-csrf-origin-check-disabled-globally" + }, + { + "patternId": "Semgrep_python.pyramid.audit.csrf-check-disabled.pyramid-csrf-check-disabled" + }, + { + "patternId": "Semgrep_python.pyramid.audit.authtkt-cookie-secure-unsafe-value.pyramid-authtkt-cookie-secure-unsafe-value" + }, + { + "patternId": "Semgrep_python.pyramid.audit.authtkt-cookie-secure-unsafe-default.pyramid-authtkt-cookie-secure-unsafe-default" + }, + { + "patternId": "Semgrep_python.pyramid.audit.authtkt-cookie-samesite.pyramid-authtkt-cookie-samesite" + }, + { + "patternId": "Semgrep_python.pyramid.audit.authtkt-cookie-httponly-unsafe-value.pyramid-authtkt-cookie-httponly-unsafe-value" + }, + { + "patternId": "Semgrep_python.pyramid.audit.authtkt-cookie-httponly-unsafe-default.pyramid-authtkt-cookie-httponly-unsafe-default" + }, + { + "patternId": "Semgrep_python.pymongo.security.mongodb.mongo-client-bad-auth" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.mode-without-authentication.crypto-mode-without-authentication" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insufficient-rsa-key-size.insufficient-rsa-key-size" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insufficient-dsa-key-size.insufficient-dsa-key-size" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-hash-algorithm.insecure-hash-algorithm-sha1" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-hash-algorithm-md5.insecure-hash-algorithm-md5" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-hash-algorithm-md4.insecure-hash-algorithm-md4" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-hash-algorithm-md2.insecure-hash-algorithm-md2" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-cipher-algorithm.insecure-cipher-algorithm-xor" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-cipher-algorithm-rc4.insecure-cipher-algorithm-rc4" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-cipher-algorithm-rc2.insecure-cipher-algorithm-rc2" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-cipher-algorithm-des.insecure-cipher-algorithm-des" + }, + { + "patternId": "Semgrep_python.pycryptodome.security.insecure-cipher-algorithm-blowfish.insecure-cipher-algorithm-blowfish" + }, + { + "patternId": "Semgrep_python.lang.security.use-defused-xml.use-defused-xml" + }, + { + "patternId": "Semgrep_python.lang.security.use-defused-xml-parse.use-defused-xml-parse" + }, + { + "patternId": "Semgrep_python.lang.security.unverified-ssl-context.unverified-ssl-context" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-function.insecure-hash-function" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-algorithms.insecure-hash-algorithm-sha1" + }, + { + "patternId": "Semgrep_python.lang.security.insecure-hash-algorithms-md5.insecure-hash-algorithm-md5" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.pickle.avoid-shelve" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.pickle.avoid-pickle" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.pickle.avoid-dill" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.pickle.avoid-cpickle" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.avoid-unsafe-ruamel.avoid-unsafe-ruamel" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.avoid-pyyaml-load.avoid-pyyaml-load" + }, + { + "patternId": "Semgrep_python.lang.security.deserialization.avoid-jsonpickle.avoid-jsonpickle" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-testcapi-run-in-subinterp.dangerous-testcapi-run-in-subinterp" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-system-call.dangerous-system-call" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-subprocess-use.dangerous-subprocess-use" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-subinterpreters-run-string.dangerous-subinterpreters-run-string" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-spawn-process.dangerous-spawn-process" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-os-exec.dangerous-os-exec" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-globals-use.dangerous-globals-use" + }, + { + "patternId": "Semgrep_python.lang.security.dangerous-code-run.dangerous-interactive-code-run" + }, + { + "patternId": "Semgrep_python.lang.security.audit.weak-ssl-version.weak-ssl-version" + }, + { + "patternId": "Semgrep_python.lang.security.audit.subprocess-shell-true.subprocess-shell-true" + }, + { + "patternId": "Semgrep_python.lang.security.audit.ssl-wrap-socket-is-deprecated.ssl-wrap-socket-is-deprecated" + }, + { + "patternId": "Semgrep_python.lang.security.audit.sqli.psycopg-sqli.psycopg-sqli" + }, + { + "patternId": "Semgrep_python.lang.security.audit.sqli.pg8000-sqli.pg8000-sqli" + }, + { + "patternId": "Semgrep_python.lang.security.audit.sqli.asyncpg-sqli.asyncpg-sqli" + }, + { + "patternId": "Semgrep_python.lang.security.audit.sqli.aiopg-sqli.aiopg-sqli" + }, + { + "patternId": "Semgrep_python.lang.security.audit.regex-dos.regex_dos" + }, + { + "patternId": "Semgrep_python.lang.security.audit.python-reverse-shell.python-reverse-shell" + }, + { + "patternId": "Semgrep_python.lang.security.audit.non-literal-import.non-literal-import" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.http-not-https-connection.http-not-https-connection" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.disabled-cert-validation.disabled-cert-validation" + }, + { + "patternId": "Semgrep_python.lang.security.audit.network.bind.avoid-bind-to-all-interfaces" + }, + { + "patternId": "Semgrep_python.lang.security.audit.md5-used-as-password.md5-used-as-password" + }, + { + "patternId": "Semgrep_python.lang.security.audit.logging.logger-credential-leak.python-logger-credential-disclosure" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-with-http.request-with-http" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-session-with-http.request-session-with-http" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-transport.requests.request-session-http-in-with-context.request-session-http-in-with-context" + }, + { + "patternId": "Semgrep_python.lang.security.audit.insecure-file-permissions.insecure-file-permissions" + }, + { + "patternId": "Semgrep_python.lang.security.audit.formatted-sql-query.formatted-sql-query" + }, + { + "patternId": "Semgrep_python.lang.security.audit.exec-detected.exec-detected" + }, + { + "patternId": "Semgrep_python.lang.security.audit.eval-detected.eval-detected" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-testcapi-run-in-subinterp-tainted-env-args.dangerous-testcapi-run-in-subinterp-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-testcapi-run-in-subinterp-audit.dangerous-testcapi-run-in-subinterp-audit" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-system-call-tainted-env-args.dangerous-system-call-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-system-call-audit.dangerous-system-call-audit" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-subprocess-use-tainted-env-args.dangerous-subprocess-use-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-subprocess-use-audit.dangerous-subprocess-use-audit" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-subinterpreters-run-string-tainted-env-args.dangerous-subinterpreters-run-string-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-subinterpreters-run-string-audit.dangerous-subinterpreters-run-string-audit" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-spawn-process-tainted-env-args.dangerous-spawn-process-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-spawn-process-audit.dangerous-spawn-process-audit" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-os-exec-tainted-env-args.dangerous-os-exec-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-os-exec-audit.dangerous-os-exec-audit" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-code-run-tainted-env-args.dangerous-interactive-code-run-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-code-run-audit.dangerous-interactive-code-run-audit" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-shell-tainted-env-args.dangerous-asyncio-shell-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-shell-audit.dangerous-asyncio-shell-audit" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-exec-tainted-env-args.dangerous-asyncio-exec-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-create-exec-tainted-env-args.dangerous-asyncio-create-exec-tainted-env-args" + }, + { + "patternId": "Semgrep_python.lang.security.audit.dangerous-asyncio-create-exec-audit.dangerous-asyncio-create-exec-audit" + }, + { + "patternId": "Semgrep_python.lang.correctness.tempfile.mktemp.tempfile-insecure" + }, + { + "patternId": "Semgrep_python.jwt.security.unverified-jwt-decode.unverified-jwt-decode" + }, + { + "patternId": "Semgrep_python.jwt.security.jwt-none-alg.jwt-python-none-alg" + }, + { + "patternId": "Semgrep_python.jwt.security.jwt-hardcode.jwt-python-hardcoded-secret" + }, + { + "patternId": "Semgrep_python.jwt.security.jwt-exposed-credentials.jwt-python-exposed-credentials" + }, + { + "patternId": "Semgrep_python.jinja2.security.audit.missing-autoescape-disabled.missing-autoescape-disabled" + }, + { + "patternId": "Semgrep_python.jinja2.security.audit.autoescape-disabled-false.incorrect-autoescape-disabled" + }, + { + "patternId": "Semgrep_python.flask.security.unsanitized-input.response-contains-unsanitized-input" + }, + { + "patternId": "Semgrep_python.flask.security.secure-static-file-serve.avoid_send_file_without_path_sanitization" + }, + { + "patternId": "Semgrep_python.flask.security.open-redirect.open-redirect" + }, + { + "patternId": "Semgrep_python.flask.security.insecure-deserialization.insecure-deserialization" + }, + { + "patternId": "Semgrep_python.flask.security.injection.user-exec.exec-injection" + }, + { + "patternId": "Semgrep_python.flask.security.injection.user-eval.eval-injection" + }, + { + "patternId": "Semgrep_python.flask.security.injection.tainted-url-host.tainted-url-host" + }, + { + "patternId": "Semgrep_python.flask.security.injection.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_python.flask.security.injection.subprocess-injection.subprocess-injection" + }, + { + "patternId": "Semgrep_python.flask.security.injection.ssrf-requests.ssrf-requests" + }, + { + "patternId": "Semgrep_python.flask.security.injection.raw-html-concat.raw-html-format" + }, + { + "patternId": "Semgrep_python.flask.security.injection.path-traversal-open.path-traversal-open" + }, + { + "patternId": "Semgrep_python.flask.security.injection.os-system-injection.os-system-injection" + }, + { + "patternId": "Semgrep_python.flask.security.injection.nan-injection.nan-injection" + }, + { + "patternId": "Semgrep_python.flask.security.injection.csv-writer-injection.csv-writer-injection" + }, + { + "patternId": "Semgrep_python.flask.security.hashids-with-flask-secret.hashids-with-flask-secret" + }, + { + "patternId": "Semgrep_python.flask.security.dangerous-template-string.dangerous-template-string" + }, + { + "patternId": "Semgrep_python.flask.security.audit.wtf-csrf-disabled.flask-wtf-csrf-disabled" + }, + { + "patternId": "Semgrep_python.flask.security.audit.render-template-string.render-template-string" + }, + { + "patternId": "Semgrep_python.flask.security.audit.directly-returned-format-string.directly-returned-format-string" + }, + { + "patternId": "Semgrep_python.flask.security.audit.debug-enabled.debug-enabled" + }, + { + "patternId": "Semgrep_python.flask.security.audit.app-run-security-config.avoid_using_app_run_directly" + }, + { + "patternId": "Semgrep_python.flask.security.audit.app-run-param-config.avoid_app_run_with_bad_host" + }, + { + "patternId": "Semgrep_python.docker.security.audit.docker-arbitrary-container-run.docker-arbitrary-container-run" + }, + { + "patternId": "Semgrep_python.django.security.passwords.use-none-for-password-default.use-none-for-password-default" + }, + { + "patternId": "Semgrep_python.django.security.passwords.password-empty-string.password-empty-string" + }, + { + "patternId": "Semgrep_python.django.security.nan-injection.nan-injection" + }, + { + "patternId": "Semgrep_python.django.security.locals-as-template-context.locals-as-template-context" + }, + { + "patternId": "Semgrep_python.django.security.injection.tainted-url-host.tainted-url-host" + }, + { + "patternId": "Semgrep_python.django.security.injection.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_python.django.security.injection.ssrf.ssrf-injection-urllib.ssrf-injection-urllib" + }, + { + "patternId": "Semgrep_python.django.security.injection.ssrf.ssrf-injection-requests.ssrf-injection-requests" + }, + { + "patternId": "Semgrep_python.django.security.injection.sql.sql-injection-using-raw.sql-injection-using-raw" + }, + { + "patternId": "Semgrep_python.django.security.injection.sql.sql-injection-using-db-cursor-execute.sql-injection-db-cursor-execute" + }, + { + "patternId": "Semgrep_python.django.security.injection.sql.sql-injection-rawsql.sql-injection-using-rawsql" + }, + { + "patternId": "Semgrep_python.django.security.injection.sql.sql-injection-extra.sql-injection-using-extra-where" + }, + { + "patternId": "Semgrep_python.django.security.injection.request-data-write.request-data-write" + }, + { + "patternId": "Semgrep_python.django.security.injection.request-data-fileresponse.request-data-fileresponse" + }, + { + "patternId": "Semgrep_python.django.security.injection.reflected-data-httpresponsebadrequest.reflected-data-httpresponsebadrequest" + }, + { + "patternId": "Semgrep_python.django.security.injection.reflected-data-httpresponse.reflected-data-httpresponse" + }, + { + "patternId": "Semgrep_python.django.security.injection.raw-html-format.raw-html-format" + }, + { + "patternId": "Semgrep_python.django.security.injection.path-traversal.path-traversal-open.path-traversal-open" + }, + { + "patternId": "Semgrep_python.django.security.injection.path-traversal.path-traversal-join.path-traversal-join" + }, + { + "patternId": "Semgrep_python.django.security.injection.path-traversal.path-traversal-file-name.path-traversal-file-name" + }, + { + "patternId": "Semgrep_python.django.security.injection.open-redirect.open-redirect" + }, + { + "patternId": "Semgrep_python.django.security.injection.email.xss-send-mail-html-message.xss-send-mail-html-message" + }, + { + "patternId": "Semgrep_python.django.security.injection.email.xss-html-email-body.xss-html-email-body" + }, + { + "patternId": "Semgrep_python.django.security.injection.csv-writer-injection.csv-writer-injection" + }, + { + "patternId": "Semgrep_python.django.security.injection.command.subprocess-injection.subprocess-injection" + }, + { + "patternId": "Semgrep_python.django.security.injection.command.command-injection-os-system.command-injection-os-system" + }, + { + "patternId": "Semgrep_python.django.security.injection.code.user-exec.user-exec" + }, + { + "patternId": "Semgrep_python.django.security.injection.code.user-exec-format-string.user-exec-format-string" + }, + { + "patternId": "Semgrep_python.django.security.injection.code.user-eval.user-eval" + }, + { + "patternId": "Semgrep_python.django.security.injection.code.user-eval-format-string.user-eval-format-string" + }, + { + "patternId": "Semgrep_python.django.security.injection.code.globals-misuse-code-execution.globals-misuse-code-execution" + }, + { + "patternId": "Semgrep_python.django.security.hashids-with-django-secret.hashids-with-django-secret" + }, + { + "patternId": "Semgrep_python.django.security.globals-as-template-context.globals-as-template-context" + }, + { + "patternId": "Semgrep_python.django.security.django-using-request-post-after-is-valid.django-using-request-post-after-is-valid" + }, + { + "patternId": "Semgrep_python.django.security.django-no-csrf-token.django-no-csrf-token" + }, + { + "patternId": "Semgrep_python.django.security.audit.xss.global-autoescape-off.global-autoescape-off" + }, + { + "patternId": "Semgrep_python.django.security.audit.xss.direct-use-of-httpresponse.direct-use-of-httpresponse" + }, + { + "patternId": "Semgrep_python.django.security.audit.xss.context-autoescape-off.context-autoescape-off" + }, + { + "patternId": "Semgrep_python.django.security.audit.xss.class-extends-safestring.class-extends-safestring" + }, + { + "patternId": "Semgrep_python.django.security.audit.raw-query.avoid-raw-sql" + }, + { + "patternId": "Semgrep_python.django.security.audit.query-set-extra.avoid-query-set-extra" + }, + { + "patternId": "Semgrep_python.django.security.audit.extends-custom-expression.extends-custom-expression" + }, + { + "patternId": "Semgrep_python.django.security.audit.custom-expression-as-sql.custom-expression-as-sql" + }, + { + "patternId": "Semgrep_python.django.security.audit.csrf-exempt.no-csrf-exempt" + }, + { + "patternId": "Semgrep_python.django.security.audit.avoid-insecure-deserialization.avoid-insecure-deserialization" + }, + { + "patternId": "Semgrep_python.distributed.security.require-encryption" + }, + { + "patternId": "Semgrep_python.cryptography.security.mode-without-authentication.crypto-mode-without-authentication" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-rsa-key-size.insufficient-rsa-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-ec-key-size.insufficient-ec-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.insufficient-dsa-key-size.insufficient-dsa-key-size" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-hash-algorithms.insecure-hash-algorithm-sha1" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-hash-algorithms-md5.insecure-hash-algorithm-md5" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-mode-ecb.insecure-cipher-mode-ecb" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms.insecure-cipher-algorithm-idea" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms-blowfish.insecure-cipher-algorithm-blowfish" + }, + { + "patternId": "Semgrep_python.cryptography.security.insecure-cipher-algorithms-arc4.insecure-cipher-algorithm-arc4" + }, + { + "patternId": "Semgrep_python.cryptography.security.empty-aes-key.empty-aes-key" + }, + { + "patternId": "Semgrep_python.boto3.security.hardcoded-token.hardcoded-token" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.tainted-pickle-deserialization.tainted-pickle-deserialization" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.tainted-html-string.tainted-html-string" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.tainted-html-response.tainted-html-response" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.tainted-code-exec.tainted-code-exec" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.sqlalchemy-sqli.sqlalchemy-sqli" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.pymysql-sqli.pymysql-sqli" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.pymssql-sqli.pymssql-sqli" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.psycopg-sqli.psycopg-sqli" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.mysql-sqli.mysql-sqli" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.dynamodb-filter-injection.dynamodb-filter-injection" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.dangerous-system-call.dangerous-system-call" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.dangerous-subprocess-use.dangerous-subprocess-use" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.dangerous-spawn-process.dangerous-spawn-process" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.dangerous-asyncio-shell.dangerous-asyncio-shell" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.dangerous-asyncio-exec.dangerous-asyncio-exec" + }, + { + "patternId": "Semgrep_python.aws-lambda.security.dangerous-asyncio-create-exec.dangerous-asyncio-create-exec" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.ruby-stdlib.openuri-request.openuri-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.ruby-stdlib.net-telnet-request.net-telnet-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.ruby-stdlib.net-http-request.net-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.ruby-stdlib.net-ftp-request.net-ftp-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.ruby-stdlib.http-client-requests.http-client-requests" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.js-node.telnet-request.telnet-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.js-node.rest-http-client-support.rest-http-client-support" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.js-node.http-request.http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.js-node.ftp-request.ftp-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.js-node.disallow-old-tls-versions2.disallow-old-tls-versions2" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.js-node.disallow-old-tls-versions1.disallow-old-tls-versions1" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.js-node.bypass-tls-verification.bypass-tls-verification" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.unirest-http-request.unirest-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.tls-renegotiation.tls-renegotiation" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.telnet-request.telnet-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.httpurlconnection-http-request.httpurlconnection-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.httpget-http-request.httpget-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.httpclient-http-request.httpclient-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.http-components-request.http-components-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.ftp-request.ftp-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.disallow-old-tls-versions2.disallow-old-tls-versions2" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.disallow-old-tls-versions1.disallow-old-tls-versions1" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-stdlib.bypass-tls-verification.bypass-tls-verification" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-spring.spring-http-request.spring-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-spring.spring-ftp-request.spring-ftp-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.java-spring.bypass-tls-verification.bypass-tls-verification" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.telnet-request.telnet-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.sling-http-request.sling-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.http-request.http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.http-customized-request.http-customized-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.grequests-http-request.grequests-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.gorequest-http-request.gorequest-http-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.ftp-request.ftp-request" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.disallow-old-tls-versions.disallow-old-tls-versions" + }, + { + "patternId": "Semgrep_problem-based-packs.insecure-transport.go-stdlib.bypass-tls-verification.bypass-tls-verification" + }, + { + "patternId": "Semgrep_php.wordpress-plugins.security.audit.wp-sql-injection-audit.wp-sql-injection-audit" + }, + { + "patternId": "Semgrep_php.wordpress-plugins.security.audit.wp-php-object-injection-audit.wp-php-object-injection-audit" + }, + { + "patternId": "Semgrep_php.wordpress-plugins.security.audit.wp-file-inclusion-audit.wp-file-inclusion-audit" + }, + { + "patternId": "Semgrep_php.wordpress-plugins.security.audit.wp-command-execution-audit.wp-command-execution-audit" + }, + { + "patternId": "Semgrep_php.wordpress-plugins.security.audit.wp-code-execution-audit.wp-code-execution-audit" + }, + { + "patternId": "Semgrep_php.symfony.security.audit.symfony-csrf-protection-disabled.symfony-csrf-protection-disabled" + }, + { + "patternId": "Semgrep_php.laravel.security.laravel-unsafe-validator.laravel-unsafe-validator" + }, + { + "patternId": "Semgrep_php.laravel.security.laravel-sql-injection.laravel-sql-injection" + }, + { + "patternId": "Semgrep_php.laravel.security.laravel-blade-form-missing-csrf.laravel-blade-form-missing-csrf" + }, + { + "patternId": "Semgrep_php.laravel.security.laravel-api-route-sql-injection.laravel-api-route-sql-injection" + }, + { + "patternId": "Semgrep_php.lang.security.unserialize-use.unserialize-use" + }, + { + "patternId": "Semgrep_php.lang.security.tainted-exec.tainted-exec" + }, + { + "patternId": "Semgrep_php.lang.security.redirect-to-request-uri.redirect-to-request-uri" + }, + { + "patternId": "Semgrep_php.lang.security.phpinfo-use.phpinfo-use" + }, + { + "patternId": "Semgrep_php.lang.security.php-ssrf.php-ssrf" + }, + { + "patternId": "Semgrep_php.lang.security.openssl-cbc-static-iv.openssl-cbc-static-iv" + }, + { + "patternId": "Semgrep_php.lang.security.md5-used-as-password.md5-used-as-password" + }, + { + "patternId": "Semgrep_php.lang.security.mb-ereg-replace-eval.mb-ereg-replace-eval" + }, + { + "patternId": "Semgrep_php.lang.security.injection.tainted-url-host.tainted-url-host" + }, + { + "patternId": "Semgrep_php.lang.security.injection.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_php.lang.security.injection.tainted-session.tainted-session" + }, + { + "patternId": "Semgrep_php.lang.security.injection.tainted-object-instantiation.tainted-object-instantiation" + }, + { + "patternId": "Semgrep_php.lang.security.injection.tainted-filename.tainted-filename" + }, + { + "patternId": "Semgrep_php.lang.security.injection.echoed-request.echoed-request" + }, + { + "patternId": "Semgrep_php.lang.security.file-inclusion.file-inclusion" + }, + { + "patternId": "Semgrep_php.lang.security.exec-use.exec-use" + }, + { + "patternId": "Semgrep_php.lang.security.eval-use.eval-use" + }, + { + "patternId": "Semgrep_php.lang.security.deserialization.extract-user-data" + }, + { + "patternId": "Semgrep_php.lang.security.curl-ssl-verifypeer-off.curl-ssl-verifypeer-off" + }, + { + "patternId": "Semgrep_php.lang.security.backticks-use.backticks-use" + }, + { + "patternId": "Semgrep_php.lang.security.audit.assert-use-audit.assert-use-audit" + }, + { + "patternId": "Semgrep_php.lang.security.assert-use.assert-use" + }, + { + "patternId": "Semgrep_php.doctrine.security.audit.doctrine-orm-dangerous-query.doctrine-orm-dangerous-query" + }, + { + "patternId": "Semgrep_php.doctrine.security.audit.doctrine-dbal-dangerous-query.doctrine-dbal-dangerous-query" + }, + { + "patternId": "Semgrep_kotlin.lang.security.weak-rsa.use-of-weak-rsa-key" + }, + { + "patternId": "Semgrep_kotlin.lang.security.use-of-sha1.use-of-sha1" + }, + { + "patternId": "Semgrep_kotlin.lang.security.use-of-md5.use-of-md5" + }, + { + "patternId": "Semgrep_kotlin.lang.security.unencrypted-socket.unencrypted-socket" + }, + { + "patternId": "Semgrep_kotlin.lang.security.no-null-cipher.no-null-cipher" + }, + { + "patternId": "Semgrep_kotlin.lang.security.gcm-detection.gcm-detection" + }, + { + "patternId": "Semgrep_kotlin.lang.security.ecb-cipher.ecb-cipher" + }, + { + "patternId": "Semgrep_kotlin.lang.security.command-injection-formatted-runtime-call.command-injection-formatted-runtime-call" + }, + { + "patternId": "Semgrep_kotlin.lang.security.anonymous-ldap-bind.anonymous-ldap-bind" + }, + { + "patternId": "Semgrep_json.aws.security.wildcard-assume-role.wildcard-assume-role" + }, + { + "patternId": "Semgrep_json.aws.security.public-s3-policy-statement.public-s3-policy-statement" + }, + { + "patternId": "Semgrep_json.aws.security.public-s3-bucket.public-s3-bucket" + }, + { + "patternId": "Semgrep_javascript_xss_rule-mustache-escape" + }, + { + "patternId": "Semgrep_javascript_require_rule-non-literal-require" + }, + { + "patternId": "Semgrep_javascript_react_rule-dangerouslysetinnerhtml" + }, + { + "patternId": "Semgrep_javascript_pathtraversal_rule-non-literal-fs-filename" + }, + { + "patternId": "Semgrep_javascript_exec_rule-child-process" + }, + { + "patternId": "Semgrep_javascript_eval_rule-eval-with-expression" + }, + { + "patternId": "Semgrep_javascript_dos_rule-non-literal-regexp" + }, + { + "patternId": "Semgrep_javascript.xml2json.security.audit.xml2json-xxe.xml2json-xxe" + }, + { + "patternId": "Semgrep_javascript.wkhtmltopdf.security.audit.wkhtmltopdf-injection.wkhtmltopdf-injection" + }, + { + "patternId": "Semgrep_javascript.wkhtmltoimage.security.audit.wkhtmltoimage-injection.wkhtmltoimage-injection" + }, + { + "patternId": "Semgrep_javascript.vue.security.audit.xss.templates.avoid-v-html.avoid-v-html" + }, + { + "patternId": "Semgrep_javascript.vm2.security.audit.vm2-context-injection.vm2-context-injection" + }, + { + "patternId": "Semgrep_javascript.vm2.security.audit.vm2-code-injection.vm2-code-injection" + }, + { + "patternId": "Semgrep_javascript.thenify.security.audit.multiargs-code-execution.multiargs-code-execution" + }, + { + "patternId": "Semgrep_javascript.shelljs.security.shelljs-exec-injection.shelljs-exec-injection" + }, + { + "patternId": "Semgrep_javascript.sequelize.security.audit.sequelize-tls-disabled-cert-validation.sequelize-tls-disabled-cert-validation" + }, + { + "patternId": "Semgrep_javascript.sequelize.security.audit.sequelize-raw-query.sequelize-raw-query" + }, + { + "patternId": "Semgrep_javascript.sequelize.security.audit.sequelize-injection-express.express-sequelize-injection" + }, + { + "patternId": "Semgrep_javascript.sandbox.security.audit.sandbox-code-injection.sandbox-code-injection" + }, + { + "patternId": "Semgrep_javascript.puppeteer.security.audit.puppeteer-setcontent-injection.puppeteer-setcontent-injection" + }, + { + "patternId": "Semgrep_javascript.puppeteer.security.audit.puppeteer-goto-injection.puppeteer-goto-injection" + }, + { + "patternId": "Semgrep_javascript.puppeteer.security.audit.puppeteer-evaluate-code-injection.puppeteer-evaluate-code-injection" + }, + { + "patternId": "Semgrep_javascript.playwright.security.audit.playwright-goto-injection.playwright-goto-injection" + }, + { + "patternId": "Semgrep_javascript.playwright.security.audit.playwright-addinitscript-code-injection.playwright-addinitscript-code-injection" + }, + { + "patternId": "Semgrep_javascript.phantom.security.audit.phantom-injection.phantom-injection" + }, + { + "patternId": "Semgrep_javascript.passport-jwt.security.passport-hardcode.hardcoded-passport-secret" + }, + { + "patternId": "Semgrep_javascript.node-expat.security.audit.expat-xxe.expat-xxe" + }, + { + "patternId": "Semgrep_javascript.monaco-editor.security.audit.monaco-hover-htmlsupport.monaco-hover-htmlsupport" + }, + { + "patternId": "Semgrep_javascript.lang.security.spawn-git-clone.spawn-git-clone" + }, + { + "patternId": "Semgrep_javascript.lang.security.detect-eval-with-expression.detect-eval-with-expression" + }, + { + "patternId": "Semgrep_javascript.lang.security.detect-child-process.detect-child-process" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.unsafe-dynamic-method.unsafe-dynamic-method" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.sqli.node-postgres-sqli.node-postgres-sqli" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.sqli.node-mysql-sqli.node-mysql-sqli" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.sqli.node-mssql-sqli.node-mssql-sqli" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.sqli.node-knex-sqli.node-knex-sqli" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.spawn-shell-true.spawn-shell-true" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.prototype-pollution.prototype-pollution-loop.prototype-pollution-loop" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.prototype-pollution.prototype-pollution-assignment.prototype-pollution-assignment" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.path-traversal.path-join-resolve-traversal.path-join-resolve-traversal" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.md5-used-as-password.md5-used-as-password" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.detect-non-literal-require.detect-non-literal-require" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.dangerous-spawn-shell.dangerous-spawn-shell" + }, + { + "patternId": "Semgrep_javascript.lang.security.audit.code-string-concat.code-string-concat" + }, + { + "patternId": "Semgrep_javascript.jsonwebtoken.security.jwt-none-alg.jwt-none-alg" + }, + { + "patternId": "Semgrep_javascript.jsonwebtoken.security.jwt-hardcode.hardcoded-jwt-secret" + }, + { + "patternId": "Semgrep_javascript.jsonwebtoken.security.audit.jwt-decode-without-verify.jwt-decode-without-verify" + }, + { + "patternId": "Semgrep_javascript.jose.security.jwt-none-alg.jwt-none-alg" + }, + { + "patternId": "Semgrep_javascript.jose.security.jwt-hardcode.hardcoded-jwt-secret" + }, + { + "patternId": "Semgrep_javascript.intercom.security.audit.intercom-settings-user-identifier-without-user-hash.intercom-settings-user-identifier-without-user-hash" + }, + { + "patternId": "Semgrep_javascript.grpc.security.grpc-nodejs-insecure-connection.grpc-nodejs-insecure-connection" + }, + { + "patternId": "Semgrep_javascript.fbjs.security.audit.insecure-createnodesfrommarkup.insecure-createnodesfrommarkup" + }, + { + "patternId": "Semgrep_javascript.express.security.x-frame-options-misconfiguration.x-frame-options-misconfiguration" + }, + { + "patternId": "Semgrep_javascript.express.security.require-request.require-request" + }, + { + "patternId": "Semgrep_javascript.express.security.injection.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_javascript.express.security.injection.raw-html-format.raw-html-format" + }, + { + "patternId": "Semgrep_javascript.express.security.express-xml2json-xxe.express-xml2json-xxe" + }, + { + "patternId": "Semgrep_javascript.express.security.express-wkhtml-injection.express-wkhtmltopdf-injection" + }, + { + "patternId": "Semgrep_javascript.express.security.express-wkhtml-injection.express-wkhtmltoimage-injection" + }, + { + "patternId": "Semgrep_javascript.express.security.express-vm2-injection.express-vm2-injection" + }, + { + "patternId": "Semgrep_javascript.express.security.express-vm-injection.express-vm-injection" + }, + { + "patternId": "Semgrep_javascript.express.security.express-sandbox-injection.express-sandbox-code-injection" + }, + { + "patternId": "Semgrep_javascript.express.security.express-puppeteer-injection.express-puppeteer-injection" + }, + { + "patternId": "Semgrep_javascript.express.security.express-phantom-injection.express-phantom-injection" + }, + { + "patternId": "Semgrep_javascript.express.security.express-jwt-hardcoded-secret.express-jwt-hardcoded-secret" + }, + { + "patternId": "Semgrep_javascript.express.security.express-insecure-template-usage.express-insecure-template-usage" + }, + { + "patternId": "Semgrep_javascript.express.security.express-expat-xxe.express-expat-xxe" + }, + { + "patternId": "Semgrep_javascript.express.security.cors-misconfiguration.cors-misconfiguration" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.xss.pug.explicit-unescape.template-explicit-unescape" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.xss.pug.and-attributes.template-and-attributes" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.xss.mustache.explicit-unescape.template-explicit-unescape" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.xss.ejs.explicit-unescape.template-explicit-unescape" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.xss.direct-response-write.direct-response-write" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.res-render-injection.res-render-injection" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-xml2json-xxe-event.express-xml2json-xxe-event" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-third-party-object-deserialization.express-third-party-object-deserialization" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-ssrf.express-ssrf" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-session-hardcoded-secret.express-session-hardcoded-secret" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-res-sendfile.express-res-sendfile" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-path-join-resolve-traversal.express-path-join-resolve-traversal" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-open-redirect.express-open-redirect" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-libxml-vm-noent.express-libxml-vm-noent" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-libxml-noent.express-libxml-noent" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-jwt-not-revoked.express-jwt-not-revoked" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-cookie-settings.express-cookie-session-no-secure" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-cookie-settings.express-cookie-session-no-path" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-cookie-settings.express-cookie-session-no-httponly" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-cookie-settings.express-cookie-session-no-expires" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-cookie-settings.express-cookie-session-no-domain" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-cookie-settings.express-cookie-session-default-name" + }, + { + "patternId": "Semgrep_javascript.express.security.audit.express-check-directory-listing.express-check-directory-listing" + }, + { + "patternId": "Semgrep_javascript.deno.security.audit.deno-dangerous-run.deno-dangerous-run" + }, + { + "patternId": "Semgrep_javascript.chrome-remote-interface.security.audit.chrome-remote-interface-compilescript-injection.chrome-remote-interface-compilescript-injection" + }, + { + "patternId": "Semgrep_javascript.browser.security.wildcard-postmessage-configuration.wildcard-postmessage-configuration" + }, + { + "patternId": "Semgrep_javascript.browser.security.raw-html-join.raw-html-join" + }, + { + "patternId": "Semgrep_javascript.browser.security.raw-html-concat.raw-html-concat" + }, + { + "patternId": "Semgrep_javascript.browser.security.open-redirect.js-open-redirect" + }, + { + "patternId": "Semgrep_javascript.browser.security.open-redirect-from-function.js-open-redirect-from-function" + }, + { + "patternId": "Semgrep_javascript.browser.security.insufficient-postmessage-origin-validation.insufficient-postmessage-origin-validation" + }, + { + "patternId": "Semgrep_javascript.browser.security.insecure-innerhtml.insecure-innerhtml" + }, + { + "patternId": "Semgrep_javascript.browser.security.insecure-document-method.insecure-document-method" + }, + { + "patternId": "Semgrep_javascript.browser.security.eval-detected.eval-detected" + }, + { + "patternId": "Semgrep_javascript.browser.security.dom-based-xss.dom-based-xss" + }, + { + "patternId": "Semgrep_javascript.bluebird.security.audit.tofastproperties-code-execution.tofastproperties-code-execution" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.vm-runincontext-injection.vm-runincontext-injection" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.tainted-html-string.tainted-html-string" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.tainted-html-response.tainted-html-response" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.tainted-eval.tainted-eval" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.sequelize-sqli.sequelize-sqli" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.pg-sqli.pg-sqli" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.mysql-sqli.mysql-sqli" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.knex-sqli.knex-sqli" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.dynamodb-request-object.dynamodb-request-object" + }, + { + "patternId": "Semgrep_javascript.aws-lambda.security.detect-child-process.detect-child-process" + }, + { + "patternId": "Semgrep_javascript.argon2.security.unsafe-argon2-config.unsafe-argon2-config" + }, + { + "patternId": "Semgrep_javascript.apollo.security.apollo-axios-ssrf.apollo-axios-ssrf" + }, + { + "patternId": "Semgrep_javascript.angular.security.detect-angular-trust-as-method.detect-angular-trust-as-method" + }, + { + "patternId": "Semgrep_javascript.angular.security.detect-angular-sce-disabled.detect-angular-sce-disabled" + }, + { + "patternId": "Semgrep_javascript.angular.security.detect-angular-element-taint.detect-angular-element-taint" + }, + { + "patternId": "Semgrep_java_xxe_rule-XMLStreamRdr" + }, + { + "patternId": "Semgrep_java_xxe_rule-XMLRdr" + }, + { + "patternId": "Semgrep_java_xss_rule-XSSReqParamToServletWriter" + }, + { + "patternId": "Semgrep_java_xss_rule-WicketXSS" + }, + { + "patternId": "Semgrep_java_xpathi_rule-XpathInjection" + }, + { + "patternId": "Semgrep_java_xml_rule-XsltTransform" + }, + { + "patternId": "Semgrep_java_xml_rule-XmlDecoder" + }, + { + "patternId": "Semgrep_java_xml_rule-SAMLIgnoreComments" + }, + { + "patternId": "Semgrep_java_templateinjection_rule-TemplateInjection" + }, + { + "patternId": "Semgrep_java_strings_rule-NormalizeAfterValidation" + }, + { + "patternId": "Semgrep_java_strings_rule-ModifyAfterValidation" + }, + { + "patternId": "Semgrep_java_strings_rule-FormatStringManipulation" + }, + { + "patternId": "Semgrep_java_strings_rule-BadHexConversion" + }, + { + "patternId": "Semgrep_java_ssrf_rule-SSRF" + }, + { + "patternId": "Semgrep_java_smtp_rule-SmtpClient" + }, + { + "patternId": "Semgrep_java_smtp_rule-InsecureSmtp" + }, + { + "patternId": "Semgrep_java_script_rule-ScriptInjection" + }, + { + "patternId": "Semgrep_java_perm_rule-OverlyPermissiveFilePermissionInline" + }, + { + "patternId": "Semgrep_java_perm_rule-DangerousPermissions" + }, + { + "patternId": "Semgrep_java_password_rule-HardcodePassword" + }, + { + "patternId": "Semgrep_java_password_rule-EmptyDBPassword" + }, + { + "patternId": "Semgrep_java_password_rule-ConstantDBPassword" + }, + { + "patternId": "Semgrep_java_inject_rule-SqlInjection" + }, + { + "patternId": "Semgrep_java_inject_rule-SpotbugsPathTraversalAbsolute" + }, + { + "patternId": "Semgrep_java_inject_rule-OgnlInjection" + }, + { + "patternId": "Semgrep_java_inject_rule-LDAPInjection" + }, + { + "patternId": "Semgrep_java_inject_rule-HttpParameterPollution" + }, + { + "patternId": "Semgrep_java_inject_rule-ELInjection" + }, + { + "patternId": "Semgrep_java_inject_rule-CommandInjection" + }, + { + "patternId": "Semgrep_java_file_rule-FilenameUtils" + }, + { + "patternId": "Semgrep_java_file_rule-FileUploadFileName" + }, + { + "patternId": "Semgrep_java_csrf_rule-SpringCSRFDisabled" + }, + { + "patternId": "Semgrep_java_crypto_rule-WeakTLSProtocolVersion" + }, + { + "patternId": "Semgrep_java_crypto_rule-WeakMessageDigest" + }, + { + "patternId": "Semgrep_java_crypto_rule-RsaNoPadding" + }, + { + "patternId": "Semgrep_java_crypto_rule-NullCipher" + }, + { + "patternId": "Semgrep_java_crypto_rule-CipherPaddingOracle" + }, + { + "patternId": "Semgrep_java_crypto_rule-CipherECBMode" + }, + { + "patternId": "Semgrep_java_crypto_rule-CipherDESedeInsecure" + }, + { + "patternId": "Semgrep_java_crypto_rule-CipherDESInsecure" + }, + { + "patternId": "Semgrep_java_cookie_rule-RequestParamToHeader" + }, + { + "patternId": "Semgrep_java_cookie_rule-HttpResponseSplitting" + }, + { + "patternId": "Semgrep_java.spring.security.injection.tainted-url-host.tainted-url-host" + }, + { + "patternId": "Semgrep_java.spring.security.injection.tainted-system-command.tainted-system-command" + }, + { + "patternId": "Semgrep_java.spring.security.injection.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_java.spring.security.injection.tainted-html-string.tainted-html-string" + }, + { + "patternId": "Semgrep_java.spring.security.injection.tainted-file-path.tainted-file-path" + }, + { + "patternId": "Semgrep_java.spring.security.audit.spring-unvalidated-redirect.spring-unvalidated-redirect" + }, + { + "patternId": "Semgrep_java.spring.security.audit.spring-sqli.spring-sqli" + }, + { + "patternId": "Semgrep_java.spring.security.audit.spring-csrf-disabled.spring-csrf-disabled" + }, + { + "patternId": "Semgrep_java.spring.security.audit.spring-actuator-non-health-enabled.spring-actuator-dangerous-endpoints-enabled" + }, + { + "patternId": "Semgrep_java.spring.security.audit.spring-actuator-non-health-enabled-yaml.spring-actuator-dangerous-endpoints-enabled-yaml" + }, + { + "patternId": "Semgrep_java.spring.security.audit.spring-actuator-fully-enabled.spring-actuator-fully-enabled" + }, + { + "patternId": "Semgrep_java.spring.security.audit.spring-actuator-fully-enabled-yaml.spring-actuator-fully-enabled-yaml" + }, + { + "patternId": "Semgrep_java.rmi.security.server-dangerous-object-deserialization.server-dangerous-object-deserialization" + }, + { + "patternId": "Semgrep_java.rmi.security.server-dangerous-class-deserialization.server-dangerous-class-deserialization" + }, + { + "patternId": "Semgrep_java.mongodb.security.injection.audit.mongodb-nosqli.mongodb-nosqli" + }, + { + "patternId": "Semgrep_java.lang.security.xmlinputfactory-possible-xxe.xmlinputfactory-possible-xxe" + }, + { + "patternId": "Semgrep_java.lang.security.xmlinputfactory-external-entities-enabled.xmlinputfactory-external-entities-enabled" + }, + { + "patternId": "Semgrep_java.lang.security.use-snakeyaml-constructor.use-snakeyaml-constructor" + }, + { + "patternId": "Semgrep_java.lang.security.servletresponse-writer-xss.servletresponse-writer-xss" + }, + { + "patternId": "Semgrep_java.lang.security.jackson-unsafe-deserialization.jackson-unsafe-deserialization" + }, + { + "patternId": "Semgrep_java.lang.security.insecure-jms-deserialization.insecure-jms-deserialization" + }, + { + "patternId": "Semgrep_java.lang.security.httpservlet-path-traversal.httpservlet-path-traversal" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xxe.transformerfactory-dtds-not-disabled.transformerfactory-dtds-not-disabled" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xxe.saxparserfactory-disallow-doctype-decl-missing.saxparserfactory-disallow-doctype-decl-missing" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xxe.documentbuilderfactory-external-parameter-entities-true.documentbuilderfactory-external-parameter-entities-true" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xxe.documentbuilderfactory-external-general-entities-true.documentbuilderfactory-external-general-entities-true" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xxe.documentbuilderfactory-disallow-doctype-decl-missing.documentbuilderfactory-disallow-doctype-decl-missing" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xxe.documentbuilderfactory-disallow-doctype-decl-false.documentbuilderfactory-disallow-doctype-decl-false" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xssrequestwrapper-is-insecure.xssrequestwrapper-is-insecure" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xss.no-direct-response-writer.no-direct-response-writer" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xss.jsp.use-jstl-escaping.use-jstl-escaping" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xss.jsp.use-escapexml.use-escapexml" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xss.jsf.autoescape-disabled.autoescape-disabled" + }, + { + "patternId": "Semgrep_java.lang.security.audit.xml-decoder.xml-decoder" + }, + { + "patternId": "Semgrep_java.lang.security.audit.weak-ssl-context.weak-ssl-context" + }, + { + "patternId": "Semgrep_java.lang.security.audit.unvalidated-redirect.unvalidated-redirect" + }, + { + "patternId": "Semgrep_java.lang.security.audit.unsafe-reflection.unsafe-reflection" + }, + { + "patternId": "Semgrep_java.lang.security.audit.tainted-xpath-from-http-request.tainted-xpath-from-http-request" + }, + { + "patternId": "Semgrep_java.lang.security.audit.tainted-session-from-http-request.tainted-session-from-http-request" + }, + { + "patternId": "Semgrep_java.lang.security.audit.tainted-ldapi-from-http-request.tainted-ldapi-from-http-request" + }, + { + "patternId": "Semgrep_java.lang.security.audit.tainted-env-from-http-request.tainted-env-from-http-request" + }, + { + "patternId": "Semgrep_java.lang.security.audit.tainted-cmd-from-http-request.tainted-cmd-from-http-request" + }, + { + "patternId": "Semgrep_java.lang.security.audit.sqli.vertx-sqli.vertx-sqli" + }, + { + "patternId": "Semgrep_java.lang.security.audit.sqli.turbine-sqli.turbine-sqli" + }, + { + "patternId": "Semgrep_java.lang.security.audit.sqli.tainted-sql-from-http-request.tainted-sql-from-http-request" + }, + { + "patternId": "Semgrep_java.lang.security.audit.sqli.jpa-sqli.jpa-sqli" + }, + { + "patternId": "Semgrep_java.lang.security.audit.sqli.jdo-sqli.jdo-sqli" + }, + { + "patternId": "Semgrep_java.lang.security.audit.sqli.jdbc-sqli.jdbc-sqli" + }, + { + "patternId": "Semgrep_java.lang.security.audit.sqli.hibernate-sqli.hibernate-sqli" + }, + { + "patternId": "Semgrep_java.lang.security.audit.script-engine-injection.script-engine-injection" + }, + { + "patternId": "Semgrep_java.lang.security.audit.permissive-cors.permissive-cors" + }, + { + "patternId": "Semgrep_java.lang.security.audit.ognl-injection.ognl-injection" + }, + { + "patternId": "Semgrep_java.lang.security.audit.object-deserialization.object-deserialization" + }, + { + "patternId": "Semgrep_java.lang.security.audit.md5-used-as-password.md5-used-as-password" + }, + { + "patternId": "Semgrep_java.lang.security.audit.ldap-injection.ldap-injection" + }, + { + "patternId": "Semgrep_java.lang.security.audit.ldap-entry-poisoning.ldap-entry-poisoning" + }, + { + "patternId": "Semgrep_java.lang.security.audit.jdbc-sql-formatted-string.jdbc-sql-formatted-string" + }, + { + "patternId": "Semgrep_java.lang.security.audit.java-reverse-shell.java-reverse-shell" + }, + { + "patternId": "Semgrep_java.lang.security.audit.insecure-smtp-connection.insecure-smtp-connection" + }, + { + "patternId": "Semgrep_java.lang.security.audit.http-response-splitting.http-response-splitting" + }, + { + "patternId": "Semgrep_java.lang.security.audit.formatted-sql-string.formatted-sql-string" + }, + { + "patternId": "Semgrep_java.lang.security.audit.el-injection.el-injection" + }, + { + "patternId": "Semgrep_java.lang.security.audit.dangerous-groovy-shell.dangerous-groovy-shell" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.weak-rsa.use-of-weak-rsa-key" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.weak-random.weak-random" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.use-of-sha1.use-of-sha1" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.use-of-rc4.use-of-rc4" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.use-of-rc2.use-of-rc2" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.use-of-md5.use-of-md5" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.use-of-md5-digest-utils.use-of-md5-digest-utils" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.use-of-default-aes.use-of-default-aes" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.use-of-blowfish.use-of-blowfish" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.use-of-aes-ecb.use-of-aes-ecb" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.unencrypted-socket.unencrypted-socket" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.ssl.insecure-trust-manager.insecure-trust-manager" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.ssl.insecure-hostname-verifier.insecure-hostname-verifier" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.ssl.avoid-implementing-custom-digests.avoid-implementing-custom-digests" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.rsa-no-padding.rsa-no-padding" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.no-static-initialization-vector.no-static-initialization-vector" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.no-null-cipher.no-null-cipher" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.gcm-nonce-reuse.gcm-nonce-reuse" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.gcm-detection.gcm-detection" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.ecb-cipher.ecb-cipher" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.desede-is-deprecated.desede-is-deprecated" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crypto.des-is-deprecated.des-is-deprecated" + }, + { + "patternId": "Semgrep_java.lang.security.audit.crlf-injection-logs.crlf-injection-logs" + }, + { + "patternId": "Semgrep_java.lang.security.audit.command-injection-process-builder.command-injection-process-builder" + }, + { + "patternId": "Semgrep_java.lang.security.audit.command-injection-formatted-runtime-call.command-injection-formatted-runtime-call" + }, + { + "patternId": "Semgrep_java.lang.security.audit.cbc-padding-oracle.cbc-padding-oracle" + }, + { + "patternId": "Semgrep_java.lang.security.audit.blowfish-insufficient-key-size.blowfish-insufficient-key-size" + }, + { + "patternId": "Semgrep_java.jjwt.security.jwt-none-alg.jjwt-none-alg" + }, + { + "patternId": "Semgrep_java.jboss.security.session_sqli.find-sql-string-concatenation" + }, + { + "patternId": "Semgrep_java.jax-rs.security.jax-rs-path-traversal.jax-rs-path-traversal" + }, + { + "patternId": "Semgrep_java.jax-rs.security.insecure-resteasy.insecure-resteasy-deserialization" + }, + { + "patternId": "Semgrep_java.jax-rs.security.insecure-resteasy.default-resteasy-provider-abuse" + }, + { + "patternId": "Semgrep_java.java-jwt.security.jwt-none-alg.java-jwt-none-alg" + }, + { + "patternId": "Semgrep_java.java-jwt.security.jwt-hardcode.java-jwt-hardcoded-secret" + }, + { + "patternId": "Semgrep_java.java-jwt.security.audit.jwt-decode-without-verify.java-jwt-decode-without-verify" + }, + { + "patternId": "Semgrep_java.aws-lambda.security.tainted-sqli.tainted-sqli" + }, + { + "patternId": "Semgrep_java.aws-lambda.security.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_java.android.security.exported_activity.exported_activity" + }, + { + "patternId": "Semgrep_go.template.security.ssti.go-ssti" + }, + { + "patternId": "Semgrep_go.otto.security.audit.dangerous-execution.dangerous-execution" + }, + { + "patternId": "Semgrep_go.lang.security.zip.path-traversal-inside-zip-extraction" + }, + { + "patternId": "Semgrep_go.lang.security.injection.tainted-url-host.tainted-url-host" + }, + { + "patternId": "Semgrep_go.lang.security.injection.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_go.lang.security.injection.raw-html-format.raw-html-format" + }, + { + "patternId": "Semgrep_go.lang.security.filepath-clean-misuse.filepath-clean-misuse" + }, + { + "patternId": "Semgrep_go.lang.security.audit.xss.template-html-does-not-escape.unsafe-template-type" + }, + { + "patternId": "Semgrep_go.lang.security.audit.xss.no-printf-in-responsewriter.no-printf-in-responsewriter" + }, + { + "patternId": "Semgrep_go.lang.security.audit.xss.no-interpolation-js-template-string.no-interpolation-js-template-string" + }, + { + "patternId": "Semgrep_go.lang.security.audit.xss.no-fprintf-to-responsewriter.no-fprintf-to-responsewriter" + }, + { + "patternId": "Semgrep_go.lang.security.audit.xss.no-direct-write-to-responsewriter.no-direct-write-to-responsewriter" + }, + { + "patternId": "Semgrep_go.lang.security.audit.unsafe.use-of-unsafe-block" + }, + { + "patternId": "Semgrep_go.lang.security.audit.unsafe-reflect-by-name.unsafe-reflect-by-name" + }, + { + "patternId": "Semgrep_go.lang.security.audit.sqli.pgx-sqli.pgx-sqli" + }, + { + "patternId": "Semgrep_go.lang.security.audit.sqli.pg-sqli.pg-sqli" + }, + { + "patternId": "Semgrep_go.lang.security.audit.sqli.pg-orm-sqli.pg-orm-sqli" + }, + { + "patternId": "Semgrep_go.lang.security.audit.sqli.gosql-sqli.gosql-sqli" + }, + { + "patternId": "Semgrep_go.lang.security.audit.reflect-makefunc.reflect-makefunc" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.wip-xss-using-responsewriter-and-printf.wip-xss-using-responsewriter-and-printf" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.use-tls.use-tls" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.unescaped-data-in-url.unescaped-data-in-url" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.unescaped-data-in-js.unescaped-data-in-js" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.fs-directory-listing.fs-directory-listing" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.formatted-template-string.formatted-template-string" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.dynamic-httptrace-clienttrace.dynamic-httptrace-clienttrace" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.cookie-missing-secure.cookie-missing-secure" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.cookie-missing-httponly.cookie-missing-httponly" + }, + { + "patternId": "Semgrep_go.lang.security.audit.net.bind_all.avoid-bind-to-all-interfaces" + }, + { + "patternId": "Semgrep_go.lang.security.audit.md5-used-as-password.md5-used-as-password" + }, + { + "patternId": "Semgrep_go.lang.security.audit.database.string-formatted-query.string-formatted-query" + }, + { + "patternId": "Semgrep_go.lang.security.audit.dangerous-syscall-exec.dangerous-syscall-exec" + }, + { + "patternId": "Semgrep_go.lang.security.audit.dangerous-exec-command.dangerous-exec-command" + }, + { + "patternId": "Semgrep_go.lang.security.audit.dangerous-exec-cmd.dangerous-exec-cmd" + }, + { + "patternId": "Semgrep_go.lang.security.audit.dangerous-command-write.dangerous-command-write" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.use_of_weak_rsa_key.use-of-weak-rsa-key" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.use_of_weak_crypto.use-of-sha1" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.use_of_weak_crypto.use-of-rc4" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.use_of_weak_crypto.use-of-md5" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.use_of_weak_crypto.use-of-des" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.tls.tls-with-insecure-cipher" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.ssl.ssl-v3-is-insecure" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.missing-ssl-minversion.missing-ssl-minversion" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.math_random.math-random-used" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.insecure_ssh.avoid-ssh-insecure-ignore-host-key" + }, + { + "patternId": "Semgrep_go.lang.security.audit.crypto.bad_imports.insecure-module-used" + }, + { + "patternId": "Semgrep_go.jwt-go.security.jwt.hardcoded-jwt-key" + }, + { + "patternId": "Semgrep_go.jwt-go.security.jwt-none-alg.jwt-go-none-algorithm" + }, + { + "patternId": "Semgrep_go.jwt-go.security.audit.jwt-parse-unverified.jwt-go-parse-unverified" + }, + { + "patternId": "Semgrep_go.grpc.security.grpc-server-insecure-connection.grpc-server-insecure-connection" + }, + { + "patternId": "Semgrep_go.grpc.security.grpc-client-insecure-connection.grpc-client-insecure-connection" + }, + { + "patternId": "Semgrep_go.gorm.security.audit.gorm-dangerous-methods-usage.gorm-dangerous-method-usage" + }, + { + "patternId": "Semgrep_go.gorilla.security.audit.websocket-missing-origin-check.websocket-missing-origin-check" + }, + { + "patternId": "Semgrep_go.gorilla.security.audit.session-cookie-missing-secure.session-cookie-missing-secure" + }, + { + "patternId": "Semgrep_go.gorilla.security.audit.session-cookie-missing-httponly.session-cookie-missing-httponly" + }, + { + "patternId": "Semgrep_go.gorilla.security.audit.handler-assignment-from-multiple-sources.handler-assignment-from-multiple-sources" + }, + { + "patternId": "Semgrep_go.aws-lambda.security.tainted-sql-string.tainted-sql-string" + }, + { + "patternId": "Semgrep_go.aws-lambda.security.database-sqli.database-sqli" + }, + { + "patternId": "Semgrep_generic.visualforce.security.ncino.xml.visualforceapiversion.visualforce-page-api-version" + }, + { + "patternId": "Semgrep_generic.visualforce.security.ncino.xml.cspheaderattribute.csp-header-attribute" + }, + { + "patternId": "Semgrep_generic.visualforce.security.ncino.vf.xssfromunescapedurlparam.xss-from-unescaped-url-param" + }, + { + "patternId": "Semgrep_generic.visualforce.security.ncino.html.usesriforcdns.use-sri-for-cdns" + }, + { + "patternId": "Semgrep_generic.secrets.security.google-maps-apikeyleak.google-maps-apikeyleak" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-username-and-password-in-uri.detected-username-and-password-in-uri" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-twilio-api-key.detected-twilio-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-telegram-bot-api-key.detected-telegram-bot-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-stripe-restricted-api-key.detected-stripe-restricted-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-stripe-api-key.detected-stripe-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-ssh-password.detected-ssh-password" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-square-oauth-secret.detected-square-oauth-secret" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-square-access-token.detected-square-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-sonarqube-docs-api-key.detected-sonarqube-docs-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-softlayer-api-key.detected-softlayer-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-snyk-api-key.detected-snyk-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-slack-webhook.detected-slack-webhook" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-slack-token.detected-slack-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-sendgrid-api-key.detected-sendgrid-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-sauce-token.detected-sauce-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-private-key.detected-private-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-pgp-private-key-block.detected-pgp-private-key-block" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-paypal-braintree-access-token.detected-paypal-braintree-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-npm-registry-auth-token.detected-npm-registry-auth-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-mailgun-api-key.detected-mailgun-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-mailchimp-api-key.detected-mailchimp-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-kolide-api-key.detected-kolide-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-jwt-token.detected-jwt-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-heroku-api-key.detected-heroku-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-google-oauth-access-token.detected-google-oauth-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-google-gcm-service-account.detected-google-gcm-service-account" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-google-cloud-api-key.detected-google-cloud-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-google-api-key.detected-google-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-github-token.detected-github-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-generic-secret.detected-generic-secret" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-generic-api-key.detected-generic-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-facebook-oauth.detected-facebook-oauth" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-facebook-access-token.detected-facebook-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-etc-shadow.detected-etc-shadow" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-aws-session-token.detected-aws-session-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-aws-secret-access-key.detected-aws-secret-access-key" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-aws-access-key-id-value.detected-aws-access-key-id-value" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-artifactory-token.detected-artifactory-token" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-artifactory-password.detected-artifactory-password" + }, + { + "patternId": "Semgrep_generic.secrets.security.detected-amazon-mws-auth-token.detected-amazon-mws-auth-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.zendesk-secret-key.zendesk-secret-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.yandex-aws-access-token.yandex-aws-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.yandex-api-key.yandex-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.yandex-access-token.yandex-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.vault-service-token.vault-service-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.vault-batch-token.vault-batch-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.typeform-api-token.typeform-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.twitter-api-secret.twitter-api-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.twitter-api-key.twitter-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.twitter-access-token.twitter-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.twitter-access-secret.twitter-access-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.twitch-api-token.twitch-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.twilio-api-key.twilio-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.travisci-access-token.travisci-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.telegram-bot-api-token.telegram-bot-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.sumologic-access-token.sumologic-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.sumologic-access-id.sumologic-access-id" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.stripe-access-token.stripe-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.squarespace-access-token.squarespace-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.square-access-token.square-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.snyk-api-token.snyk-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.slack-webhook-url.slack-webhook-url" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.slack-user-token.slack-user-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.slack-legacy-workspace-token.slack-legacy-workspace-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.slack-legacy-token.slack-legacy-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.slack-legacy-bot-token.slack-legacy-bot-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.slack-config-access-token.slack-config-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.slack-bot-token.slack-bot-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.slack-app-token.slack-app-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.sidekiq-sensitive-url.sidekiq-sensitive-url" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.sidekiq-secret.sidekiq-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.shopify-shared-secret.shopify-shared-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.shopify-private-app-access-token.shopify-private-app-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.shopify-custom-access-token.shopify-custom-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.shopify-access-token.shopify-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.shippo-api-token.shippo-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.sentry-access-token.sentry-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.sendinblue-api-token.sendinblue-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.sendgrid-api-token.sendgrid-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.sendbird-access-token.sendbird-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.scalingo-api-token.scalingo-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.rubygems-api-token.rubygems-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.readme-api-token.readme-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.rapidapi-access-token.rapidapi-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.pypi-upload-token.pypi-upload-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.pulumi-api-token.pulumi-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.private-key.private-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.prefect-api-token.prefect-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.postman-api-token.postman-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.planetscale-password.planetscale-password" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.planetscale-oauth-token.planetscale-oauth-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.planetscale-api-token.planetscale-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.plaid-secret-key.plaid-secret-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.plaid-client-id.plaid-client-id" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.plaid-api-token.plaid-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.openai-api-key.openai-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.okta-access-token.okta-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.nytimes-access-token.nytimes-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.npm-access-token.npm-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.new-relic-user-api-key.new-relic-user-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.new-relic-user-api-id.new-relic-user-api-id" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.new-relic-browser-api-token.new-relic-browser-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.netlify-access-token.netlify-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.microsoft-teams-webhook.microsoft-teams-webhook" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.messagebird-client-id.messagebird-client-id" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.messagebird-api-token.messagebird-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.mattermost-access-token.mattermost-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.mailgun-signing-key.mailgun-signing-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.mailgun-private-api-token.mailgun-private-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.mailchimp-api-key.mailchimp-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.lob-api-key.lob-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.linkedin-client-secret.linkedin-client-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.linkedin-client-id.linkedin-client-id" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.linear-client-secret.linear-client-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.linear-api-key.linear-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.launchdarkly-access-token.launchdarkly-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.kucoin-secret-key.kucoin-secret-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.kucoin-access-token.kucoin-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.kraken-access-token.kraken-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.jwt.jwt" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.jfrog-identity-token.jfrog-identity-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.jfrog-api-key.jfrog-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.intercom-api-key.intercom-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.infracost-api-token.infracost-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.huggingface-organization-api-token.huggingface-organization-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.huggingface-access-token.huggingface-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.hubspot-api-key.hubspot-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.heroku-api-key.heroku-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.hashicorp-tf-password.hashicorp-tf-password" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.hashicorp-tf-api-token.hashicorp-tf-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.grafana-service-account-token.grafana-service-account-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.grafana-cloud-api-token.grafana-cloud-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.grafana-api-key.grafana-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.gitter-access-token.gitter-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.gitlab-rrt.gitlab-rrt" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.gitlab-ptt.gitlab-ptt" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.gitlab-pat.gitlab-pat" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.github-refresh-token.github-refresh-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.github-pat.github-pat" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.github-oauth.github-oauth" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.github-fine-grained-pat.github-fine-grained-pat" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.github-app-token.github-app-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.gcp-api-key.gcp-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.freshbooks-access-token.freshbooks-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.frameio-api-token.frameio-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.flutterwave-secret-key.flutterwave-secret-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.flutterwave-encryption-key.flutterwave-encryption-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.flickr-access-token.flickr-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.finnhub-access-token.finnhub-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.finicity-client-secret.finicity-client-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.finicity-api-token.finicity-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.fastly-api-token.fastly-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.facebook.facebook" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.etsy-access-token.etsy-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.easypost-test-api-token.easypost-test-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.easypost-api-token.easypost-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.dynatrace-api-token.dynatrace-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.duffel-api-token.duffel-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.dropbox-short-lived-api-token.dropbox-short-lived-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.dropbox-long-lived-api-token.dropbox-long-lived-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.dropbox-api-token.dropbox-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.droneci-access-token.droneci-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.doppler-api-token.doppler-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.discord-client-secret.discord-client-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.discord-api-token.discord-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.digitalocean-refresh-token.digitalocean-refresh-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.digitalocean-pat.digitalocean-pat" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.digitalocean-access-token.digitalocean-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.defined-networking-api-token.defined-networking-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.datadog-access-token.datadog-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.databricks-api-token.databricks-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.confluent-secret-key.confluent-secret-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.confluent-access-token.confluent-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.coinbase-access-token.coinbase-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.codecov-access-token.codecov-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.clojars-api-token.clojars-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.bittrex-secret-key.bittrex-secret-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.bittrex-access-key.bittrex-access-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.bitbucket-client-secret.bitbucket-client-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.bitbucket-client-id.bitbucket-client-id" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.beamer-api-token.beamer-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.aws-access-token.aws-access-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.authress-service-client-access-key.authress-service-client-access-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.atlassian-api-token.atlassian-api-token" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.asana-client-secret.asana-client-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.asana-client-id.asana-client-id" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.alibaba-secret-key.alibaba-secret-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.alibaba-access-key-id.alibaba-access-key-id" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.algolia-api-key.algolia-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.airtable-api-key.airtable-api-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.age-secret-key.age-secret-key" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.adobe-client-secret.adobe-client-secret" + }, + { + "patternId": "Semgrep_generic.secrets.gitleaks.adobe-client-id.adobe-client-id" + }, + { + "patternId": "Semgrep_elixir.lang.correctness.atom-exhaustion.atom_exhaustion" + }, + { + "patternId": "Semgrep_dockerfile.security.no-sudo-in-dockerfile.no-sudo-in-dockerfile" + }, + { + "patternId": "Semgrep_dockerfile.security.missing-user.missing-user" + }, + { + "patternId": "Semgrep_dockerfile.security.missing-user-entrypoint.missing-user-entrypoint" + }, + { + "patternId": "Semgrep_dockerfile.security.last-user-is-root.last-user-is-root" + }, + { + "patternId": "Semgrep_csharp_other_rule-UnsafeXSLTSettingUsed" + }, + { + "patternId": "Semgrep_csharp_injection_rule-XPathInjection" + }, + { + "patternId": "Semgrep_csharp_injection_rule-SQLInjection" + }, + { + "patternId": "Semgrep_csharp_injection_rule-LdapInjection" + }, + { + "patternId": "Semgrep_csharp_injection_rule-CommandInjection" + }, + { + "patternId": "Semgrep_csharp_endpoint_rule-UnvalidatedRedirect" + }, + { + "patternId": "Semgrep_csharp_deserialization_rule-InsecureDeserialization" + }, + { + "patternId": "Semgrep_csharp_csrf_rule-Csrf" + }, + { + "patternId": "Semgrep_csharp_crypto_rule-WeakRNG" + }, + { + "patternId": "Semgrep_csharp_crypto_rule-WeakCipherAlgorithm" + }, + { + "patternId": "Semgrep_csharp_crypto_rule-CertificateValidationDisabled" + }, + { + "patternId": "Semgrep_csharp.razor.security.html-raw-json.html-raw-json" + }, + { + "patternId": "Semgrep_csharp.lang.security.xxe.xmltextreader-unsafe-defaults.xmltextreader-unsafe-defaults" + }, + { + "patternId": "Semgrep_csharp.lang.security.xxe.xmlreadersettings-unsafe-parser-override.xmlreadersettings-unsafe-parser-override" + }, + { + "patternId": "Semgrep_csharp.lang.security.xxe.xmldocument-unsafe-parser-override.xmldocument-unsafe-parser-override" + }, + { + "patternId": "Semgrep_csharp.lang.security.stacktrace-disclosure.stacktrace-disclosure" + }, + { + "patternId": "Semgrep_csharp.lang.security.ssrf.web-request.ssrf" + }, + { + "patternId": "Semgrep_csharp.lang.security.ssrf.web-client.ssrf" + }, + { + "patternId": "Semgrep_csharp.lang.security.ssrf.rest-client.ssrf" + }, + { + "patternId": "Semgrep_csharp.lang.security.ssrf.http-client.ssrf" + }, + { + "patternId": "Semgrep_csharp.lang.security.sqli.csharp-sqli.csharp-sqli" + }, + { + "patternId": "Semgrep_csharp.lang.security.regular-expression-dos.regular-expression-dos.regular-expression-dos" + }, + { + "patternId": "Semgrep_csharp.lang.security.regular-expression-dos.regular-expression-dos-infinite-timeout.regular-expression-dos-infinite-timeout" + }, + { + "patternId": "Semgrep_csharp.lang.security.insecure-deserialization.soap-formatter.insecure-soapformatter-deserialization" + }, + { + "patternId": "Semgrep_csharp.lang.security.insecure-deserialization.newtonsoft.insecure-newtonsoft-deserialization" + }, + { + "patternId": "Semgrep_csharp.lang.security.insecure-deserialization.net-data-contract.insecure-netdatacontract-deserialization" + }, + { + "patternId": "Semgrep_csharp.lang.security.insecure-deserialization.los-formatter.insecure-losformatter-deserialization" + }, + { + "patternId": "Semgrep_csharp.lang.security.insecure-deserialization.javascript-serializer.insecure-javascriptserializer-deserialization" + }, + { + "patternId": "Semgrep_csharp.lang.security.insecure-deserialization.insecure-typefilterlevel-full.insecure-typefilterlevel-full" + }, + { + "patternId": "Semgrep_csharp.lang.security.insecure-deserialization.fs-pickler.insecure-fspickler-deserialization" + }, + { + "patternId": "Semgrep_csharp.lang.security.insecure-deserialization.binary-formatter.insecure-binaryformatter-deserialization" + }, + { + "patternId": "Semgrep_csharp.lang.security.injections.os-command.os-command-injection" + }, + { + "patternId": "Semgrep_csharp.lang.security.http.http-listener-wildcard-bindings.http-listener-wildcard-bindings" + }, + { + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine" + }, + { + "patternId": "Semgrep_csharp.lang.security.cryptography.x509-subject-name-validation.x509-subject-name-validation" + }, + { + "patternId": "Semgrep_csharp.lang.security.cryptography.unsigned-security-token.unsigned-security-token" + }, + { + "patternId": "Semgrep_csharp.lang.security.ad.jwt-tokenvalidationparameters-no-expiry-validation.jwt-tokenvalidationparameters-no-expiry-validation" + }, + { + "patternId": "Semgrep_csharp.lang.correctness.sslcertificatetrust.sslcertificatetrust-handshake-no-trust.correctness-sslcertificatetrust-handshake-no-trust" + }, + { + "patternId": "Semgrep_csharp.lang.correctness.regioninfo.regioninfo-interop.correctness-regioninfo-interop" + }, + { + "patternId": "Semgrep_csharp.lang.correctness.double.double-epsilon-equality.correctness-double-epsilon-equality" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.use_weak_rsa_encryption_padding.use_weak_rsa_encryption_padding" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.use_weak_rng_for_keygeneration.use_weak_rng_for_keygeneration" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.use_ecb_mode.use_ecb_mode" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.use_deprecated_cipher_algorithm.use_deprecated_cipher_algorithm" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.razor-template-injection.razor-template-injection" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.mvc-missing-antiforgery.mvc-missing-antiforgery" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.audit.xpath-injection.xpath-injection" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.audit.razor-use-of-htmlstring.razor-use-of-htmlstring" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.audit.open-directory-listing.open-directory-listing" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.audit.missing-or-broken-authorization.missing-or-broken-authorization" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.audit.mass-assignment.mass-assignment" + }, + { + "patternId": "Semgrep_csharp.dotnet.security.audit.ldap-injection.ldap-injection" + }, + { + "patternId": "Semgrep_clojure.security.clojure-read-string.read-string-unsafe.read-string-unsafe" + }, + { + "patternId": "Semgrep_clojure.lang.security.use-of-sha1.use-of-sha1" + }, + { + "patternId": "Semgrep_clojure.lang.security.use-of-md5.use-of-md5" + }, + { + "patternId": "Semgrep_clojure.lang.security.documentbuilderfactory-xxe.documentbuilderfactory-xxe" + }, + { + "patternId": "Semgrep_clojure.lang.security.command-injection-shell-call.command-injection-shell-call" + }, + { + "patternId": "Semgrep_c.lang.security.use-after-free.use-after-free" + }, + { + "patternId": "Semgrep_c.lang.security.random-fd-exhaustion.random-fd-exhaustion" + }, + { + "patternId": "Semgrep_c.lang.security.insecure-use-string-copy-fn.insecure-use-string-copy-fn" + }, + { + "patternId": "Semgrep_c.lang.security.insecure-use-printf-fn.insecure-use-printf-fn" + }, + { + "patternId": "Semgrep_c.lang.security.insecure-use-gets-fn.insecure-use-gets-fn" + }, + { + "patternId": "Semgrep_c.lang.security.function-use-after-free.function-use-after-free" + }, + { + "patternId": "Semgrep_bash.curl.security.curl-pipe-bash.curl-pipe-bash" + }, + { + "patternId": "Semgrep_bash.curl.security.curl-eval.curl-eval" + } + ] + }, + { + "toolId": "Lizard", + "patterns": [ + { + "patternId": "Lizard_file-nloc-medium", + "parameters": { + "threshold": "500" + } + }, + { + "patternId": "Lizard_parameter-count-medium", + "parameters": { + "threshold": "8" + } + }, + { + "patternId": "Lizard_nloc-medium", + "parameters": { + "threshold": "50" + } + } + ] + }, + { + "toolId": "Hadolint", + "patterns": [ + { + "patternId": "Hadolint_DL3021" + }, + { + "patternId": "Hadolint_DL3024" + }, + { + "patternId": "Hadolint_DL3023" + }, + { + "patternId": "Hadolint_DL3022" + }, + { + "patternId": "Hadolint_DL4003" + }, + { + "patternId": "Hadolint_DL3006" + }, + { + "patternId": "Hadolint_DL3007" + }, + { + "patternId": "Hadolint_SC1007" + }, + { + "patternId": "Hadolint_SC2164" + }, + { + "patternId": "Hadolint_SC1035" + }, + { + "patternId": "Hadolint_SC1065" + }, + { + "patternId": "Hadolint_SC1083" + }, + { + "patternId": "Hadolint_SC2140" + }, + { + "patternId": "Hadolint_SC1097" + }, + { + "patternId": "Hadolint_SC2015" + }, + { + "patternId": "Hadolint_SC2035" + }, + { + "patternId": "Hadolint_DL3014" + }, + { + "patternId": "Hadolint_DL3008" + }, + { + "patternId": "Hadolint_SC1066" + }, + { + "patternId": "Hadolint_DL3012" + }, + { + "patternId": "Hadolint_DL3002" + }, + { + "patternId": "Hadolint_SC2026" + }, + { + "patternId": "Hadolint_SC1045" + }, + { + "patternId": "Hadolint_SC1095" + }, + { + "patternId": "Hadolint_DL4004" + }, + { + "patternId": "Hadolint_SC1081" + }, + { + "patternId": "Hadolint_SC2028" + }, + { + "patternId": "Hadolint_SC1077" + }, + { + "patternId": "Hadolint_SC1087" + }, + { + "patternId": "Hadolint_SC1010" + }, + { + "patternId": "Hadolint_DL3001" + }, + { + "patternId": "Hadolint_SC1079" + }, + { + "patternId": "Hadolint_DL3003" + }, + { + "patternId": "Hadolint_SC2002" + }, + { + "patternId": "Hadolint_DL3004" + }, + { + "patternId": "Hadolint_SC1068" + }, + { + "patternId": "Hadolint_SC1078" + }, + { + "patternId": "Hadolint_DL4000" + }, + { + "patternId": "Hadolint_DL3000" + }, + { + "patternId": "Hadolint_DL3009" + }, + { + "patternId": "Hadolint_DL3011" + }, + { + "patternId": "Hadolint_SC1098" + }, + { + "patternId": "Hadolint_SC2046" + }, + { + "patternId": "Hadolint_SC2086" + }, + { + "patternId": "Hadolint_SC1086" + }, + { + "patternId": "Hadolint_SC2154" + }, + { + "patternId": "Hadolint_SC1018" + }, + { + "patternId": "Hadolint_DL3013" + }, + { + "patternId": "Hadolint_DL3015" + } + ] + }, + { + "toolId": "SonarCSharp", + "patterns": [ + { + "patternId": "SonarCSharp_S6781" + }, + { + "patternId": "SonarCSharp_S6377" + }, + { + "patternId": "SonarCSharp_S5344" + }, + { + "patternId": "SonarCSharp_S4347" + }, + { + "patternId": "SonarCSharp_S6444" + }, + { + "patternId": "SonarCSharp_S4502" + }, + { + "patternId": "SonarCSharp_S2115" + }, + { + "patternId": "SonarCSharp_S5753" + }, + { + "patternId": "SonarCSharp_S5332" + }, + { + "patternId": "SonarCSharp_S4423" + }, + { + "patternId": "SonarCSharp_S3329" + }, + { + "patternId": "SonarCSharp_S2612" + }, + { + "patternId": "SonarCSharp_S2257" + }, + { + "patternId": "SonarCSharp_S2053" + }, + { + "patternId": "SonarCSharp_S5773" + }, + { + "patternId": "SonarCSharp_S5766" + }, + { + "patternId": "SonarCSharp_S5659" + }, + { + "patternId": "SonarCSharp_S2755" + }, + { + "patternId": "SonarCSharp_S5542" + }, + { + "patternId": "SonarCSharp_S4830" + }, + { + "patternId": "SonarCSharp_S5547" + }, + { + "patternId": "SonarCSharp_S2068", + "parameters": { + "credentialWords": "password, passwd, pwd, passphrase" + } + }, + { + "patternId": "SonarCSharp_S2245" + }, + { + "patternId": "SonarCSharp_S4790" + }, + { + "patternId": "SonarCSharp_S5042" + }, + { + "patternId": "SonarCSharp_S4426" + }, + { + "patternId": "SonarCSharp_S4433" + }, + { + "patternId": "SonarCSharp_S1215" + }, + { + "patternId": "SonarCSharp_S3610" + }, + { + "patternId": "SonarCSharp_S1764" + }, + { + "patternId": "SonarCSharp_S3459" + }, + { + "patternId": "SonarCSharp_S2934" + }, + { + "patternId": "SonarCSharp_S131" + }, + { + "patternId": "SonarCSharp_S1186" + }, + { + "patternId": "SonarCSharp_S3217" + }, + { + "patternId": "SonarCSharp_S3005" + }, + { + "patternId": "SonarCSharp_S2368" + }, + { + "patternId": "SonarCSharp_S1226" + }, + { + "patternId": "SonarCSharp_S112" + }, + { + "patternId": "SonarCSharp_S2688" + }, + { + "patternId": "SonarCSharp_S3450" + }, + { + "patternId": "SonarCSharp_S2743" + }, + { + "patternId": "SonarCSharp_S3447" + }, + { + "patternId": "SonarCSharp_S2551" + }, + { + "patternId": "SonarCSharp_S3440" + }, + { + "patternId": "SonarCSharp_S3876" + }, + { + "patternId": "SonarCSharp_S1481" + }, + { + "patternId": "SonarCSharp_S1699" + }, + { + "patternId": "SonarCSharp_S2692" + }, + { + "patternId": "SonarCSharp_S2674" + }, + { + "patternId": "SonarCSharp_S2995" + }, + { + "patternId": "SonarCSharp_S2190" + }, + { + "patternId": "SonarCSharp_S3880" + }, + { + "patternId": "SonarCSharp_S2386" + }, + { + "patternId": "SonarCSharp_S3600" + }, + { + "patternId": "SonarCSharp_S3397" + }, + { + "patternId": "SonarCSharp_S3251" + }, + { + "patternId": "SonarCSharp_S3877" + }, + { + "patternId": "SonarCSharp_S3466" + }, + { + "patternId": "SonarCSharp_S2955" + }, + { + "patternId": "SonarCSharp_S127" + }, + { + "patternId": "SonarCSharp_S1210" + }, + { + "patternId": "SonarCSharp_S3443" + }, + { + "patternId": "SonarCSharp_S3216" + }, + { + "patternId": "SonarCSharp_S1871" + }, + { + "patternId": "SonarCSharp_S2996" + }, + { + "patternId": "SonarCSharp_S1994" + }, + { + "patternId": "SonarCSharp_S3263" + }, + { + "patternId": "SonarCSharp_S3456" + }, + { + "patternId": "SonarCSharp_S3449" + }, + { + "patternId": "SonarCSharp_S2583" + }, + { + "patternId": "SonarCSharp_S110", + "parameters": { + "max": "5", + "filteredClasses": "" + } + }, + { + "patternId": "SonarCSharp_S3898" + }, + { + "patternId": "SonarCSharp_S3215" + }, + { + "patternId": "SonarCSharp_S2123" + }, + { + "patternId": "SonarCSharp_S2372" + }, + { + "patternId": "SonarCSharp_S2681" + }, + { + "patternId": "SonarCSharp_S3453" + }, + { + "patternId": "SonarCSharp_S3220" + }, + { + "patternId": "SonarCSharp_S1163" + }, + { + "patternId": "SonarCSharp_S2953" + }, + { + "patternId": "SonarCSharp_S2997" + }, + { + "patternId": "SonarCSharp_S2757" + }, + { + "patternId": "SonarCSharp_S2184" + }, + { + "patternId": "SonarCSharp_S2930" + }, + { + "patternId": "SonarCSharp_S2275" + }, + { + "patternId": "SonarCSharp_S2345" + }, + { + "patternId": "SonarCSharp_S2178" + }, + { + "patternId": "SonarCSharp_S3457" + }, + { + "patternId": "SonarCSharp_S2328" + }, + { + "patternId": "SonarCSharp_S3926" + }, + { + "patternId": "SonarCSharp_S3168" + }, + { + "patternId": "SonarCSharp_S3451" + }, + { + "patternId": "SonarCSharp_S1104" + }, + { + "patternId": "SonarCSharp_S1643" + }, + { + "patternId": "SonarCSharp_S1944" + }, + { + "patternId": "SonarCSharp_S3871" + }, + { + "patternId": "SonarCSharp_S3869" + }, + { + "patternId": "SonarCSharp_S3874" + }, + { + "patternId": "SonarCSharp_S1698" + }, + { + "patternId": "SonarCSharp_S2339" + }, + { + "patternId": "SonarCSharp_S2223" + }, + { + "patternId": "SonarCSharp_S3244" + }, + { + "patternId": "SonarCSharp_S2387" + }, + { + "patternId": "SonarCSharp_S2357" + }, + { + "patternId": "SonarCSharp_S2952" + }, + { + "patternId": "SonarCSharp_S1313" + }, + { + "patternId": "SonarCSharp_S1006" + }, + { + "patternId": "SonarCSharp_S1206" + }, + { + "patternId": "SonarCSharp_S3249" + }, + { + "patternId": "SonarCSharp_S3237" + }, + { + "patternId": "SonarCSharp_S3172" + }, + { + "patternId": "SonarCSharp_S1854" + }, + { + "patternId": "SonarCSharp_S1118" + }, + { + "patternId": "SonarCSharp_S2696" + }, + { + "patternId": "SonarCSharp_S1172" + }, + { + "patternId": "SonarCSharp_S2760" + }, + { + "patternId": "SonarCSharp_S2291" + }, + { + "patternId": "SonarCSharp_S2201" + }, + { + "patternId": "SonarCSharp_S3427" + }, + { + "patternId": "SonarCSharp_S1449" + }, + { + "patternId": "SonarCSharp_S2761" + }, + { + "patternId": "SonarCSharp_S3603" + }, + { + "patternId": "SonarCSharp_S3241" + }, + { + "patternId": "SonarCSharp_S1862" + }, + { + "patternId": "SonarCSharp_S3010" + }, + { + "patternId": "SonarCSharp_S3444" + }, + { + "patternId": "SonarCSharp_S3655" + }, + { + "patternId": "SonarCSharp_S1656" + }, + { + "patternId": "SonarCSharp_S3247" + }, + { + "patternId": "SonarCSharp_S3597" + }, + { + "patternId": "SonarCSharp_S3445" + }, + { + "patternId": "SonarCSharp_S1244" + }, + { + "patternId": "SonarCSharp_S2197" + }, + { + "patternId": "SonarCSharp_S2330" + }, + { + "patternId": "SonarCSharp_S3875" + }, + { + "patternId": "SonarCSharp_S2259" + }, + { + "patternId": "SonarCSharp_S3169" + }, + { + "patternId": "SonarCSharp_S3889" + }, + { + "patternId": "SonarCSharp_S2931" + }, + { + "patternId": "SonarCSharp_S2486" + }, + { + "patternId": "SonarCSharp_S2225" + }, + { + "patternId": "SonarCSharp_S2360" + } + ] + }, + { + "toolId": "Checkov", + "patterns": [ + { + "patternId": "Checkov_CKV2_GCP_36" + }, + { + "patternId": "Checkov_CKV2_GCP_35" + }, + { + "patternId": "Checkov_CKV_AZURE_144" + }, + { + "patternId": "Checkov_CKV_AZURE_142" + }, + { + "patternId": "Checkov_CKV2_GCP_3" + }, + { + "patternId": "Checkov_CKV_GCP_3" + } + ] + }, + { + "toolId": "PMD", + "patterns": [ + { + "patternId": "PMD_category_java_security_HardCodedCryptoKey" + }, + { + "patternId": "PMD_category_java_bestpractices_JUnitTestsShouldIncludeAssert" + }, + { + "patternId": "PMD_category_vm_errorprone_EmptyForeachStmt" + }, + { + "patternId": "PMD_category_apex_security_ApexBadCrypto" + }, + { + "patternId": "PMD_category_java_errorprone_EmptyFinalizer" + }, + { + "patternId": "PMD_category_java_design_AvoidThrowingRawExceptionTypes" + }, + { + "patternId": "PMD_category_java_errorprone_UselessOperationOnImmutable" + }, + { + "patternId": "PMD_category_plsql_bestpractices_TomKytesDespair" + }, + { + "patternId": "PMD_category_java_design_NPathComplexity" + }, + { + "patternId": "PMD_category_java_errorprone_MethodWithSameNameAsEnclosingClass" + }, + { + "patternId": "PMD_category_apex_design_ExcessiveParameterList" + }, + { + "patternId": "PMD_category_java_bestpractices_UnusedFormalParameter" + }, + { + "patternId": "PMD_category_apex_security_ApexXSSFromURLParam" + }, + { + "patternId": "PMD_category_java_errorprone_EqualsNull" + }, + { + "patternId": "PMD_category_apex_security_ApexSOQLInjection" + }, + { + "patternId": "PMD_category_apex_design_ExcessivePublicCount" + }, + { + "patternId": "PMD_category_java_errorprone_JumbledIncrementer" + }, + { + "patternId": "PMD_category_apex_security_ApexXSSFromEscapeFalse" + }, + { + "patternId": "PMD_category_java_errorprone_UnnecessaryBooleanAssertion" + }, + { + "patternId": "PMD_category_apex_security_ApexDangerousMethods" + }, + { + "patternId": "PMD_category_ecmascript_errorprone_InnaccurateNumericLiteral" + }, + { + "patternId": "PMD_category_java_errorprone_AvoidDecimalLiteralsInBigDecimalConstructor" + }, + { + "patternId": "PMD_category_java_errorprone_AvoidCallingFinalize" + }, + { + "patternId": "PMD_category_jsp_bestpractices_DontNestJsfInJstlIteration" + }, + { + "patternId": "PMD_category_java_errorprone_UnconditionalIfStatement" + }, + { + "patternId": "PMD_category_java_errorprone_DontUseFloatTypeForLoopIndices" + }, + { + "patternId": "PMD_category_java_errorprone_NonStaticInitializer" + }, + { + "patternId": "PMD_category_apex_security_ApexOpenRedirect" + }, + { + "patternId": "PMD_category_java_errorprone_JUnitSpelling" + }, + { + "patternId": "PMD_category_java_errorprone_AvoidInstanceofChecksInCatchClause" + }, + { + "patternId": "PMD_category_vm_errorprone_EmptyIfStmt" + }, + { + "patternId": "PMD_category_java_errorprone_JUnitStaticSuite" + }, + { + "patternId": "PMD_category_java_multithreading_AvoidThreadGroup" + }, + { + "patternId": "PMD_category_plsql_design_ExcessivePackageBodyLength" + }, + { + "patternId": "PMD_category_java_errorprone_AvoidBranchingStatementAsLastInLoop" + }, + { + "patternId": "PMD_category_java_errorprone_ReturnFromFinallyBlock" + }, + { + "patternId": "PMD_category_java_errorprone_AssignmentToNonFinalStatic" + }, + { + "patternId": "PMD_category_plsql_design_TooManyMethods", + "parameters": { + "maxmethods": "1" + } + }, + { + "patternId": "PMD_category_plsql_errorprone_TO_TIMESTAMPWithoutDateFormat" + }, + { + "patternId": "PMD_category_jsp_security_IframeMissingSrcAttribute" + }, + { + "patternId": "PMD_category_apex_design_AvoidDeeplyNestedIfStmts" + }, + { + "patternId": "PMD_category_java_errorprone_AvoidMultipleUnaryOperators" + }, + { + "patternId": "PMD_category_vm_design_AvoidDeeplyNestedIfStmts" + }, + { + "patternId": "PMD_category_apex_security_ApexSuggestUsingNamedCred" + }, + { + "patternId": "PMD_category_apex_security_ApexInsecureEndpoint" + }, + { + "patternId": "PMD_category_java_bestpractices_CheckResultSet" + }, + { + "patternId": "PMD_category_java_errorprone_UnnecessaryCaseChange" + }, + { + "patternId": "PMD_category_apex_security_ApexSharingViolations" + }, + { + "patternId": "PMD_category_vm_design_NoInlineJavaScript" + }, + { + "patternId": "PMD_category_java_design_AvoidThrowingNullPointerException" + }, + { + "patternId": "PMD_category_ecmascript_bestpractices_ConsistentReturn" + }, + { + "patternId": "PMD_category_jsp_errorprone_JspEncoding" + }, + { + "patternId": "PMD_category_plsql_design_ExcessivePackageSpecificationLength" + }, + { + "patternId": "PMD_category_pom_errorprone_InvalidDependencyTypes", + "parameters": { + "validTypes": "pom,jar,maven-plugin,ejb,war,ear,rar,par" + } + }, + { + "patternId": "PMD_category_ecmascript_errorprone_EqualComparison" + }, + { + "patternId": "PMD_category_java_performance_UseStringBufferLength" + }, + { + "patternId": "PMD_category_java_design_SingularField" + }, + { + "patternId": "PMD_category_java_bestpractices_AvoidReassigningParameters" + }, + { + "patternId": "PMD_category_java_errorprone_NonCaseLabelInSwitchStatement" + }, + { + "patternId": "PMD_category_xml_errorprone_MistypedCDATASection" + }, + { + "patternId": "PMD_category_java_bestpractices_UnusedPrivateField" + }, + { + "patternId": "PMD_category_jsp_bestpractices_NoHtmlComments" + }, + { + "patternId": "PMD_category_vf_security_VfUnescapeEl" + }, + { + "patternId": "PMD_category_java_errorprone_CheckSkipResult" + }, + { + "patternId": "PMD_category_jsp_design_NoLongScripts" + }, + { + "patternId": "PMD_category_jsp_security_NoUnsanitizedJSPExpression" + }, + { + "patternId": "PMD_category_java_performance_StringInstantiation" + }, + { + "patternId": "PMD_category_apex_security_ApexCRUDViolation" + }, + { + "patternId": "PMD_category_plsql_design_ExcessiveParameterList" + }, + { + "patternId": "PMD_category_java_multithreading_DontCallThreadRun" + }, + { + "patternId": "PMD_category_java_errorprone_MisplacedNullCheck" + }, + { + "patternId": "PMD_category_vf_security_VfCsrf" + }, + { + "patternId": "PMD_category_plsql_errorprone_TO_DATE_TO_CHAR" + }, + { + "patternId": "PMD_category_ecmascript_bestpractices_AvoidWithStatement" + }, + { + "patternId": "PMD_category_java_bestpractices_SwitchStmtsShouldHaveDefault" + }, + { + "patternId": "PMD_category_plsql_design_ExcessiveObjectLength" + }, + { + "patternId": "PMD_category_java_design_ExcessiveParameterList" + }, + { + "patternId": "PMD_category_java_errorprone_DoNotHardCodeSDCard" + }, + { + "patternId": "PMD_category_jsp_design_NoScriptlets" + }, + { + "patternId": "PMD_category_vm_design_ExcessiveTemplateLength", + "parameters": { + "minimum": "1000" + } + }, + { + "patternId": "PMD_category_java_errorprone_AvoidAccessibilityAlteration" + }, + { + "patternId": "PMD_category_java_errorprone_BrokenNullCheck" + }, + { + "patternId": "PMD_category_java_bestpractices_UnusedLocalVariable" + }, + { + "patternId": "PMD_category_plsql_design_ExcessiveMethodLength" + }, + { + "patternId": "PMD_category_xsl_performance_AvoidAxisNavigation", + "parameters": { + "checkSelfDescendantAbreviation": "false" + } + }, + { + "patternId": "PMD_category_java_errorprone_CompareObjectsWithEquals", + "parameters": { + "typesThatCompareByReference": "java.lang.Enum,java.lang.Class" + } + }, + { + "patternId": "PMD_category_java_errorprone_MissingStaticMethodInNonInstantiatableClass", + "parameters": { + "annotations": "org.springframework.beans.factory.annotation.Autowired,javax.inject.Inject" + } + }, + { + "patternId": "PMD_category_java_errorprone_UseEqualsToCompareStrings" + }, + { + "patternId": "PMD_category_pom_errorprone_ProjectVersionAsDependencyVersion" + }, + { + "patternId": "PMD_category_plsql_errorprone_TO_DATEWithoutDateFormat" + }, + { + "patternId": "PMD_category_plsql_design_ExcessiveTypeLength" + }, + { + "patternId": "PMD_category_java_performance_StringToString" + }, + { + "patternId": "PMD_category_apex_design_ExcessiveClassLength" + } + ] + }, + { + "toolId": "jackson", + "patterns": [ + { + "patternId": "jackson_duplicate-keys" + }, + { + "patternId": "jackson_parse-error" + } + ] + }, + { + "toolId": "markdownlint", + "patterns": [ + { + "patternId": "markdownlint_MD053", + "parameters": { + "ignored_definitions": "[\"//\"]" + } + }, + { + "patternId": "markdownlint_MD052", + "parameters": { + "ignored_labels": "[\"x\"]", + "shortcut_syntax": "false" + } + }, + { + "patternId": "markdownlint_MD051", + "parameters": { + "ignore_case": "false", + "ignored_pattern": "" + } + }, + { + "patternId": "markdownlint_MD024", + "parameters": { + "siblings_only": "false" + } + }, + { + "patternId": "markdownlint_MD011" + } + ] + }, + { + "toolId": "Bandit", + "patterns": [ + { + "patternId": "Bandit_B202" + }, + { + "patternId": "Bandit_B113" + }, + { + "patternId": "Bandit_B311" + }, + { + "patternId": "Bandit_B301" + }, + { + "patternId": "Bandit_B609" + }, + { + "patternId": "Bandit_B506" + }, + { + "patternId": "Bandit_B407" + }, + { + "patternId": "Bandit_B317" + }, + { + "patternId": "Bandit_B102" + }, + { + "patternId": "Bandit_B505" + }, + { + "patternId": "Bandit_B108" + }, + { + "patternId": "Bandit_B608" + }, + { + "patternId": "Bandit_B702" + }, + { + "patternId": "Bandit_B401" + }, + { + "patternId": "Bandit_B406" + }, + { + "patternId": "Bandit_B315" + }, + { + "patternId": "Bandit_B501" + }, + { + "patternId": "Bandit_B107" + }, + { + "patternId": "Bandit_B110" + }, + { + "patternId": "Bandit_B603" + }, + { + "patternId": "Bandit_B201" + }, + { + "patternId": "Bandit_B104" + }, + { + "patternId": "Bandit_B304" + }, + { + "patternId": "Bandit_B601" + }, + { + "patternId": "Bandit_B321" + }, + { + "patternId": "Bandit_B309" + }, + { + "patternId": "Bandit_B606" + }, + { + "patternId": "Bandit_B310" + }, + { + "patternId": "Bandit_B316" + }, + { + "patternId": "Bandit_B105" + }, + { + "patternId": "Bandit_B318" + }, + { + "patternId": "Bandit_B112" + }, + { + "patternId": "Bandit_B405" + }, + { + "patternId": "Bandit_B402" + }, + { + "patternId": "Bandit_B313" + }, + { + "patternId": "Bandit_B320" + }, + { + "patternId": "Bandit_B409" + }, + { + "patternId": "Bandit_B602" + }, + { + "patternId": "Bandit_B307" + }, + { + "patternId": "Bandit_B303" + }, + { + "patternId": "Bandit_B701" + }, + { + "patternId": "Bandit_B403" + }, + { + "patternId": "Bandit_B604" + }, + { + "patternId": "Bandit_B312" + }, + { + "patternId": "Bandit_B502" + }, + { + "patternId": "Bandit_B411" + }, + { + "patternId": "Bandit_B408" + }, + { + "patternId": "Bandit_B308" + }, + { + "patternId": "Bandit_B306" + }, + { + "patternId": "Bandit_B410" + }, + { + "patternId": "Bandit_B314" + }, + { + "patternId": "Bandit_B302" + }, + { + "patternId": "Bandit_B103" + }, + { + "patternId": "Bandit_B319" + }, + { + "patternId": "Bandit_B503" + }, + { + "patternId": "Bandit_B504" + }, + { + "patternId": "Bandit_B305" + }, + { + "patternId": "Bandit_B404" + } + ] + }, + { + "toolId": "Trivy", + "patterns": [ + { + "patternId": "Trivy_malicious_packages" + }, + { + "patternId": "Trivy_vulnerability_high" + }, + { + "patternId": "Trivy_vulnerability_critical" + }, + { + "patternId": "Trivy_vulnerability_minor" + }, + { + "patternId": "Trivy_vulnerability_medium" + }, + { + "patternId": "Trivy_secret" + } + ] + }, + { + "toolId": "shellcheck", + "patterns": [ + { + "patternId": "shellcheck_SC2156" + }, + { + "patternId": "shellcheck_SC2115" + }, + { + "patternId": "shellcheck_SC2035" + }, + { + "patternId": "shellcheck_SC2086" + }, + { + "patternId": "shellcheck_SC2025" + }, + { + "patternId": "shellcheck_SC2148" + }, + { + "patternId": "shellcheck_SC2029" + }, + { + "patternId": "shellcheck_SC2016" + }, + { + "patternId": "shellcheck_SC2001" + }, + { + "patternId": "shellcheck_SC2024" + }, + { + "patternId": "shellcheck_SC2028" + }, + { + "patternId": "shellcheck_SC2004" + }, + { + "patternId": "shellcheck_SC2002" + }, + { + "patternId": "shellcheck_SC2026" + }, + { + "patternId": "shellcheck_SC2033" + }, + { + "patternId": "shellcheck_SC2015" + }, + { + "patternId": "shellcheck_SC2034" + }, + { + "patternId": "shellcheck_SC2020" + }, + { + "patternId": "shellcheck_SC2027" + }, + { + "patternId": "shellcheck_SC2036" + }, + { + "patternId": "shellcheck_SC2003" + }, + { + "patternId": "shellcheck_SC2031" + }, + { + "patternId": "shellcheck_SC2022" + } + ] + }, + { + "toolId": "Agentlinter", + "patterns": [ + { + "patternId": "Agentlinter_token-budget_under-150-tokens" + }, + { + "patternId": "Agentlinter_token-budget_total-tokens" + }, + { + "patternId": "Agentlinter_token-budget_section-weight" + }, + { + "patternId": "Agentlinter_token-budget_compressible-padding" + }, + { + "patternId": "Agentlinter_structure_position-risk-warning" + }, + { + "patternId": "Agentlinter_structure_modular-files" + }, + { + "patternId": "Agentlinter_structure_has-main-file" + }, + { + "patternId": "Agentlinter_structure_dead-import" + }, + { + "patternId": "Agentlinter_structure_circular-import" + }, + { + "patternId": "Agentlinter_skill-safety_skill-name-match-dir" + }, + { + "patternId": "Agentlinter_skill-safety_sensitive-paths" + }, + { + "patternId": "Agentlinter_skill-safety_injection-vectors" + }, + { + "patternId": "Agentlinter_skill-safety_has-metadata" + }, + { + "patternId": "Agentlinter_skill-safety_excessive-permissions" + }, + { + "patternId": "Agentlinter_skill-safety_data-exfiltration" + }, + { + "patternId": "Agentlinter_skill-safety_dangerous-commands" + }, + { + "patternId": "Agentlinter_security_prompt-injection-vulnerability" + }, + { + "patternId": "Agentlinter_security_no-secrets" + }, + { + "patternId": "Agentlinter_security_no-pii-exposure" + }, + { + "patternId": "Agentlinter_security_no-injection-defense" + }, + { + "patternId": "Agentlinter_security_has-permission-boundaries" + }, + { + "patternId": "Agentlinter_security_has-injection-defense" + }, + { + "patternId": "Agentlinter_security_env-var-references" + }, + { + "patternId": "Agentlinter_security_api-key-exposure" + }, + { + "patternId": "Agentlinter_runtime_token-strength" + }, + { + "patternId": "Agentlinter_runtime_group-policy" + }, + { + "patternId": "Agentlinter_runtime_gateway-bind" + }, + { + "patternId": "Agentlinter_runtime_dm-policy" + }, + { + "patternId": "Agentlinter_runtime_config-secrets" + }, + { + "patternId": "Agentlinter_runtime_config-exists" + }, + { + "patternId": "Agentlinter_runtime_auth-mode" + }, + { + "patternId": "Agentlinter_remote-ready_model-settings-specified" + }, + { + "patternId": "Agentlinter_memory_no-mental-notes" + }, + { + "patternId": "Agentlinter_memory_has-state-tracking" + }, + { + "patternId": "Agentlinter_memory_has-memory-strategy" + }, + { + "patternId": "Agentlinter_memory_has-learning-loop" + }, + { + "patternId": "Agentlinter_memory_has-handoff-protocol" + }, + { + "patternId": "Agentlinter_memory_has-file-based-notes" + }, + { + "patternId": "Agentlinter_memory_has-context-window-awareness" + }, + { + "patternId": "Agentlinter_consistency_timezone-locale-drift" + }, + { + "patternId": "Agentlinter_consistency_stale-package-reference" + }, + { + "patternId": "Agentlinter_consistency_stale-date" + }, + { + "patternId": "Agentlinter_consistency_priority-conflict" + }, + { + "patternId": "Agentlinter_consistency_permission-conflict" + }, + { + "patternId": "Agentlinter_consistency_no-duplicate-instructions" + }, + { + "patternId": "Agentlinter_consistency_circular-dependency" + }, + { + "patternId": "Agentlinter_completeness_verification-criteria-required" + }, + { + "patternId": "Agentlinter_completeness_session-learning-hooks" + }, + { + "patternId": "Agentlinter_completeness_has-workflow" + }, + { + "patternId": "Agentlinter_completeness_has-priorities" + }, + { + "patternId": "Agentlinter_completeness_has-output-format" + }, + { + "patternId": "Agentlinter_completeness_has-error-handling" + }, + { + "patternId": "Agentlinter_completeness_has-boundaries" + }, + { + "patternId": "Agentlinter_completeness_freshness-file-paths" + }, + { + "patternId": "Agentlinter_claude-code_skills-vs-commands" + }, + { + "patternId": "Agentlinter_claude-code_relevance-trap" + }, + { + "patternId": "Agentlinter_claude-code_progressive-disclosure" + }, + { + "patternId": "Agentlinter_claude-code_instruction-count" + }, + { + "patternId": "Agentlinter_claude-code_hooks-structure" + }, + { + "patternId": "Agentlinter_claude-code_descriptive-ratio" + }, + { + "patternId": "Agentlinter_claude-code_agent-focus" + }, + { + "patternId": "Agentlinter_clarity_token-efficiency-score" + }, + { + "patternId": "Agentlinter_clarity_token-budget-range" + }, + { + "patternId": "Agentlinter_consistency_referenced-files-exist" + }, + { + "patternId": "Agentlinter_clarity_no-contradictions" + }, + { + "patternId": "Agentlinter_clarity_naked-conditional" + }, + { + "patternId": "Agentlinter_clarity_escape-hatch-missing" + }, + { + "patternId": "Agentlinter_clarity_english-config-files" + }, + { + "patternId": "Agentlinter_clarity_duplicate-content" + }, + { + "patternId": "Agentlinter_blueprint_coverage" + }, + { + "patternId": "Agentlinter_blueprint_constraints-defined" + } + ] + } + ], + "exclude": [ + "build/builder.ps1", + "build/builder.sh", + "build/installer/CODE_SIGNING.md", + "build/installer/configure-localdumps.ps1", + "build/installer/create-selfsigned-codesign-cert.ps1", + "build/installer/sign-authenticode.ps1", + "build/scripts/build.ps1", + "build/scripts/dev-helpers.ps1", + "build/scripts/install-local.ps1", + "build/scripts/linux/build-apt-repo.sh", + "build/scripts/linux/build-avalonia-packages.ps1", + "build/scripts/linux/build-avalonia-packages.sh", + "build/scripts/linux/build-linux-packages.ps1", + "build/scripts/linux/build-linux-packages.sh", + "build/scripts/linux/build-local-test.sh", + "build/scripts/linux/build-rust-packages.sh", + "build/scripts/linux/flatpak/com.gregframework.gregModmanager.yml", + "build/scripts/linux/flatpak/gregmodmanager-flatpak-launcher.sh", + "build/scripts/linux/gregmodmanager-cleanup.sh", + "build/scripts/linux/patch-steamworks-symbols.py", + "build/scripts/macos/run-remote-manual-test.sh", + "build/scripts/README.md", + "build/scripts/run.ps1", + "build/scripts/start.ps1" + ] +} diff --git a/.codacy/tmp/codacy-remote-results.json b/.codacy/tmp/codacy-remote-results.json new file mode 100644 index 0000000..1d42ab2 --- /dev/null +++ b/.codacy/tmp/codacy-remote-results.json @@ -0,0 +1,3933 @@ +{ + "metadata": { + "startedAt": "2026-10-28T07:05:57.928Z", + "completedAt": "2026-10-28T07:08:17.963Z", + "durationMs": 140035, + "repositoryRoot": "/mnt/win/Repositories/GameModding/DataCenter/GregDesktopApps/gregApp.Modmanager", + "executionMode": "auto-install", + "phaseTimings": { + "availabilityMs": 3259, + "fileDiscoveryMs": 97, + "fileRoutingMs": 16, + "toolExecutionMs": 132123, + "installMs": 4427, + "toolUpdateMs": 0 + } + }, + "capability": { + "ready": [ + { + "toolId": "Prospector", + "displayName": "Prospector", + "version": "1.19.1", + "installation": "codacy", + "runner": "local", + "filesRouted": 1, + "configSource": "codacy" + }, + { + "toolId": "PyLintPython3", + "displayName": "Pylint", + "version": "4.0.5", + "installation": "codacy", + "runner": "local", + "filesRouted": 1, + "configSource": "codacy" + }, + { + "toolId": "Semgrep", + "displayName": "Opengrep", + "version": "1.26.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 224, + "configSource": "codacy" + }, + { + "toolId": "Lizard", + "displayName": "Lizard", + "version": "1.23.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 186, + "configSource": "codacy" + }, + { + "toolId": "Hadolint", + "displayName": "Hadolint", + "version": "2.14.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 3, + "configSource": "codacy" + }, + { + "toolId": "Checkov", + "displayName": "Checkov", + "version": "3.3.8", + "installation": "codacy", + "runner": "local", + "filesRouted": 33, + "configSource": "codacy" + }, + { + "toolId": "jackson", + "displayName": "Jackson Linter", + "version": "1.0.0", + "installation": "bundled", + "runner": "local", + "filesRouted": 13, + "configSource": "codacy" + }, + { + "toolId": "markdownlint", + "displayName": "markdownlint", + "version": "0.41.1", + "installation": "bundled", + "runner": "local", + "filesRouted": 47, + "configSource": "codacy" + }, + { + "toolId": "Bandit", + "displayName": "Bandit", + "version": "1.9.4", + "installation": "codacy", + "runner": "local", + "filesRouted": 1, + "configSource": "codacy" + }, + { + "toolId": "Trivy", + "displayName": "Trivy", + "version": "0.72.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 344, + "configSource": "codacy" + }, + { + "toolId": "shellcheck", + "displayName": "ShellCheck", + "version": "0.11.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 3, + "configSource": "codacy" + }, + { + "toolId": "Agentlinter", + "displayName": "Agentlinter", + "version": "0.3.3", + "installation": "bundled", + "runner": "local", + "filesRouted": 4, + "configSource": "codacy" + }, + { + "toolId": "PMD", + "displayName": "PMD", + "version": "6.55.0", + "installation": "codacy", + "runner": "local", + "filesRouted": 1, + "configSource": "codacy" + } + ], + "unavailable": [ + { + "toolId": "psscriptanalyzer", + "displayName": "PSScriptAnalyzer", + "reason": "No local analyzer (configured on Codacy Cloud)", + "availableVia": "cloud" + }, + { + "toolId": "SonarCSharp", + "displayName": "SonarC#", + "reason": "No local analyzer (configured on Codacy Cloud)", + "availableVia": "cloud" + } + ], + "checkedAt": "2026-10-28T07:06:01.295Z" + }, + "issues": [ + { + "filePath": ".forgejo/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 111, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 118, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 132, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 141, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 203, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 212, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/linux-packages.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 59, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/linux-packages.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 68, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 35, + "column": 9, + "endLine": 42, + "endColumn": 2, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " ver='${{ github.event.inputs.version }}'", + " if [[ ! \"$ver\" =~ ^[0-9]+\\.[0-9]+\\.[0-9]+(-[a-zA-Z0-9.-]+)?$ ]]; then", + " echo \"Invalid version format: $ver. Expected: x.y.z or x.y.z-prerelease\"", + " exit 1", + " fi", + " echo \"Version format OK: $ver\"", + "" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".forgejo/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 45, + "column": 9, + "endLine": 68, + "endColumn": 2, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " ver='${{ github.event.inputs.version }}'", + " date=\"$(date +%F)\"", + " changelog='CHANGELOG.md'", + "", + " if ! grep -q '## \\[Unreleased\\]' \"$changelog\"; then", + " echo \"CHANGELOG.md does not contain an [Unreleased] section. Nothing to promote.\"", + " exit 1", + " fi", + "", + " new_unreleased=$(printf '## [Unreleased]\\n\\n### Added\\n\\n### Changed\\n\\n### Deprecated\\n\\n### Removed\\n\\n### Fixed\\n\\n### Security\\n\\n')", + " python3 - \"$changelog\" \"$ver\" \"$date\" \"$new_unreleased\" <<'EOF'", + " import sys", + " path, ver, date, new_unreleased = sys.argv[1:5]", + " with open(path, encoding='utf-8') as fh:", + " content = fh.read()", + " versioned = f'## [{ver}] - {date}'", + " content = content.replace('## [Unreleased]', versioned, 1)", + " content = content.replace(versioned + '\\n', versioned + '\\n\\n' + new_unreleased, 1)", + " with open(path, 'w', encoding='utf-8', newline='') as fh:", + " fh.write(content)", + " print(f'Promoted [Unreleased] to [{ver}] - {date}')", + " EOF", + "" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".forgejo/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 71, + "column": 9, + "endLine": 78, + "endColumn": 2, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " ver='${{ github.event.inputs.version }}'", + " printf '%s\\n' \"$ver\" > VERSION", + " csproj='src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj'", + " old=\"$(sed -n 's:.*\\([^<]*\\).*:\\1:p' \"$csproj\" | head -n 1)\"", + " sed -i \"s|[^<]*|${ver}|\" \"$csproj\"", + " echo \"Version: VERSION=$ver, .csproj: $old -> $ver\"", + "" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".forgejo/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 80, + "column": 9, + "endLine": 86, + "endColumn": 2, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " git config user.name \"actions[bot]\"", + " git config user.email \"actions[bot]@users.noreply.localhost\"", + " git add CHANGELOG.md VERSION src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj", + " git commit -m \"chore(release): promote changelog and bump version to ${{ github.event.inputs.version }}\"", + " git push origin main", + "" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".forgejo/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 89, + "column": 9, + "endLine": 92, + "endColumn": 35, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " ver='${{ github.event.inputs.version }}'", + " git tag \"v$ver\"", + " git push origin \"v$ver\"" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 34, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 45, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 54, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 63, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 70, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 88, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 95, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 134, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 135, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 148, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 155, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 168, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".forgejo/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 178, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 111, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 118, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 132, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 141, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 203, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/build-and-release.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 212, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/linux-packages.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 59, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/linux-packages.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 68, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 35, + "column": 9, + "endLine": 42, + "endColumn": 2, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " ver='${{ github.event.inputs.version }}'", + " if [[ ! \"$ver\" =~ ^[0-9]+\\.[0-9]+\\.[0-9]+(-[a-zA-Z0-9.-]+)?$ ]]; then", + " echo \"Invalid version format: $ver. Expected: x.y.z or x.y.z-prerelease\"", + " exit 1", + " fi", + " echo \"Version format OK: $ver\"", + "" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".gitea/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 45, + "column": 9, + "endLine": 68, + "endColumn": 2, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " ver='${{ github.event.inputs.version }}'", + " date=\"$(date +%F)\"", + " changelog='CHANGELOG.md'", + "", + " if ! grep -q '## \\[Unreleased\\]' \"$changelog\"; then", + " echo \"CHANGELOG.md does not contain an [Unreleased] section. Nothing to promote.\"", + " exit 1", + " fi", + "", + " new_unreleased=$(printf '## [Unreleased]\\n\\n### Added\\n\\n### Changed\\n\\n### Deprecated\\n\\n### Removed\\n\\n### Fixed\\n\\n### Security\\n\\n')", + " python3 - \"$changelog\" \"$ver\" \"$date\" \"$new_unreleased\" <<'EOF'", + " import sys", + " path, ver, date, new_unreleased = sys.argv[1:5]", + " with open(path, encoding='utf-8') as fh:", + " content = fh.read()", + " versioned = f'## [{ver}] - {date}'", + " content = content.replace('## [Unreleased]', versioned, 1)", + " content = content.replace(versioned + '\\n', versioned + '\\n\\n' + new_unreleased, 1)", + " with open(path, 'w', encoding='utf-8', newline='') as fh:", + " fh.write(content)", + " print(f'Promoted [Unreleased] to [{ver}] - {date}')", + " EOF", + "" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".gitea/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 71, + "column": 9, + "endLine": 78, + "endColumn": 2, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " ver='${{ github.event.inputs.version }}'", + " printf '%s\\n' \"$ver\" > VERSION", + " csproj='src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj'", + " old=\"$(sed -n 's:.*\\([^<]*\\).*:\\1:p' \"$csproj\" | head -n 1)\"", + " sed -i \"s|[^<]*|${ver}|\" \"$csproj\"", + " echo \"Version: VERSION=$ver, .csproj: $old -> $ver\"", + "" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".gitea/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 80, + "column": 9, + "endLine": 86, + "endColumn": 2, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " git config user.name \"actions[bot]\"", + " git config user.email \"actions[bot]@users.noreply.localhost\"", + " git add CHANGELOG.md VERSION src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj", + " git commit -m \"chore(release): promote changelog and bump version to ${{ github.event.inputs.version }}\"", + " git push origin main", + "" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".gitea/workflows/promote-changelog.yml", + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "toolId": "Semgrep", + "line": 89, + "column": 9, + "endLine": 92, + "endColumn": 35, + "message": "Using variable interpolation `${{...}}` with `github` context data in a `run:` step could allow an attacker to inject their own code into the runner.", + "lineContent": " run: |", + "multilineContent": [ + " run: |", + " ver='${{ github.event.inputs.version }}'", + " git tag \"v$ver\"", + " git push origin \"v$ver\"" + ], + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 34, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 45, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 54, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 63, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 70, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 88, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 95, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 134, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 135, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 148, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 155, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 168, + "column": 9, + "endColumn": 44, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: dtolnay/rust-toolchain@stable", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".gitea/workflows/rust.yml", + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "toolId": "Semgrep", + "line": 178, + "column": 9, + "endColumn": 37, + "message": "An action sourced from a third-party repository on GitHub is not pinned to a full length commit SHA. Pinning an action to a full length commit SHA is currently the only way to use an action as an immutable release.", + "lineContent": " - uses: Swatinem/rust-cache@v2", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 538, + "column": 13, + "endColumn": 51, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " System.Diagnostics.Process.Start(psi);", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 570, + "column": 17, + "endColumn": 31, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " FileName = exe,", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 574, + "column": 13, + "endColumn": 51, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " System.Diagnostics.Process.Start(psi);", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/ProtocolRegistryService.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 86, + "column": 13, + "endColumn": 47, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " Process.Start(psi)?.WaitForExit();", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/RalphSyncService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 21, + "column": 21, + "endColumn": 25, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\tFile.WriteAllText(path, JsonSerializer.Serialize(payload, AppJsonContext.Default.RalphTaskStatus));\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/ReproBundleService.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 177, + "column": 3, + "endColumn": 35, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": "\t\treturn Process.Start(startInfo);", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SafeProcess.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 143, + "column": 13, + "endColumn": 32, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " FileName = fileName,", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SafeProcess.cs", + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "toolId": "Semgrep", + "line": 152, + "column": 9, + "endColumn": 29, + "message": "OS command injection is a critical vulnerability that can lead to a full system compromise as it may allow an adversary to pass in arbitrary commands or arguments to be executed.", + "lineContent": " Process.Start(info);", + "category": "Security", + "severity": "Error" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 515, + "column": 52, + "endColumn": 62, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\tvar previewBytes = await File.ReadAllBytesAsync(absPreview, cancellationToken).ConfigureAwait(false);", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 517, + "column": 34, + "endColumn": 45, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\tawait File.WriteAllBytesAsync(tempPreview, previewBytes, cancellationToken).ConfigureAwait(false);", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 223, + "column": 32, + "endColumn": 36, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\tvar json = File.ReadAllText(path);\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 877, + "column": 37, + "endColumn": 41, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\t\ttry { bytes = File.ReadAllBytes(full); }\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 890, + "column": 34, + "endColumn": 41, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\t\t\t\t\tvar pb = File.ReadAllBytes(preview);\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "toolId": "Semgrep", + "line": 997, + "column": 21, + "endColumn": 25, + "message": "String argument projectRoot is used to read or write data from a file via Path.Combine without direct sanitization via Path.GetFileName.", + "lineContent": "\t\tFile.WriteAllText(path, JsonSerializer.Serialize(metadata, AppJsonContext.Default.WorkshopMetadata));\r", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 593, + "column": 5, + "endColumn": 25, + "message": "temp_dir should not be used for security operations.", + "lineContent": " std::env::temp_dir().join(\"gregmodmanager-protocol\")", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe", + "toolId": "Semgrep", + "line": 2816, + "column": 25, + "endColumn": 48, + "message": "current_exe should not be used for security operations.", + "lineContent": " let message = match std::env::current_exe() {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 2964, + "column": 15, + "endColumn": 35, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(\"gregmodmanager-thumbs\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/main.rs", + "patternId": "Semgrep_rust.lang.security.args.args", + "toolId": "Semgrep", + "line": 34, + "column": 24, + "endColumn": 40, + "message": "args should not be used for security operations.", + "lineContent": " for arg in std::env::args().skip(1) {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/main.rs", + "patternId": "Semgrep_rust.lang.security.args.args", + "toolId": "Semgrep", + "line": 48, + "column": 16, + "endColumn": 32, + "message": "args should not be used for security operations.", + "lineContent": " for arg in std::env::args().skip(1) {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-app/src/shots.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 449, + "column": 15, + "endColumn": 35, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let tmp = std::env::temp_dir().join(format!(\"greg-sync-test-{}\", std::process::id()));", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-cli/src/main.rs", + "patternId": "Semgrep_rust.lang.security.args.args", + "toolId": "Semgrep", + "line": 73, + "column": 20, + "endColumn": 36, + "message": "args should not be used for security operations.", + "lineContent": " let code = run(std::env::args().collect());", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-core/src/docs/project_docs.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 272, + "column": 13, + "endColumn": 33, + "message": "temp_dir should not be used for security operations.", + "lineContent": " std::env::temp_dir().join(format!(\"greg-docs-test-{nanos}-{}\", std::process::id()));", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 622, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 640, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/discovery.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 109, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let base = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/game.rs", + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe", + "toolId": "Semgrep", + "line": 224, + "column": 38, + "endColumn": 61, + "message": "current_exe should not be used for security operations.", + "lineContent": " if let Ok(exe_dir) = std::env::current_exe() {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/installers.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 300, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/installers.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 329, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/local_content.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 220, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let base = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/native_config.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 71, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/packs.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 129, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/sync.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 198, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let base = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-loader/src/templates.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 277, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-modstore/src/install.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 195, + "column": 24, + "endColumn": 44, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let artifact = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-modstore/src/install.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 442, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/instance.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 85, + "column": 5, + "endColumn": 25, + "message": "temp_dir should not be used for security operations.", + "lineContent": " std::env::temp_dir().join(format!(\"{app_name}.lock\"))", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/instance.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 166, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let path = std::env::temp_dir().join(\"gregtest-inst-missing-1.lock\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/paths.rs", + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe", + "toolId": "Semgrep", + "line": 15, + "column": 22, + "endColumn": 45, + "message": "current_exe should not be used for security operations.", + "lineContent": " if let Ok(exe) = std::env::current_exe() {", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/paths.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 29, + "column": 5, + "endColumn": 25, + "message": "temp_dir should not be used for security operations.", + "lineContent": " std::env::temp_dir().join(\"gregModmanager-logs\")", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/prefs.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 31, + "column": 32, + "endColumn": 52, + "message": "temp_dir should not be used for security operations.", + "lineContent": " .unwrap_or_else(|| std::env::temp_dir().join(\"gregmodmanager-preferences.json\"));", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-platform/src/workspace.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 360, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage", + "toolId": "Semgrep", + "line": 693, + "column": 28, + "endLine": 770, + "endColumn": 14, + "message": "Detected 'unsafe' usage, please audit for secure usage", + "lineContent": " let attached = unsafe {", + "multilineContent": [ + " let attached = unsafe {", + " let ugc = sys::SteamAPI_SteamUGC_v021();", + " if ugc.is_null() {", + " return Err(SteamError::Api(\"Steam UGC interface unavailable\".into()));", + " }", + " let handle = sys::SteamAPI_ISteamUGC_StartItemUpdate(ugc, self.app_id.0, file_id);", + " if handle == sys::k_UGCUpdateHandleInvalid {", + " return Err(SteamError::Api(\"Steam rejected the gallery update\".into()));", + " }", + " let mut attached = 0usize;", + " for file in &files {", + " let ok = sys::SteamAPI_ISteamUGC_AddItemPreviewFile(", + " ugc,", + " handle,", + " file.as_ptr(),", + " sys::EItemPreviewType::k_EItemPreviewType_Image,", + " );", + " if ok {", + " attached += 1;", + " } else {", + " log(\"Gallery attach rejected by Steam for one file.\");", + " }", + " }", + " if attached == 0 {", + " return Err(SteamError::Api(\"Steam attached no gallery files\".into()));", + " }", + " let note = CString::new(\"gallery\").expect(\"static cstring\");", + " let call = sys::SteamAPI_ISteamUGC_SubmitItemUpdate(ugc, handle, note.as_ptr());", + " if call == 0 {", + " return Err(SteamError::Api(\"gallery submit rejected\".into()));", + " }", + " let pipe = sys::SteamAPI_GetHSteamPipe();", + " let deadline = Instant::now() + Duration::from_secs(240);", + " loop {", + " if cancel.load(Ordering::Relaxed) {", + " return Err(SteamError::Cancelled);", + " }", + " self.client.run_callbacks();", + " let mut result: sys::SubmitItemUpdateResult_t = std::mem::zeroed();", + " let mut failed = false;", + " let ready = sys::SteamAPI_ManualDispatch_GetAPICallResult(", + " pipe,", + " call,", + " &mut result as *mut _ as *mut std::os::raw::c_void,", + " std::mem::size_of::() as std::os::raw::c_int,", + " sys::SubmitItemUpdateResult_t_k_iCallback as std::os::raw::c_int,", + " &mut failed,", + " );", + " if ready {", + " if failed {", + " return Err(SteamError::Api(", + " \"gallery submit failed (transport)\".into(),", + " ));", + " }", + " if result.m_eResult != sys::EResult::k_EResultOK {", + " return Err(SteamError::Api(format!(", + " \"gallery submit failed: {:?}\",", + " result.m_eResult", + " )));", + " }", + " // Packed FFI struct: unaligned read for the u64 field.", + " let returned_id =", + " std::ptr::addr_of!(result.m_nPublishedFileId).read_unaligned();", + " if returned_id != file_id {", + " return Err(SteamError::Api(format!(", + " \"gallery submit returned wrong item {returned_id}\"", + " )));", + " }", + " break attached;", + " }", + " if Instant::now() >= deadline {", + " return Err(SteamError::Timeout(", + " \"gallery submit produced no result\".into(),", + " ));", + " }", + " std::thread::sleep(Duration::from_millis(50));", + " }", + " };" + ], + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage", + "toolId": "Semgrep", + "line": 789, + "column": 13, + "endLine": 882, + "endColumn": 14, + "message": "Detected 'unsafe' usage, please audit for secure usage", + "lineContent": " unsafe {", + "multilineContent": [ + " unsafe {", + " let ugc = sys::SteamAPI_SteamUGC_v021();", + " if ugc.is_null() {", + " return Err(SteamError::Api(\"Steam UGC interface unavailable\".into()));", + " }", + " let mut id = file_id;", + " let handle =", + " sys::SteamAPI_ISteamUGC_CreateQueryUGCDetailsRequest(ugc, &mut id as *mut _, 1);", + " if handle == sys::k_UGCQueryHandleInvalid {", + " return Err(SteamError::Api(\"gallery query rejected\".into()));", + " }", + " let outcome: Result> = (|| {", + " if !sys::SteamAPI_ISteamUGC_SetReturnAdditionalPreviews(ugc, handle, true) {", + " return Err(SteamError::Api(\"gallery flag rejected\".into()));", + " }", + " let call = sys::SteamAPI_ISteamUGC_SendQueryUGCRequest(ugc, handle);", + " if call == 0 {", + " return Err(SteamError::Api(\"gallery query rejected\".into()));", + " }", + " let pipe = sys::SteamAPI_GetHSteamPipe();", + " let deadline = Instant::now() + Duration::from_secs(60);", + " loop {", + " if cancel.load(Ordering::Relaxed) {", + " return Err(SteamError::Cancelled);", + " }", + " self.client.run_callbacks();", + " let mut completed: sys::SteamUGCQueryCompleted_t = std::mem::zeroed();", + " let mut failed = false;", + " let ready = sys::SteamAPI_ManualDispatch_GetAPICallResult(", + " pipe,", + " call,", + " &mut completed as *mut _ as *mut std::os::raw::c_void,", + " std::mem::size_of::()", + " as std::os::raw::c_int,", + " sys::SteamUGCQueryCompleted_t_k_iCallback as std::os::raw::c_int,", + " &mut failed,", + " );", + " if ready {", + " if failed {", + " return Err(SteamError::Api(", + " \"gallery query failed (transport)\".into(),", + " ));", + " }", + " if completed.m_eResult != sys::EResult::k_EResultOK {", + " return Err(SteamError::Api(format!(", + " \"gallery query failed: {:?}\",", + " completed.m_eResult", + " )));", + " }", + " if completed.m_unNumResultsReturned < 1 {", + " return Err(SteamError::Api(format!(\"item {file_id} not found\")));", + " }", + " break;", + " }", + " if Instant::now() >= deadline {", + " return Err(SteamError::Timeout(", + " \"gallery query produced no result\".into(),", + " ));", + " }", + " std::thread::sleep(Duration::from_millis(50));", + " }", + " let count =", + " sys::SteamAPI_ISteamUGC_GetQueryUGCNumAdditionalPreviews(ugc, handle, 0);", + " let mut urls = Vec::new();", + " for index in 0..count {", + " let mut url_buf = [0 as c_char; 1024];", + " let mut name_buf = [0 as c_char; 256];", + " let mut preview_type = sys::EItemPreviewType::k_EItemPreviewType_Image;", + " let ok = sys::SteamAPI_ISteamUGC_GetQueryUGCAdditionalPreview(", + " ugc,", + " handle,", + " 0,", + " index,", + " url_buf.as_mut_ptr(),", + " url_buf.len() as u32,", + " name_buf.as_mut_ptr(),", + " name_buf.len() as u32,", + " &mut preview_type,", + " );", + " if !ok || preview_type != sys::EItemPreviewType::k_EItemPreviewType_Image {", + " continue;", + " }", + " let url = CStr::from_ptr(url_buf.as_ptr())", + " .to_string_lossy()", + " .into_owned();", + " if !url.trim().is_empty() {", + " urls.push(url);", + " }", + " }", + " Ok(urls)", + " })();", + " sys::SteamAPI_ISteamUGC_ReleaseQueryUGCRequest(ugc, handle);", + " outcome", + " }" + ], + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 683, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 835, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 864, + "column": 19, + "endColumn": 39, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let dir = std::env::temp_dir().join(\"greg-gallery-empty\");", + "category": "Security", + "severity": "High" + }, + { + "filePath": "xtask/src/main.rs", + "patternId": "Semgrep_rust.lang.security.args.args", + "toolId": "Semgrep", + "line": 117, + "column": 20, + "endColumn": 36, + "message": "args should not be used for security operations.", + "lineContent": " let mut args = std::env::args().skip(1);", + "category": "Security", + "severity": "High" + }, + { + "filePath": "xtask/src/main.rs", + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "toolId": "Semgrep", + "line": 408, + "column": 20, + "endColumn": 40, + "message": "temp_dir should not be used for security operations.", + "lineContent": " let base = std::env::temp_dir().join(format!(", + "category": "Security", + "severity": "High" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 66, + "column": 1, + "endLine": 149, + "message": "MainWindow::OnLoaded has a NLOC of 78 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Program.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 17, + "column": 1, + "endLine": 158, + "message": "Program::Main has a NLOC of 118 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Services/DialogService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 42, + "column": 1, + "endLine": 101, + "message": "DialogService::CreateDialogWindow has a NLOC of 56 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 108, + "column": 1, + "endLine": 168, + "message": "EditorPage::OnReloadFromSteam has a NLOC of 57 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 735, + "column": 1, + "endLine": 821, + "message": "EditorPage::OnAddScreenshot has a NLOC of 77 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 876, + "column": 1, + "endLine": 941, + "message": "EditorPage::OnPickPreview has a NLOC of 60 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 975, + "column": 1, + "endLine": 1038, + "message": "EditorPage::OnSaveAndUpload has a NLOC of 53 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1042, + "column": 1, + "endLine": 1109, + "message": "EditorPage::RunUploadFlowAsync has a NLOC of 61 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/AppSettings.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 115, + "column": 1, + "endLine": 176, + "message": "AppSettings::TryDetectGameRoot has a NLOC of 55 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/HeadlessRunner.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 16, + "column": 1, + "endLine": 94, + "message": "HeadlessRunner::TryHandle has a NLOC of 72 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/HeadlessRunner.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 202, + "column": 1, + "endLine": 278, + "message": "HeadlessRunner::RunPublishAsync has a NLOC of 62 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/KeepAChangelogParser.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 51, + "column": 1, + "endLine": 139, + "message": "ChangelogEntry::TryParseEntries has a NLOC of 75 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/MarkdownToSteamBbCode.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 38, + "column": 1, + "endLine": 318, + "message": "MarkdownToSteamBbCode::Convert has a NLOC of 228 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/MelonLoaderInstallerService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 53, + "column": 1, + "endLine": 112, + "message": "MelonLoaderInstallState::EnsureCurrentAsync has a NLOC of 56 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/ModStoreUpdateService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 49, + "column": 1, + "endLine": 113, + "message": "ModStoreUpdateService::InstallReleaseAsync has a NLOC of 60 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamBbCodePreview.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 36, + "column": 1, + "endLine": 219, + "message": "SteamBbCodePreview::ParseContent has a NLOC of 173 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamModfixInstallerService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 22, + "column": 1, + "endLine": 80, + "message": "SteamModfixInstallResult::EnsureCurrentAsync has a NLOC of 56 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 33, + "column": 1, + "endLine": 125, + "message": "SteamWorkshopService::EnsureInitialized has a NLOC of 79 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 381, + "column": 1, + "endLine": 830, + "message": "SteamWorkshopService::PublishAsync has a NLOC of 363 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1189, + "column": 1, + "endLine": 1310, + "message": "SteamWorkshopService::ImportPublishedToWorkspaceAsync has a NLOC of 101 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/UploadDependencyChecker.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 101, + "column": 1, + "endLine": 178, + "message": "UploadDependencyChecker::CheckMetadataFields has a NLOC of 76 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/UploadDependencyChecker.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 322, + "column": 1, + "endLine": 401, + "message": "UploadDependencyChecker::CheckProjectDocs has a NLOC of 76 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/UploadDependencyChecker.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 446, + "column": 1, + "endLine": 497, + "message": "UploadDependencyChecker::CheckGregFrameworkDependency has a NLOC of 51 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 387, + "column": 1, + "endLine": 506, + "message": "WorkspaceService::CreateSourceTemplates has a NLOC of 115 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 508, + "column": 1, + "endLine": 603, + "message": "WorkspaceService::BuildMetadataForTemplate has a NLOC of 94 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 605, + "column": 1, + "endLine": 669, + "message": "WorkspaceService::CreateVanillaObjectDecorationTemplate has a NLOC of 62 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 677, + "column": 1, + "endLine": 755, + "message": "WorkspaceService::CreateModdedGameMirrorLayout has a NLOC of 74 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1000, + "column": 1, + "endLine": 1075, + "message": "WorkspaceService::CreateUxmlTemplate has a NLOC of 69 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Steam/SteamApiNativeLoader.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 133, + "column": 1, + "endLine": 215, + "message": "SteamApiNativeLoader::EnumerateCandidatePaths has a NLOC of 76 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Steam/SteamApiNativeLoader.cs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 243, + "column": 1, + "endLine": 330, + "message": "SteamApiNativeLoader::EnumerateHeuristicGameRoots has a NLOC of 69 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 26, + "column": 1, + "endLine": 88, + "message": "tick has a NLOC of 57 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 149, + "column": 1, + "endLine": 206, + "message": "on_nav has a NLOC of 54 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 866, + "column": 1, + "endLine": 932, + "message": "push_editor has a NLOC of 67 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 974, + "column": 1, + "endLine": 1030, + "message": "update_doc_hints has a NLOC of 57 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1101, + "column": 1, + "endLine": 1177, + "message": "editor_publish has a NLOC of 74 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1306, + "column": 1, + "endLine": 1364, + "message": "browse_go has a NLOC of 58 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1463, + "column": 1, + "endLine": 1558, + "message": "drain_browse has a NLOC of 96 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1611, + "column": 1, + "endLine": 1662, + "message": "store_check_updates has a NLOC of 52 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 1747, + "column": 1, + "endLine": 1853, + "message": "drain_store has a NLOC of 105 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 2109, + "column": 1, + "endLine": 2254, + "message": "refresh_problems has a NLOC of 137 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 2316, + "column": 1, + "endLine": 2379, + "message": "packs_refresh has a NLOC of 63 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 3010, + "column": 1, + "endLine": 3067, + "message": "download_thumb has a NLOC of 58 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 2082, + "column": 1, + "endLine": 3068, + "message": "percent_encode_bug has a NLOC of 67 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 17, + "column": 1, + "endLine": 84, + "message": "main has a NLOC of 60 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 87, + "column": 1, + "endLine": 398, + "message": "wire has a NLOC of 300 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/shots.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 441, + "column": 1, + "endLine": 522, + "message": "project_sync_hashes_off_ui_thread has a NLOC of 76 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/state.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 136, + "column": 1, + "endLine": 279, + "message": "new has a NLOC of 133 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-cli/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 77, + "column": 1, + "endLine": 143, + "message": "run has a NLOC of 63 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-cli/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 275, + "column": 1, + "endLine": 346, + "message": "run_publish has a NLOC of 69 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/bbcode.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 10, + "column": 1, + "endLine": 243, + "message": "convert has a NLOC of 208 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/bbcode.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 289, + "column": 1, + "endLine": 656, + "message": "is_horizontal_rule has a NLOC of 368 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/changelog.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 30, + "column": 1, + "endLine": 199, + "message": "normalize_version has a NLOC of 170 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/project_docs.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 151, + "column": 1, + "endLine": 210, + "message": "resolve_steam_changelog has a NLOC of 60 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 96, + "column": 1, + "endLine": 151, + "message": "check_metadata_fields has a NLOC of 54 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 178, + "column": 1, + "endLine": 257, + "message": "check_project_docs has a NLOC of 79 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 368, + "column": 1, + "endLine": 494, + "message": "check_security_preflight has a NLOC of 121 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/discovery.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 46, + "column": 1, + "endLine": 101, + "message": "discover has a NLOC of 56 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/installers.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 101, + "column": 1, + "endLine": 243, + "message": "latest_github_asset has a NLOC of 143 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/packs.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 47, + "column": 1, + "endLine": 111, + "message": "apply_pack has a NLOC of 64 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-loader/src/templates.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 66, + "column": 1, + "endLine": 132, + "message": "metadata_for_template has a NLOC of 67 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-modstore/src/auth_client.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 100, + "column": 1, + "endLine": 157, + "message": "exchange_callback_code has a NLOC of 58 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-modstore/src/install.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 149, + "column": 1, + "endLine": 465, + "message": "install_release_inner has a NLOC of 292 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-modstore/src/intent.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 77, + "column": 1, + "endLine": 135, + "message": "validate has a NLOC of 54 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-platform/src/repro.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 13, + "column": 1, + "endLine": 77, + "message": "create_bundle has a NLOC of 58 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-platform/src/workspace.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 233, + "column": 1, + "endLine": 285, + "message": "compute_publish_hash has a NLOC of 53 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 433, + "column": 1, + "endLine": 497, + "message": "page has a NLOC of 65 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 560, + "column": 1, + "endLine": 656, + "message": "submit has a NLOC of 97 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 670, + "column": 1, + "endLine": 773, + "message": "upload_gallery has a NLOC of 102 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 780, + "column": 1, + "endLine": 883, + "message": "additional_preview_urls has a NLOC of 103 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 99, + "column": 1, + "endLine": 239, + "message": "publish_inner has a NLOC of 131 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 457, + "column": 1, + "endLine": 519, + "message": "import_to_workspace has a NLOC of 63 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "xtask/src/main.rs", + "patternId": "Lizard_nloc-medium", + "toolId": "Lizard", + "line": 218, + "column": 1, + "endLine": 293, + "message": "dist has a NLOC of 68 (threshold: 50)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml.cs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 525 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/EditorPage.axaml.cs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 945 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Avalonia/Views/ModManagerPage.axaml.cs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 532 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/SteamWorkshopService.cs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 1227 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 954 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-app/src/actions.rs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 2893 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/docs/bbcode.rs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 696 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/l10n_strings.rs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 725 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-core/src/upload.rs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 633 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/backend.rs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 818 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": "crates/greg-steam/src/service.rs", + "patternId": "Lizard_file-nloc-medium", + "toolId": "Lizard", + "line": 1, + "column": 1, + "message": "File has 774 lines of code (threshold: 500)", + "lineContent": "", + "category": "Complexity", + "severity": "Warning" + }, + { + "filePath": ".devcontainer/Dockerfile", + "patternId": "Hadolint_DL3008", + "toolId": "Hadolint", + "line": 9, + "column": 1, + "message": "Pin versions in apt get install. Instead of `apt-get install ` use `apt-get install =`", + "lineContent": "RUN groupadd --gid \"$USER_GID\" \"$USERNAME\" \\", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "docs/examples/manifests/07_steam_manifest.json", + "patternId": "jackson_parse-error", + "toolId": "jackson", + "line": 1, + "column": 1, + "message": "Unexpected end of JSON input", + "lineContent": "", + "category": "ErrorProne", + "severity": "Error" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 23, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 108, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 135, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 191, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Removed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 200, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 204, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 211, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Changed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 221, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 232, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 237, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Changed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 242, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 248, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 263, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Changed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 269, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 278, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 285, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Changed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 290, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 297, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Fixed", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 303, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "CHANGELOG.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 309, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "### Added", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 396, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Community", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 626, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Sammlungen", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 826, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Downloads", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 1687, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Sicherheit", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "ModStoreAndManager-Roadmap.md", + "patternId": "markdownlint_MD024", + "toolId": "markdownlint", + "line": 1894, + "column": 1, + "message": "Multiple headings with the same content", + "lineContent": "## Sammlungen", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Bandit_B404", + "toolId": "Bandit", + "line": 5, + "column": 1, + "endColumn": 18, + "message": "Consider possible security implications associated with the subprocess module. (CWE-78)", + "lineContent": "import subprocess", + "category": "Security", + "severity": "Info", + "confidence": 3 + }, + { + "filePath": ".github/scripts/malicious_scan.py", + "patternId": "Bandit_B603", + "toolId": "Bandit", + "line": 39, + "column": 14, + "endLine": 46, + "endColumn": 6, + "message": "subprocess call - check for execution of untrusted input. (CWE-78)", + "lineContent": " result = subprocess.run(", + "multilineContent": [ + " result = subprocess.run(", + " [\"git\", *args],", + " capture_output=True,", + " text=True,", + " encoding=\"utf-8\",", + " errors=\"replace\",", + " check=False,", + " )" + ], + "category": "Security", + "severity": "Warning", + "confidence": 3 + }, + { + "patternId": "Trivy_vulnerability_medium", + "message": "Insecure dependency cargo/rustls@0.23.45 (GHSA-c8m5-c952-6cm4: Rustls: Session Debug formatting exposes TLS master secrets and resumption PSKs) (update to 0.23.46)", + "category": "Security", + "severity": "Warning", + "sourceId": "GHSA-c8m5-c952-6cm4", + "filePath": "Cargo.lock", + "toolId": "Trivy", + "line": 5160, + "column": 1, + "lineContent": "[[package]]" + }, + { + "patternId": "Trivy_vulnerability_minor", + "message": "Insecure dependency cargo/rustls@0.23.45 (GHSA-h2v8-394m-p7vv: Rustls: Brotli certificate decompression can allocate an attacker-controlled amount of memory up to 1 GiB before authentication.) (update to 0.23.46)", + "category": "Security", + "severity": "Info", + "sourceId": "GHSA-h2v8-394m-p7vv", + "filePath": "Cargo.lock", + "toolId": "Trivy", + "line": 5160, + "column": 1, + "lineContent": "[[package]]" + }, + { + "patternId": "Trivy_vulnerability_minor", + "message": "Insecure dependency cargo/rustls@0.23.45 (GHSA-vp88-798v-h67f: rustls: ECH rejection can expose buffered application data to authenticated outer server before `ech_required` alert) (update to 0.23.46)", + "category": "Security", + "severity": "Info", + "sourceId": "GHSA-vp88-798v-h67f", + "filePath": "Cargo.lock", + "toolId": "Trivy", + "line": 5160, + "column": 1, + "lineContent": "[[package]]" + }, + { + "patternId": "Trivy_vulnerability_minor", + "message": "Insecure dependency cargo/rustls@0.23.45 (GHSA-w44r-93j7-qv28: rustls: An unauthenticated ServerHello poisons the per-name key-exchange record, so later ClientHellos carry only a classical X25519 share) (update to 0.23.46)", + "category": "Security", + "severity": "Info", + "sourceId": "GHSA-w44r-93j7-qv28", + "filePath": "Cargo.lock", + "toolId": "Trivy", + "line": 5160, + "column": 1, + "lineContent": "[[package]]" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_naked-conditional", + "toolId": "Agentlinter", + "line": 57, + "column": 1, + "message": "Vague conditional: \"- Preserve binary-size settings unless a measured, reviewed change requires othe\". Specify exact threshold or trigger.", + "lineContent": "- Preserve binary-size settings unless a measured, reviewed change requires otherwise.", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "toolId": "Agentlinter", + "line": 12, + "column": 1, + "message": "Absolute rule without escape hatch: \"- MelonLoader plugins (`SubDirectoryFixer`, `gregPlugin.ModmanagerComp\"", + "lineContent": "- MelonLoader plugins (`SubDirectoryFixer`, `gregPlugin.ModmanagerCompanion`) stay .NET 6 — they load inside MelonLoader and are never rewritten in Rust. Frozen sources: `./.reference/modmanager-old/src/GregModmanager.Melons/`. If the Rust app must build them, shell out to the `dotnet` CLI via `xtask`.", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "toolId": "Agentlinter", + "line": 14, + "column": 1, + "message": "Absolute rule without escape hatch: \"- Always use Orchestration of several Agents if possible to\"", + "lineContent": "- Always use Orchestration of several Agents if possible to", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "toolId": "Agentlinter", + "line": 42, + "column": 1, + "message": "Absolute rule without escape hatch: \"- `greg-core` must not depend on UI crates (`slint`). If a required fi\"", + "lineContent": "- `greg-core` must not depend on UI crates (`slint`). If a required fix appears to need that dependency, stop and ask for maintainer confirmation.", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_consistency_referenced-files-exist", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Referenced file \"RUST_GRAPH.md\" not found in workspace.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "ErrorProne", + "severity": "High" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_consistency_referenced-files-exist", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Referenced file \"EXTERNAL_DEPENDENCIES.md\" not found in workspace.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "ErrorProne", + "severity": "High" + }, + { + "filePath": "TOOLS.md", + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "toolId": "Agentlinter", + "line": 30, + "column": 1, + "message": "Absolute rule without escape hatch: \"- Telemetry must respect `AppSettings.TelemetryEnabled`.\"", + "lineContent": "- Telemetry must respect `AppSettings.TelemetryEnabled`.", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "TOOLS.md", + "patternId": "Agentlinter_consistency_referenced-files-exist", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Referenced file \"EXTERNAL_DEPENDENCIES.md\" not found in workspace.", + "lineContent": "# TOOLS.md — Build, CI, and Operations", + "category": "ErrorProne", + "severity": "High" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-memory-strategy", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No memory strategy defined. The agent will lose all context between sessions.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-file-based-notes", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No file-based memory system (daily notes, logs). Consider structured note-taking for long-term knowledge.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_no-mental-notes", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "Memory strategy exists but missing explicit 'write it down' principle. Mental notes don't survive restarts.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-context-window-awareness", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No context window awareness. The agent should know how to handle long conversations and context overflow.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-state-tracking", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No task/state tracking mechanism. The agent can't resume work from where it left off.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_memory_has-learning-loop", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No learning loop defined. The agent doesn't know how to improve over time from past interactions.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + }, + { + "filePath": "AGENTS.md", + "patternId": "Agentlinter_runtime_config-exists", + "toolId": "Agentlinter", + "line": 1, + "column": 1, + "message": "No runtime config (clawdbot.json / openclaw.json) found. Runtime checks skipped.", + "lineContent": "# AGENTS.md — gregModmanager (Rust restart)", + "category": "BestPractice", + "severity": "Warning" + } + ], + "errors": [ + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `$` was unexpected", + "level": "warning", + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/WorkspaceService.cs", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ secrets.WINDOWS_SIGN_PFX_B64` was unexpecte…", + "level": "warning", + "filePath": ".gitea/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ needs.version.outputs.version` was unexpect…", + "level": "warning", + "filePath": ".gitea/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `${{` was unexpected", + "level": "warning", + "filePath": ".gitea/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ github.server_url` was unexpected", + "level": "warning", + "filePath": ".gitea/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ github.server_url` was unexpected", + "level": "warning", + "filePath": ".gitea/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ secrets.WINDOWS_SIGN_PFX_B64` was unexpecte…", + "level": "warning", + "filePath": ".forgejo/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ needs.version.outputs.version` was unexpect…", + "level": "warning", + "filePath": ".forgejo/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `${{` was unexpected", + "level": "warning", + "filePath": ".forgejo/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ github.server_url` was unexpected", + "level": "warning", + "filePath": ".forgejo/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ github.server_url` was unexpected", + "level": "warning", + "filePath": ".forgejo/workflows/build-and-release.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `$` was unexpected", + "level": "warning", + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Services/HeadlessRunner.cs", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `] { handleObj, (uint)0, j, null, null, imagePreviewTypeValue…` was unexpected", + "level": "warning", + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Steam/SteamUgcPreviews.cs", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `${{` was unexpected", + "level": "warning", + "filePath": ".gitea/workflows/linux-packages.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ github.server_url` was unexpected", + "level": "warning", + "filePath": ".gitea/workflows/linux-packages.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `${{` was unexpected", + "level": "warning", + "filePath": ".forgejo/workflows/linux-packages.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ github.server_url` was unexpected", + "level": "warning", + "filePath": ".forgejo/workflows/linux-packages.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ github.event.inputs.version` was unexpected", + "level": "warning", + "filePath": ".forgejo/workflows/promote-changelog.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error When parsing a snippet as Bash for metavariable-pattern in rule 'codacy.generated.Semgrep.yaml.github-actions.security.curl-eval.curl-eval', `{ github.event.inputs.version` was unexpected", + "level": "warning", + "filePath": ".gitea/workflows/promote-changelog.yml", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `USER \"$USERNAME\" RUN dotnet --list-sdks` was unexpected", + "level": "warning", + "filePath": ".devcontainer/Dockerfile", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "PartialParsing", + "message": "Syntax error `namespace SubDirectoryFixer;` was unexpected", + "level": "warning", + "filePath": ".reference/modmanager-old/src/GregModmanager.Melons/SubDirectoryFixer/SubDirectoryFixerPlugin.cs", + "fileNotAnalyzed": true + }, + { + "toolId": "Semgrep", + "phase": "toolInvoke", + "kind": "Syntax error", + "message": "Syntax error missing element", + "level": "warning", + "filePath": "docs/examples/manifests/07_steam_manifest.json", + "fileNotAnalyzed": true + }, + { + "toolId": "Trivy", + "phase": "toolInvoke", + "kind": "NetworkError", + "message": "OSV.dev API call failed: OSV API returned HTTP 400: Bad Request. Malicious package detection skipped.", + "level": "warning" + } + ], + "toolResults": [ + { + "toolId": "Prospector", + "status": "success", + "issueCount": 0, + "errorCount": 0, + "durationMs": 481, + "filesAnalyzed": 1 + }, + { + "toolId": "PyLintPython3", + "status": "success", + "issueCount": 0, + "errorCount": 0, + "durationMs": 1468, + "filesAnalyzed": 1 + }, + { + "toolId": "Semgrep", + "status": "success", + "issueCount": 100, + "errorCount": 22, + "durationMs": 28756, + "filesAnalyzed": 224 + }, + { + "toolId": "Lizard", + "status": "success", + "issueCount": 83, + "errorCount": 0, + "durationMs": 729, + "filesAnalyzed": 186 + }, + { + "toolId": "Hadolint", + "status": "success", + "issueCount": 1, + "errorCount": 0, + "durationMs": 80, + "filesAnalyzed": 3 + }, + { + "toolId": "Checkov", + "status": "success", + "issueCount": 0, + "errorCount": 0, + "durationMs": 3146, + "filesAnalyzed": 33 + }, + { + "toolId": "PMD", + "status": "success", + "issueCount": 0, + "errorCount": 0, + "durationMs": 929, + "filesAnalyzed": 1 + }, + { + "toolId": "jackson", + "status": "success", + "issueCount": 1, + "errorCount": 0, + "durationMs": 32, + "filesAnalyzed": 13 + }, + { + "toolId": "markdownlint", + "status": "success", + "issueCount": 25, + "errorCount": 0, + "durationMs": 614, + "filesAnalyzed": 47 + }, + { + "toolId": "Bandit", + "status": "success", + "issueCount": 2, + "errorCount": 0, + "durationMs": 154, + "filesAnalyzed": 1 + }, + { + "toolId": "Trivy", + "status": "success", + "issueCount": 4, + "errorCount": 1, + "durationMs": 94071, + "filesAnalyzed": 344 + }, + { + "toolId": "shellcheck", + "status": "success", + "issueCount": 0, + "errorCount": 0, + "durationMs": 154, + "filesAnalyzed": 3 + }, + { + "toolId": "Agentlinter", + "status": "success", + "issueCount": 15, + "errorCount": 0, + "durationMs": 1498, + "filesAnalyzed": 4 + } + ], + "patternSummary": { + "groups": [ + { + "severity": "Error", + "severityLabel": "CRITICAL", + "category": "Security", + "categoryLabel": "Security", + "patterns": [ + { + "patternId": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "title": "Avoid Shell Injection in GitHub Actions run Steps", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "Error", + "issueCount": 10, + "fileCount": 2, + "noisy": false + }, + { + "patternId": "Semgrep_csharp_injection_rule-CommandInjection", + "title": "Avoid OS Command Injection", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "Error", + "issueCount": 7, + "fileCount": 4, + "noisy": false + } + ], + "totalIssues": 17, + "totalPatterns": 2 + }, + { + "severity": "Error", + "severityLabel": "CRITICAL", + "category": "ErrorProne", + "categoryLabel": "Error Prone", + "patterns": [ + { + "patternId": "jackson_parse-error", + "title": "Prohibit Invalid JSON Files", + "toolId": "jackson", + "toolDisplayName": "Jackson Linter", + "category": "ErrorProne", + "severity": "Error", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 1, + "totalPatterns": 1 + }, + { + "severity": "High", + "severityLabel": "HIGH", + "category": "Security", + "categoryLabel": "Security", + "patterns": [ + { + "patternId": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "title": "Enforce Pinning of Third-Party GitHub Actions to Full Commit SHA", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 42, + "fileCount": 6, + "noisy": false + }, + { + "patternId": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "title": "Avoid Using temp_dir for Security Operations", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 25, + "fileCount": 18, + "noisy": false + }, + { + "patternId": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "title": "Avoid Unsafe Path.Combine Usage Without Sanitization", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 7, + "fileCount": 3, + "noisy": false + }, + { + "patternId": "Semgrep_rust.lang.security.args.args", + "title": "Avoid Using args for Security Operations", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 4, + "fileCount": 3, + "noisy": false + }, + { + "patternId": "Semgrep_rust.lang.security.current-exe.current-exe", + "title": "Avoid Using current_exe for Security Operations", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 3, + "fileCount": 3, + "noisy": false + }, + { + "patternId": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage", + "title": "Avoid Unsafe Usage", + "toolId": "Semgrep", + "toolDisplayName": "Opengrep", + "category": "Security", + "severity": "High", + "issueCount": 2, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 83, + "totalPatterns": 6 + }, + { + "severity": "High", + "severityLabel": "HIGH", + "category": "ErrorProne", + "categoryLabel": "Error Prone", + "patterns": [ + { + "patternId": "Agentlinter_consistency_referenced-files-exist", + "title": "Ensure referenced files exist", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "ErrorProne", + "severity": "High", + "issueCount": 3, + "fileCount": 2, + "noisy": false + } + ], + "totalIssues": 3, + "totalPatterns": 1 + }, + { + "severity": "Warning", + "severityLabel": "WARNING", + "category": "Security", + "categoryLabel": "Security", + "patterns": [ + { + "patternId": "Bandit_B603", + "title": "Check subprocess usage without shell=True", + "toolId": "Bandit", + "toolDisplayName": "Bandit", + "category": "Security", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Trivy_vulnerability_medium", + "title": "Detect Insecure Dependencies (Medium Severity)", + "toolId": "Trivy", + "toolDisplayName": "Trivy", + "category": "Security", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 2, + "totalPatterns": 2 + }, + { + "severity": "Warning", + "severityLabel": "WARNING", + "category": "BestPractice", + "categoryLabel": "Best Practice", + "patterns": [ + { + "patternId": "markdownlint_MD024", + "title": "Avoid Multiple Headings with the Same Content", + "toolId": "markdownlint", + "toolDisplayName": "markdownlint", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 25, + "fileCount": 2, + "noisy": false + }, + { + "patternId": "Agentlinter_clarity_escape-hatch-missing", + "title": "Require escape hatch for absolute rules", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 4, + "fileCount": 2, + "noisy": false + }, + { + "patternId": "Hadolint_DL3008", + "title": "Enforce Pinning Versions in apt-get install", + "toolId": "Hadolint", + "toolDisplayName": "Hadolint", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_clarity_naked-conditional", + "title": "Avoid naked conditionals — require specific, measurable triggers", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-memory-strategy", + "title": "Require explicit memory/continuity strategy", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-file-based-notes", + "title": "Require file-based notes for persistent memory", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_no-mental-notes", + "title": "Avoid relying on mental notes; write things down", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-context-window-awareness", + "title": "Ensure agent is aware of context window limitations", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-state-tracking", + "title": "Ensure agent tracks current task state", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_memory_has-learning-loop", + "title": "Ensure agent learns from past interactions", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Agentlinter_runtime_config-exists", + "title": "Require agent runtime config file", + "toolId": "Agentlinter", + "toolDisplayName": "Agentlinter", + "category": "BestPractice", + "severity": "Warning", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 38, + "totalPatterns": 11 + }, + { + "severity": "Warning", + "severityLabel": "WARNING", + "category": "Complexity", + "categoryLabel": "Complexity", + "patterns": [ + { + "patternId": "Lizard_nloc-medium", + "title": "Limit Function Length (Medium)", + "toolId": "Lizard", + "toolDisplayName": "Lizard", + "category": "Complexity", + "severity": "Warning", + "issueCount": 72, + "fileCount": 37, + "noisy": false + }, + { + "patternId": "Lizard_file-nloc-medium", + "title": "Limit File Length (Medium)", + "toolId": "Lizard", + "toolDisplayName": "Lizard", + "category": "Complexity", + "severity": "Warning", + "issueCount": 11, + "fileCount": 11, + "noisy": false + } + ], + "totalIssues": 83, + "totalPatterns": 2 + }, + { + "severity": "Info", + "severityLabel": "MINOR", + "category": "Security", + "categoryLabel": "Security", + "patterns": [ + { + "patternId": "Trivy_vulnerability_minor", + "title": "Detect Insecure Dependencies (Minor Severity)", + "toolId": "Trivy", + "toolDisplayName": "Trivy", + "category": "Security", + "severity": "Info", + "issueCount": 3, + "fileCount": 1, + "noisy": false + }, + { + "patternId": "Bandit_B404", + "title": "Consider security implications of importing subprocess module", + "toolId": "Bandit", + "toolDisplayName": "Bandit", + "category": "Security", + "severity": "Info", + "issueCount": 1, + "fileCount": 1, + "noisy": false + } + ], + "totalIssues": 4, + "totalPatterns": 2 + } + ], + "totalIssues": 231, + "totalPatterns": 27, + "noisyPatternCount": 0, + "noisyThreshold": 500 + }, + "skippedFiles": [ + { + "filePath": ".codacy/codacy.config.baseline.json", + "sizeBytes": 220518 + }, + { + "filePath": ".codacy/codacy.config.json", + "sizeBytes": 220518 + }, + { + "filePath": ".codacy/tmp/codacy-remote-config.json", + "sizeBytes": 220518 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Resources/Fonts/Vendored/JetBrainsMono/JetBrainsMono-Bold.ttf", + "sizeBytes": 274098 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Resources/Fonts/Vendored/JetBrainsMono/JetBrainsMono-Medium.ttf", + "sizeBytes": 270318 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/Resources/Fonts/Vendored/JetBrainsMono/JetBrainsMono-Regular.ttf", + "sizeBytes": 270226 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/libsteam_api.so", + "sizeBytes": 386864 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/libsteam_api64.so", + "sizeBytes": 386864 + }, + { + "filePath": ".reference/modmanager-old/src/GregModmanager.Core/steam_api64.dll", + "sizeBytes": 262946 + } + ] +} \ No newline at end of file diff --git a/.codacy/tmp/codacy-repo-before.json b/.codacy/tmp/codacy-repo-before.json new file mode 100644 index 0000000..6cf0fcb --- /dev/null +++ b/.codacy/tmp/codacy-repo-before.json @@ -0,0 +1,300 @@ +{ + "repository": { + "repository": { + "provider": "gh", + "owner": "mleem97", + "name": "gregModmanager", + "visibility": "Public", + "defaultBranch": { + "name": "main" + }, + "lastUpdated": "2026-10-27T02:29:40.149Z", + "languages": [ + "CSharp", + "Dockerfile", + "JSON", + "Markdown", + "Powershell", + "Python", + "Rust", + "Shell", + "XML", + "YAML" + ], + "standards": [ + { + "id": 160487, + "name": "AI Policy" + }, + { + "id": 160947, + "name": "Default coding standard" + } + ], + "gatePolicyName": "Codacy Gate Policy", + "problems": [] + }, + "lastAnalysedCommit": { + "sha": "c11e0cf488b4806ece73e1d7111c73744a738a72", + "startedAnalysis": "2026-10-27T02:29:49.252Z", + "endedAnalysis": "2026-10-27T02:30:10.705Z" + }, + "issuesCount": 226, + "loc": 39041, + "coverage": { + "status": "None" + }, + "complexFilesPercentage": 27, + "duplicationPercentage": 10, + "goals": { + "maxIssuePercentage": 20, + "maxDuplicatedFilesPercentage": 10, + "minCoveragePercentage": 60, + "maxComplexFilesPercentage": 10, + "fileDuplicationBlockThreshold": 1, + "fileComplexityValueThreshold": 20 + } + }, + "pullRequests": [], + "issuesOverview": { + "categories": [ + { + "name": "BestPractice", + "total": 48 + }, + { + "name": "Performance", + "total": 1 + }, + { + "name": "Security", + "total": 73 + }, + { + "name": "ErrorProne", + "total": 14 + }, + { + "name": "Complexity", + "total": 90 + } + ], + "languages": [ + { + "name": "CSharp", + "total": 91 + }, + { + "name": "Dockerfile", + "total": 1 + }, + { + "name": "Shell", + "total": 12 + }, + { + "name": "Rust", + "total": 85 + }, + { + "name": "Markdown", + "total": 20 + }, + { + "name": "YAML", + "total": 17 + } + ], + "levels": [ + { + "name": "High", + "total": 73 + }, + { + "name": "Warning", + "total": 141 + }, + { + "name": "Error", + "total": 12 + } + ], + "tags": [ + { + "name": "readability", + "total": 1 + }, + { + "name": "security", + "total": 24 + }, + { + "name": "clarity", + "total": 1 + }, + { + "name": "documentation", + "total": 1 + }, + { + "name": "headings", + "total": 8 + }, + { + "name": "fwk:github-actions", + "total": 17 + }, + { + "name": "filesystem", + "total": 7 + } + ], + "patterns": [ + { + "id": "Semgrep_yaml.github-actions.security.run-shell-injection.run-shell-injection", + "title": "Avoid Shell Injection in GitHub Actions run Steps", + "total": 2 + }, + { + "id": "shellcheck_SC2034", + "title": "Avoid Unused Variables", + "total": 1 + }, + { + "id": "SonarCSharp_S2760", + "title": "Avoid Sequential Tests Checking the Same Condition", + "total": 1 + }, + { + "id": "Semgrep_rust.lang.security.args.args", + "title": "Avoid Using args for Security Operations", + "total": 3 + }, + { + "id": "shellcheck_SC2086", + "title": "Enforce Double Quoting to Prevent Globbing and Word Splitting", + "total": 2 + }, + { + "id": "Semgrep_rust.lang.security.unsafe-usage.unsafe-usage", + "title": "Avoid Unsafe Usage", + "total": 2 + }, + { + "id": "Agentlinter_clarity_naked-conditional", + "title": "Avoid naked conditionals — require specific, measurable triggers", + "total": 1 + }, + { + "id": "Semgrep_csharp.lang.security.filesystem.unsafe-path-combine.unsafe-path-combine", + "title": "Avoid Unsafe Path.Combine Usage Without Sanitization", + "total": 7 + }, + { + "id": "Semgrep_rust.lang.security.current-exe.current-exe", + "title": "Avoid Using current_exe for Security Operations", + "total": 3 + }, + { + "id": "Lizard_nloc-medium", + "title": "Limit Function Length (Medium)", + "total": 79 + }, + { + "id": "Agentlinter_consistency_referenced-files-exist", + "title": "Ensure referenced files exist", + "total": 3 + }, + { + "id": "SonarCSharp_S3898", + "title": "Implement IEquatable on Value Types", + "total": 1 + }, + { + "id": "SonarCSharp_S2339", + "title": "Avoid Using Public Constant Members", + "total": 6 + }, + { + "id": "Hadolint_DL3008", + "title": "Enforce Pinning Versions in apt-get install", + "total": 1 + }, + { + "id": "shellcheck_SC2015", + "title": "Avoid Using `A && B || C` as if-Then-Else", + "total": 9 + }, + { + "id": "SonarCSharp_S2486", + "title": "Avoid Ignoring Generic Exceptions", + "total": 9 + }, + { + "id": "SonarCSharp_S6444", + "title": "Specify a timeout for regular expressions", + "total": 4 + }, + { + "id": "Semgrep_yaml.github-actions.security.third-party-action-not-pinned-to-commit-sha.third-party-action-not-pinned-to-commit-sha", + "title": "Enforce Pinning of Third-Party GitHub Actions to Full Commit SHA", + "total": 15 + }, + { + "id": "markdownlint_MD024", + "title": "Avoid Multiple Headings with the Same Content", + "total": 8 + }, + { + "id": "SonarCSharp_S2360", + "title": "Avoid Using Optional Parameters", + "total": 20 + }, + { + "id": "Semgrep_rust.lang.security.temp-dir.temp-dir", + "title": "Avoid Using temp_dir for Security Operations", + "total": 22 + }, + { + "id": "SonarCSharp_S1172", + "title": "Remove Unused Method Parameters", + "total": 2 + }, + { + "id": "Lizard_file-nloc-medium", + "title": "Limit File Length (Medium)", + "total": 11 + }, + { + "id": "Semgrep_csharp_injection_rule-CommandInjection", + "title": "Avoid OS Command Injection", + "total": 6 + }, + { + "id": "Agentlinter_clarity_escape-hatch-missing", + "title": "Require escape hatch for absolute rules", + "total": 8 + } + ], + "authors": [ + { + "name": "marvinleede@gmail.com", + "total": 181 + }, + { + "name": "52848568+mleem97@users.noreply.github.com", + "total": 14 + } + ], + "potentialFalsePositives": [ + { + "name": "equalOrAboveThreshold", + "total": 0 + }, + { + "name": "belowThreshold", + "total": 226 + } + ] + } +} diff --git a/.codacy/tmp/codacy-tools-before.json b/.codacy/tmp/codacy-tools-before.json new file mode 100644 index 0000000..42eb9e6 --- /dev/null +++ b/.codacy/tmp/codacy-tools-before.json @@ -0,0 +1,316 @@ +[ + { + "name": "Prospector", + "uuid": "25673894-eac1-4941-87a6-81f1abd5c321", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "Pylint", + "uuid": "31677b6d-4ae0-4f56-8041-606a8d7a8e61", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "PMD7", + "uuid": "ed7e8287-707d-485a-a0cb-e211004432c2", + "isClientSide": false, + "settings": { + "isEnabled": false, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [] + } + }, + { + "name": "Spectral", + "uuid": "fb60ff64-3d91-11ec-9bbc-0242ac130002", + "isClientSide": false, + "settings": { + "isEnabled": false, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [] + } + }, + { + "name": "PSScriptAnalyzer", + "uuid": "8fb0fb29-fa6e-43f2-9a73-9cd3873b4d8a", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "remark-lint", + "uuid": "f1eec388-0526-4c6c-954e-9b20b51bd9e7", + "isClientSide": false, + "settings": { + "isEnabled": false, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [] + } + }, + { + "name": "Ruff", + "uuid": "aac6ad5e-093d-47c4-97ff-87f91d6128a2", + "isClientSide": false, + "settings": { + "isEnabled": false, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [] + } + }, + { + "name": "Opengrep", + "uuid": "6792c561-236d-41b7-ba5e-9d6bee0d548b", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160487, + "name": "AI Policy" + }, + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "Lizard", + "uuid": "76348462-84b3-409a-90d3-955e90abfb87", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "Hadolint", + "uuid": "d3ec07a8-71b3-4b89-a25e-9c32ef827668", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "SonarC#", + "uuid": "8954dff3-f19c-429c-ac76-c45fa5e73b62", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "Pylint (deprecated)", + "uuid": "34225275-f79e-4b85-8126-c7512c987c0d", + "isClientSide": false, + "settings": { + "isEnabled": false, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [] + } + }, + { + "name": "Checkov", + "uuid": "13af9d89-1ce5-4fec-a168-765c3e7b26b3", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160487, + "name": "AI Policy" + } + ] + } + }, + { + "name": "PMD", + "uuid": "9ed24812-b6ee-4a58-9004-0ed183c45b8f", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "Unity Roslyn Analyzers", + "uuid": "aaf8a1d9-793a-450d-997b-db628a8084fd", + "isClientSide": true, + "settings": { + "isEnabled": false, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [] + } + }, + { + "name": "Jackson Linter", + "uuid": "4f94ee55-6b76-4765-8f38-9ebb3920762b", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "markdownlint", + "uuid": "547ff16b-d57c-4d75-8067-5ccf3ea88a00", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "Bandit", + "uuid": "89b6fc6a-9137-4cf3-8b9f-dcc3bedfa738", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "Trivy", + "uuid": "2fd7fbe0-33f9-4ab3-ab73-e9b62404e2cb", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160487, + "name": "AI Policy" + }, + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "ShellCheck", + "uuid": "233f8aac-4fb6-4193-8a17-e64515bea152", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + }, + { + "name": "Agentlinter", + "uuid": "498c9a6e-5ff8-45de-9bd3-0fef69370617", + "isClientSide": false, + "settings": { + "isEnabled": true, + "hasConfigurationFile": false, + "usesConfigurationFile": false, + "enabledBy": [ + { + "id": 160947, + "name": "Default coding standard" + } + ] + } + } +] diff --git a/.devcontainer/Dockerfile b/.devcontainer/Dockerfile index 4e3d8ef..daac13a 100644 --- a/.devcontainer/Dockerfile +++ b/.devcontainer/Dockerfile @@ -1,21 +1,24 @@ -# Avalonia desktop (net10 LTS): SDK 10 plus native X11/font/GL deps so the -# Modmanager builds and can at least smoke-run headless via xvfb. -FROM mcr.microsoft.com/dotnet/sdk:10.0-bookworm-slim +# Rust (rust + Slint) desktop dev container: rustup toolchain plus the native +# X11/font/GL deps so the Slint UI builds and can at least smoke-run headless +# via xvfb. Release builds cross-compile through the same toolchain. +FROM rust:1-bookworm ARG USERNAME=vscode ARG USER_UID=1000 ARG USER_GID=1000 -RUN groupadd --gid "$USER_GID" "$USERNAME" \ - && useradd --uid "$USER_UID" --gid "$USER_GID" -m -s /bin/bash "$USERNAME" \ - && apt-get update \ - && apt-get install -y --no-install-recommends \ - git sudo xvfb \ - libice6 libsm6 libx11-6 libxkbcommon0 libfontconfig1 libfreetype6 \ - libgl1 libegl1 zlib1g dbus-x11 \ - && echo "$USERNAME ALL=(root) NOPASSWD:ALL" > "/etc/sudoers.d/$USERNAME" \ - && chmod 0440 "/etc/sudoers.d/$USERNAME" \ - && rm -rf /var/lib/apt/lists/* +RUN apt-get update \ + && apt-get install -y --no-install-recommends \ + git sudo xvfb \ + libice6 libsm6 libx11-6 libxkbcommon0 libfontconfig1 libfreetype6 \ + libgl1 libegl1 zlib1g dbus-x11 \ + && echo "$USERNAME ALL=(root) NOPASSWD:ALL" > "/etc/sudoers.d/$USERNAME" \ + && chmod 0440 "/etc/sudoers.d/$USERNAME" \ + && rm -rf /var/lib/apt/lists/* USER "$USERNAME" -RUN dotnet --list-sdks +WORKDIR /src +COPY . . +RUN rustup component add clippy rustfmt && cargo fetch + +RUN rustc --version && cargo --version diff --git a/.devcontainer/devcontainer.json b/.devcontainer/devcontainer.json index 2260935..0d0bda4 100644 --- a/.devcontainer/devcontainer.json +++ b/.devcontainer/devcontainer.json @@ -1,20 +1,17 @@ { - "name": "greg modmanager (avalonia, net10)", + "name": "greg modmanager (rust, slint)", "build": { "dockerfile": "Dockerfile" }, "remoteUser": "vscode", "containerEnv": { - "DOTNET_CLI_TELEMETRY_OPTOUT": "1", - "DOTNET_NOLOGO": "1" + "CARGO_TERM_COLOR": "always", + "RUSTUP_TOOLCHAIN": "stable" }, - "mounts": [ - "source=greg-modmanager-nuget,target=/home/vscode/.nuget/packages,type=volume" - ], "customizations": { "vscode": { - "extensions": ["ms-dotnettools.csharp"] + "extensions": ["rust-lang.rust-analyzer"] } }, - "postCreateCommand": "dotnet restore GregModmanager.sln" + "postCreateCommand": "rustup component add rust-analyzer && cargo fetch" } diff --git a/.env.example b/.env.example new file mode 100644 index 0000000..14eb409 --- /dev/null +++ b/.env.example @@ -0,0 +1,169 @@ +# gregModmanager environment inventory — placeholders only, never real secrets. +# The Rust binaries do NOT load .env automatically. Export selected variables +# in the launching process; inject CI secrets explicitly into the relevant job. +# Blank optional overrides should normally remain UNSET: some readers treat an +# empty string as a configured value. Do not blindly export this entire file. +# Status: ACTIVE = read today; RESERVED = proposed integration contract only. +# See docs/ENVIRONMENT.md for deployment ownership and synchronization gaps. + +# ACTIVE — desktop / CLI +GREG_LOCAL_BUILD=0 +GREG_LOCAL_TEST_BUILD=0 +RUST_LOG=info +# Optional paths; uncomment and set only when overriding discovery. +# GREG_WORKSPACE=/path/to/workspace +# GREG_GAME_ROOT=/path/to/game +GREG_MODSTORE_DISABLED=1 +GREG_MODSTORE_WEB_URL=https://datacentermods.com +GREG_MODSTORE_API_URL=https://datacentermods.com +GREG_AUTH_URL=https://datacentermods.com/auth +GREG_MODSTORE_TOKEN= +GREG_MELONLOADER_FEED_URL=https://github.com/LavaGang/MelonLoader/releases +# Optional Steam Web API fallback for Workshop metadata / previews. +STEAM_WEB_API_KEY= +# Optional locale overrides (normally inherited from the OS). +# LC_ALL=de_DE.UTF-8 +# LANG=de_DE.UTF-8 + +# ACTIVE — opt-in Loki sender. URL must include /loki/api/v1/push. +# GREG_LOCAL_BUILD=1 forces http://localhost:3100/loki/api/v1/push. +GREG_TELEMETRY_ENABLED=0 +GREG_LOKI_URL= +GREG_LOKI_USER= +GREG_LOKI_PASS= +GREG_LOKI_TENANT= + +# RESERVED — canonical Grafana / Loki deployment credentials. +# Mentioned by the former CI workflow; not read by the Rust sender. +# Until wired: map ENDPOINT -> GREG_LOKI_URL, USER -> GREG_LOKI_USER, +# API_KEY -> GREG_LOKI_PASS, TENANT -> GREG_LOKI_TENANT in the launcher. +# ENDPOINT is the complete Loki push URL, not the Grafana dashboard URL. +TELEMETRY_ENDPOINT= +TELEMETRY_USER= +TELEMETRY_API_KEY= +TELEMETRY_TENANT= + +# ACTIVE — Report Assistant GitHub Issues channel (runtime credentials). +# API URL has a default; token + owner/repository enable direct submission. +GREG_GITHUB_API_URL=https://api.github.com +GREG_GITHUB_ISSUE_TARGET_REPO= +GREG_GITHUB_TOKEN= + +# LEGACY — former Actions workflow notification. The current Jenkinsfile +# has no notification dispatcher; retain this name for migration compatibility. +DISCORD_WEBHOOK_URL= +# RESERVED — separate Discord embed destinations; no routing implemented yet. +# Public stable/full releases only; exclude prereleases and internal details. +RELEASE_DISCORD_WEBHOOK_URL= +# Internal workflow success / failure / cancelled status. +WORKFLOW_DISCORD_WEBHOOK_URL= +# Build durations, artifact sizes and platform build results. +BUILD_METRICS_DISCORD_WEBHOOK_URL= +# Coverage, lint, test and security summaries. +QUALITY_METRICS_DISCORD_WEBHOOK_URL= +# Aggregated crashes / errors; redact personal data and report contents. +ERROR_METRICS_DISCORD_WEBHOOK_URL= +# Aggregated usage / Loki alert summaries; preserve telemetry consent. +TELEMETRY_METRICS_DISCORD_WEBHOOK_URL= +# Sync backlog, retries, conflicts and failed deliveries. +SYNC_METRICS_DISCORD_WEBHOOK_URL= + +# LEGACY — former Actions CI / release inputs; configure only when a job +# explicitly consumes them. Current Jenkins check/build matrix uses none. +# GITHUB_TOKEN was runner-provided in Actions; Forgejo used the same name. +# FORGEJO_TOKEN / GH_TOKEN were assigned by the former jobs. +GITHUB_TOKEN= +FORGEJO_TOKEN= +GH_TOKEN= +WINDOWS_SIGN_PFX_B64= +WINDOWS_SIGN_PASSWORD= +# Signing script reads CODE_SIGN_PFX_PASSWORD; path/thumbprint are wrapper +# conventions documented in build/installer/CODE_SIGNING.md. +CODE_SIGN_PFX= +CODE_SIGN_PFX_PASSWORD= +CODE_SIGN_THUMBPRINT= +# ACTIVE — optional local coverage helper. +CODACY_PROJECT_TOKEN= +# RESERVED / documented conventions: the current coverage wrapper does not +# explicitly read or forward these overrides; verify reporter support first. +# CODACY_API_BASE_URL=https://api.codacy.com +# CODACY_REPORTER_VERSION= +# Remote macOS manual test helper (requires a configured SSH host). +MACOS_TEST_HOST= +# MACOS_TEST_DIR=~/gregModmanager-manual-test +MACOS_TEST_ARCH=arm64 +# Gate inputs normally supplied by CI, not by the desktop app. +# STAGE=dev +# KIND=patch +NEEDS_REFS=false +DEV_COV=0 +BASE_COV=0 + +# RESERVED — server-side GitHub mirror / synchronization service. +# Separate from the desktop Report Assistant token above. +GITHUB_API_URL=https://api.github.com +GITHUB_REPOSITORY= +GITHUB_SYNC_TOKEN= +GITHUB_WEBHOOK_SECRET= + +# RESERVED — Bugsink ingestion and management / sync service. +# No Bugsink/Sentry reader exists in the active Rust workspace today. +# DSN is an ingestion address, NOT a management API token. +# Confirm API capabilities and webhook support against your deployed Bugsink. +BUGSINK_DSN= +SENTRY_DSN= +BUGSINK_BASE_URL= +BUGSINK_API_TOKEN= +BUGSINK_PROJECT_ID= +BUGSINK_WEBHOOK_SECRET= + +# RESERVED in this repo — direct MantisNext report / sync client. +# Origin only; existing target route is /api/v1/issues (GET, POST). +# Create token in MantisNext account settings; Authorization: Bearer . +# Token needs issues:read / issues:write and project membership/access. +MANTIS_NEXT_BASE_URL= +MANTIS_NEXT_API_TOKEN= +MANTIS_NEXT_PROJECT_ID= +# Optional UUIDs belonging to that project; omit if unused. +MANTIS_NEXT_CATEGORY_ID= +MANTIS_NEXT_VERSION_ID= +# Existing target receiver /api/webhooks/jenkins; client must send Bearer token. +MANTIS_NEXT_JENKINS_WEBHOOK_URL= + +# ACTIVE on MantisNext web/worker ONLY, not consumed by gregModmanager. +# Configure the same Plane settings on the web service and integration worker. +PLANE_API_BASE_URL=https://api.plane.so +PLANE_WEB_BASE_URL= +PLANE_WORKSPACE_SLUG= +PLANE_API_KEY= +# Same receiver secrets must be configured at each sending provider. +PLANE_WEBHOOK_SECRET= +FORGEJO_WEBHOOK_SECRET= +JENKINS_WEBHOOK_TOKEN= +# True only after a separate persistent integrations:worker is deployed. +INTEGRATION_WORKER_ENABLED=false +# RESERVED: record intended Plane UUID for provisioning; actual MantisNext +# project mapping is stored via /integrations, not read from this variable. +PLANE_PROJECT_ID= + +# RESERVED — shared bridge configuration for a future full mirror. +# Credentials alone do not implement synchronization; keep disabled for now. +ISSUE_SYNC_ENABLED=false +ISSUE_SYNC_DRY_RUN=true +# Versioned mapping: project/issue IDs, users, states, priorities and labels. +# Must also persist delivery IDs, checkpoints and conflict decisions durably. +ISSUE_SYNC_MAPPING_FILE= +ISSUE_SYNC_POLL_INTERVAL_SECONDS=60 +ISSUE_SYNC_RETRY_LIMIT=5 +# Proposed conflict policy: queue for review rather than overwrite silently. +ISSUE_SYNC_CONFLICT_POLICY=manual + +# ACTIVE — generated per-child managed runtime handshake, not user secrets. +# The manager sets these only on a reviewed modded game process. Do not set +# them globally; each launch needs a fresh nonce/acknowledgement. +# GREGMODMANAGER_MANAGED=1 +# GREGMODMANAGER_ROOT=/absolute/manager/base +# GREGMODMANAGER_SESSION= +# GREGMODMANAGER_READY=/Configs/runtime/.ready.json +# Legacy Companion source discovery (not the managed launch contract): +# GREGMODMANAGER_SOURCES= diff --git a/.forgejo/FUNDING.yml b/.forgejo/FUNDING.yml new file mode 100644 index 0000000..da883d5 --- /dev/null +++ b/.forgejo/FUNDING.yml @@ -0,0 +1,5 @@ +github: [mleem97] +custom: + - https://github.com/sponsors/mleem97 + - https://gregframework.eu + - https://datacentermods.com diff --git a/.forgejo/ISSUE_TEMPLATE/bug_report_de.yml b/.forgejo/ISSUE_TEMPLATE/bug_report_de.yml new file mode 100644 index 0000000..86adb6a --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/bug_report_de.yml @@ -0,0 +1,95 @@ +name: "🇩🇪 Fehlerbericht" +description: "Melde einen reproduzierbaren Fehler im Modmanager" +title: "[BUG]: " +labels: ["bug"] +body: + - type: markdown + attributes: + value: | + Danke, dass du diesen Fehler meldest. + Bitte gib so viele Details wie möglich an, damit wir ihn schnell beheben können. + + - type: textarea + id: summary + attributes: + label: Was ist passiert? + description: Eine klare und präzise Zusammenfassung des Problems. + placeholder: "Wenn ich auf ... klicke, macht die App ..." + validations: + required: true + + - type: textarea + id: steps + attributes: + label: Schritte zur Reproduktion + description: Genaue Schritte, um den Fehler auszulösen. + placeholder: | + 1. Öffne ... + 2. Klicke auf ... + 3. Der Fehler ... tritt auf + validations: + required: true + + - type: textarea + id: expected + attributes: + label: Erwartetes Verhalten + placeholder: "Ich habe erwartet, dass die Mod aktiviert wird und..." + validations: + required: true + + - type: dropdown + id: os + attributes: + label: Betriebssystem + options: + - Windows 11 + - Windows 10 + - Linux + - macOS + validations: + required: true + + - type: input + id: app_version + attributes: + label: Modmanager-Version + placeholder: "z.B. 1.0.2" + validations: + required: true + + - type: input + id: game_version + attributes: + label: Spielversion + description: Welche Version des Spiels moddest du? + placeholder: "z.B. v1.5.2" + + - type: dropdown + id: install_type + attributes: + label: Installationsart + options: + - Installer + - Portable / Lokale Installation + - Selbst kompiliert (Built from source) + - Unsicher + validations: + required: true + + - type: textarea + id: logs + attributes: + label: Relevante Logs / Screenshots + description: Kopiere Logs aus Einstellungen -> Logs oder ziehe Screenshots hier hinein. + render: shell + + - type: checkboxes + id: checklist + attributes: + label: Vor dem Absenden + options: + - label: Ich habe in den bestehenden Issues gesucht, um sicherzugehen, dass dies noch nicht gemeldet wurde. + required: true + - label: Ich habe klare Schritte zur Reproduktion hinzugefügt. + required: true diff --git a/.forgejo/ISSUE_TEMPLATE/bug_report_en.yml b/.forgejo/ISSUE_TEMPLATE/bug_report_en.yml new file mode 100644 index 0000000..fbcb415 --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/bug_report_en.yml @@ -0,0 +1,95 @@ +name: "🇬🇧 Bug Report" +description: "Report a reproducible bug in the Mod Manager" +title: "[BUG]: " +labels: ["bug"] +body: + - type: markdown + attributes: + value: | + Thanks for reporting this issue. + Please provide as much detail as possible so we can reproduce and fix it quickly. + + - type: textarea + id: summary + attributes: + label: What happened? + description: Clear and concise summary of the problem. + placeholder: "When I click ..., the app ..." + validations: + required: true + + - type: textarea + id: steps + attributes: + label: Steps to reproduce + description: Exact steps to reproduce the issue. + placeholder: | + 1. Open ... + 2. Click ... + 3. See error ... + validations: + required: true + + - type: textarea + id: expected + attributes: + label: Expected behavior + placeholder: "I expected the mod to enable and..." + validations: + required: true + + - type: dropdown + id: os + attributes: + label: Operating System + options: + - Windows 11 + - Windows 10 + - Linux + - macOS + validations: + required: true + + - type: input + id: app_version + attributes: + label: Mod Manager version + placeholder: "e.g. 1.0.2" + validations: + required: true + + - type: input + id: game_version + attributes: + label: Game version + description: Which version of the game are you modding? + placeholder: "e.g. v1.5.2" + + - type: dropdown + id: install_type + attributes: + label: Installation type + options: + - Installer + - Portable / Local install + - Built from source + - Not sure + validations: + required: true + + - type: textarea + id: logs + attributes: + label: Relevant logs / screenshots + description: Paste logs from Settings -> Logs or drag & drop screenshots here. + render: shell + + - type: checkboxes + id: checklist + attributes: + label: Before submitting + options: + - label: I searched existing issues to make sure this hasn't been reported yet. + required: true + - label: I included clear reproduction steps. + required: true diff --git a/.forgejo/ISSUE_TEMPLATE/config.yml b/.forgejo/ISSUE_TEMPLATE/config.yml new file mode 100644 index 0000000..f299d58 --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/config.yml @@ -0,0 +1,5 @@ +blank_issues_enabled: false +contact_links: + - name: Discussions / Questions + url: https://github.com/mleem97/gregModmanager/discussions + about: Ask general questions and discuss ideas. diff --git a/.forgejo/ISSUE_TEMPLATE/crash_report.yml b/.forgejo/ISSUE_TEMPLATE/crash_report.yml new file mode 100644 index 0000000..09936f5 --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/crash_report.yml @@ -0,0 +1,85 @@ +name: "Crash report" +description: "Report a crash / app closes unexpectedly" +title: "[Crash]: " +labels: ["bug", "crash"] +body: + - type: markdown + attributes: + value: | + Use this template when the app crashes or closes unexpectedly. + + - type: dropdown + id: crash_phase + attributes: + label: When did it crash? + options: + - On startup + - While opening a project + - While editing metadata + - While publishing/uploading + - While browsing Mod Store + - During installation/update + - Other + validations: + required: true + + - type: textarea + id: steps + attributes: + label: Reproduction steps + placeholder: | + 1. Start app + 2. Open project ... + 3. Click ... + 4. App crashes + validations: + required: true + + - type: input + id: app_version + attributes: + label: App version + placeholder: "e.g. 1.0.2" + validations: + required: true + + - type: dropdown + id: install_type + attributes: + label: Installation type + options: + - Installer (Program Files) + - Portable/local install + - Build from source + validations: + required: true + + - type: textarea + id: logs + attributes: + label: App logs + description: Paste logs from `%LOCALAPPDATA%\\gregModmanager\\logs`. + render: shell + + - type: textarea + id: dumps + attributes: + label: Crash dumps (optional) + description: If LocalDumps are enabled, mention dump path or attach dump metadata. + placeholder: "%LOCALAPPDATA%\\gregModmanager\\dumps" + + - type: textarea + id: event_viewer + attributes: + label: Event Viewer error (optional) + description: Paste faulting module and exception code from Windows Event Viewer. + + - type: checkboxes + id: checklist + attributes: + label: Before submitting + options: + - label: I reproduced this at least once. + required: true + - label: I included logs or Event Viewer details. + required: true diff --git a/.forgejo/ISSUE_TEMPLATE/documentation_improvement.yml b/.forgejo/ISSUE_TEMPLATE/documentation_improvement.yml new file mode 100644 index 0000000..c6e16a3 --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/documentation_improvement.yml @@ -0,0 +1,26 @@ +name: "Documentation improvement" +description: "Report missing/unclear docs or suggest documentation updates" +title: "[Docs]: " +labels: ["documentation"] +body: + - type: input + id: location + attributes: + label: Docs location + placeholder: "README.md section, wiki page, etc." + validations: + required: true + + - type: textarea + id: issue + attributes: + label: What is wrong or missing? + placeholder: "This section is outdated / missing install steps ..." + validations: + required: true + + - type: textarea + id: suggestion + attributes: + label: Suggested change + placeholder: "Replace/add text ..." diff --git a/.forgejo/ISSUE_TEMPLATE/feature_request.yml b/.forgejo/ISSUE_TEMPLATE/feature_request.yml new file mode 100644 index 0000000..4da2bba --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/feature_request.yml @@ -0,0 +1,33 @@ +name: "Feature request" +description: "Suggest a new feature or improvement" +title: "[Feature]: " +labels: ["enhancement"] +body: + - type: textarea + id: problem + attributes: + label: Problem / use case + description: What problem would this feature solve? + placeholder: "It's hard to ..." + validations: + required: true + + - type: textarea + id: proposal + attributes: + label: Proposed solution + placeholder: "Add a button/setting/workflow that ..." + validations: + required: true + + - type: textarea + id: alternatives + attributes: + label: Alternatives considered + placeholder: "Current workaround ..." + + - type: textarea + id: extra + attributes: + label: Additional context + placeholder: "Mockups, links, examples ..." diff --git a/.forgejo/ISSUE_TEMPLATE/installer_problem.yml b/.forgejo/ISSUE_TEMPLATE/installer_problem.yml new file mode 100644 index 0000000..b0bf52a --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/installer_problem.yml @@ -0,0 +1,49 @@ +name: "Installer / update problem" +description: "Setup, install, uninstall, or update issue" +title: "[Installer]: " +labels: ["bug", "installer"] +body: + - type: textarea + id: summary + attributes: + label: Problem summary + placeholder: "Installer fails / app crashes only after install / update did not replace files ..." + validations: + required: true + + - type: textarea + id: steps + attributes: + label: Steps to reproduce + placeholder: | + 1. Run setup ... + 2. Install to default path ... + 3. Launch app ... + 4. Observe ... + validations: + required: true + + - type: input + id: setup_version + attributes: + label: Setup/app version + placeholder: "e.g. 1.0.2" + + - type: input + id: install_path + attributes: + label: Install path + placeholder: "e.g. C:\\Program Files\\gregModmanager" + + - type: textarea + id: setup_logs + attributes: + label: Setup logs or messages + description: Include any installer error dialogs or logs. + + - type: textarea + id: app_logs + attributes: + label: App logs after install + description: Paste relevant lines from `%LOCALAPPDATA%\\gregModmanager\\logs`. + render: shell diff --git a/.forgejo/ISSUE_TEMPLATE/performance_issue.yml b/.forgejo/ISSUE_TEMPLATE/performance_issue.yml new file mode 100644 index 0000000..e9c865f --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/performance_issue.yml @@ -0,0 +1,38 @@ +name: "Performance issue" +description: "Report slowdowns, freezes, or high resource usage" +title: "[Performance]: " +labels: ["performance"] +body: + - type: textarea + id: summary + attributes: + label: What is slow? + placeholder: "Loading projects takes 30s ..." + validations: + required: true + + - type: textarea + id: scenario + attributes: + label: Scenario + placeholder: "What action causes the slowdown?" + validations: + required: true + + - type: input + id: dataset + attributes: + label: Project size / count + placeholder: "e.g. 120 projects, 2GB content" + + - type: textarea + id: measurements + attributes: + label: Measurements (optional) + description: CPU, memory, timings, profiler snapshots. + + - type: input + id: app_version + attributes: + label: App version + placeholder: "e.g. 1.0.2" diff --git a/.forgejo/ISSUE_TEMPLATE/question.yml b/.forgejo/ISSUE_TEMPLATE/question.yml new file mode 100644 index 0000000..aeaeb5a --- /dev/null +++ b/.forgejo/ISSUE_TEMPLATE/question.yml @@ -0,0 +1,18 @@ +name: "Question / support" +description: "Ask a usage question" +title: "[Question]: " +labels: ["question"] +body: + - type: textarea + id: question + attributes: + label: Your question + placeholder: "How do I ...?" + validations: + required: true + + - type: textarea + id: context + attributes: + label: Context + description: What you already tried, app version, install type. diff --git a/.forgejo/PULL_REQUEST_TEMPLATE.md b/.forgejo/PULL_REQUEST_TEMPLATE.md new file mode 100644 index 0000000..48e9e4f --- /dev/null +++ b/.forgejo/PULL_REQUEST_TEMPLATE.md @@ -0,0 +1,15 @@ +## Description + + +## Motivation and Context + + +## Types of changes +- [ ] Bug fix (non-breaking change which fixes an issue) +- [ ] New feature (non-breaking change which adds functionality) +- [ ] Breaking change (fix or feature that would cause existing functionality to not work as expected) + +## Checklist: +- [ ] My code follows the code style of this project. +- [ ] I have updated the documentation accordingly. +- [ ] I have added tests to cover my changes. diff --git a/.forgejo/copilot-instructions.md b/.forgejo/copilot-instructions.md new file mode 100644 index 0000000..ede9ed2 --- /dev/null +++ b/.forgejo/copilot-instructions.md @@ -0,0 +1,8 @@ +# Copilot Instructions + +This file contains agent-oriented instructions for the `gregModmanager` repository. +Read this before modifying code, building, or creating pull requests. + +--- + +Always follow all instructions that are Stated in ../AGENTS.md, as well as any instructions in this file. If there are conflicts, prioritize the instructions in AGENTS.md. diff --git a/.forgejo/instructions/codacy.instructions.md b/.forgejo/instructions/codacy.instructions.md new file mode 100644 index 0000000..abc5a1b --- /dev/null +++ b/.forgejo/instructions/codacy.instructions.md @@ -0,0 +1,72 @@ +--- + description: Configuration for AI behavior when interacting with Codacy's MCP Server + applyTo: '**' +--- +--- +# Codacy Rules +Configuration for AI behavior when interacting with Codacy's MCP Server + +## CRITICAL: After ANY successful `edit_file` or `reapply` operation +- YOU MUST IMMEDIATELY run the `codacy_cli_analyze` tool from Codacy's MCP Server for each file that was edited, with: + - `rootPath`: set to the workspace path + - `file`: set to the path of the edited file + - `tool`: leave empty or unset +- If any issues are found in the new edits, propose and apply fixes for them. +- > NOTE: Failure to follow this rule is considered a critical error. + +## When you tried to run the `codacy_cli_analyze` tool and the Codacy CLI is not installed +- Ask the user 'Codacy CLI is not installed. Would you like me to install it now?' +- If the user responds with "yes", run the `codacy_cli_install` tool and then continue with the original task +- If the user responds with "no", instruct the user that they can disable automatic analysis in the extension settings +- Wait for the user to respond before proceeding with any other actions + +## After every response +- If you made any file edits in this conversation, verify you ran `codacy_cli_analyze` tool from Codacy's MCP Server + +## When there are no Codacy MCP Server tools available, or the MCP Server is not reachable +- Suggest the user the following troubleshooting steps: + - Try to reset the MCP on the extension + - If the user is using VSCode, suggest them to review their Copilot > MCP settings in Github, under their organization or personal account. Refer them to Settings > Copilot > Enable MCP servers in Copilot. Suggested URL (https://github.com/settings/copilot/features) or https://github.com/organizations/{organization-name}/settings/copilot/features (This can only be done by their organization admins / owners) +- If none of the above steps work, suggest the user to contact Codacy support + +## Trying to call a tool that needs a rootPath as a parameter +- Always use the standard, non-URL-encoded file system path + +## CRITICAL: Dependencies and Security Checks +- IMMEDIATELY after ANY of these actions: + - Running npm/yarn/pnpm install + - Adding dependencies to package.json + - Adding requirements to requirements.txt + - Adding dependencies to pom.xml + - Adding dependencies to build.gradle + - Any other package manager operations +- You MUST run the `codacy_cli_analyze` tool with: + - `rootPath`: set to the workspace path + - `tool`: set to "trivy" + - `file`: leave empty or unset +- If any vulnerabilities are found because of the newly added packages: + - Stop all other operations + - Propose and apply fixes for the security issues + - Only continue with the original task after security issues are resolved +- EXAMPLE: + - After: npm install react-markdown + - Do: Run codacy_cli_analyze with trivy + - Before: Continuing with any other tasks + +## General +- Repeat the relevant steps for each modified file. +- "Propose fixes" means to both suggest and, if possible, automatically apply the fixes. +- You MUST NOT wait for the user to ask for analysis or remind you to run the tool. +- Do not run `codacy_cli_analyze` looking for changes in duplicated code or code complexity metrics. +- Complexity metrics are different from complexity issues. When trying to fix complexity in a repository or file, focus on solving the complexity issues and ignore the complexity metric. +- Do not run `codacy_cli_analyze` looking for changes in code coverage. +- Do not try to manually install Codacy CLI using either brew, npm, npx, or any other package manager. +- If the Codacy CLI is not installed, just run the `codacy_cli_analyze` tool from Codacy's MCP Server. +- When calling `codacy_cli_analyze`, only send provider, organization and repository if the project is a git repository. + +## Whenever a call to a Codacy tool that uses `repository` or `organization` as a parameter returns a 404 error +- Offer to run the `codacy_setup_repository` tool to add the repository to Codacy +- If the user accepts, run the `codacy_setup_repository` tool +- Do not ever try to run the `codacy_setup_repository` tool on your own +- After setup, immediately retry the action that failed (only retry once) +--- diff --git a/.forgejo/scripts/malicious_scan.py b/.forgejo/scripts/malicious_scan.py new file mode 100644 index 0000000..b0fff22 --- /dev/null +++ b/.forgejo/scripts/malicious_scan.py @@ -0,0 +1,393 @@ +#!/usr/bin/env python3 +import argparse +import json +import re +import subprocess +from dataclasses import dataclass +from pathlib import Path +from typing import Dict, List, Pattern, Tuple + + +@dataclass +class Finding: + rule_id: str + message: str + severity: str + file_path: str + start_line: int + description: str + + +@dataclass(frozen=True) +class ScanPatterns: + secret: Pattern[str] + secret_assignment: Pattern[str] + network: Pattern[str] + system: Pattern[str] + obfuscation: Pattern[str] + + +SCAN_EXTENSIONS = { + ".cs", ".csx", ".ps1", ".psm1", ".py", ".js", ".jsx", ".ts", ".tsx", ".mjs", ".cjs", + ".sh", ".bash", ".zsh", ".cmd", ".bat", ".yml", ".yaml", ".json", ".toml", ".ini", ".env", + ".sql", ".rb", ".php", ".java", ".kt", ".go", ".rs", +} + + +def run_git(args: List[str]) -> str: + validate_git_args(args) + result = subprocess.run( + ["git", *args], + capture_output=True, + text=True, + encoding="utf-8", + errors="replace", + check=False, + ) + if result.returncode != 0: + raise RuntimeError(f"Git command failed: {result.stderr.strip()}") + return result.stdout or "" + + +def validate_git_args(args: List[str]) -> None: + if not args: + raise ValueError("At least one git argument is required.") + + for arg in args: + if not arg or "\x00" in arg or "\n" in arg or "\r" in arg: + raise ValueError("Invalid git argument.") + + +def git_changed_files(days: int) -> List[str]: + out = run_git([ + "log", + f"--since={days} days ago", + "--name-only", + "--pretty=format:", + ]) + files = sorted({line.strip() for line in out.splitlines() if line.strip()}) + return [f for f in files if Path(f).is_file()] + + +def is_scannable(path: Path) -> bool: + suffix = path.suffix.lower() + if suffix not in SCAN_EXTENSIONS: + return False + if any(part.startswith(".") and part not in {".github"} for part in path.parts): + return False + return True + + +def git_added_lines(days: int) -> Dict[str, List[Tuple[int, str]]]: + out = run_git([ + "log", + f"--since={days} days ago", + "--patch", + "--unified=0", + "--pretty=format:", + ]) + + file_lines: Dict[str, List[Tuple[int, str]]] = {} + current_file: str = "" + current_new_line: int = 0 + + for raw in out.splitlines(): + current_file, current_new_line = parse_diff_line(raw, current_file, current_new_line, file_lines) + + return {k: v for k, v in file_lines.items() if v} + + +def parse_diff_line(raw: str, current_file: str, current_new_line: int, file_lines: Dict[str, List[Tuple[int, str]]]) -> Tuple[str, int]: + line = raw.rstrip("\n") + if line.startswith("+++ b/"): + return select_current_file(line, file_lines), current_new_line + + if line.startswith("@@"): + return current_file, read_hunk_line_number(line, current_new_line) + + if not current_file: + return current_file, current_new_line + + if line.startswith("+") and not line.startswith("+++"): + file_lines[current_file].append((current_new_line, line[1:])) + return current_file, current_new_line + 1 + + if line.startswith("-"): + return current_file, current_new_line + + return current_file, current_new_line + 1 + + +def select_current_file(line: str, file_lines: Dict[str, List[Tuple[int, str]]]) -> str: + candidate = line[6:] + path = Path(candidate) + if path.is_file() and is_scannable(path): + file_lines.setdefault(candidate, []) + return candidate + return "" + + +def read_hunk_line_number(line: str, fallback: int) -> int: + match = re.search(r"\+(\d+)(?:,(\d+))?", line) + return int(match.group(1)) if match else fallback + + +def git_recent_commits(days: int) -> List[str]: + out = run_git([ + "log", + f"--since={days} days ago", + "--pretty=format:%h - %an, %ar : %s", + ]) + return [line for line in out.splitlines() if line.strip()] + + +def first_match_line(added_lines: List[Tuple[int, str]], pattern: Pattern[str]) -> int: + for line_number, text in added_lines: + if pattern.search(text): + return line_number + return 1 + + +def map_severity(score: int) -> str: + if score >= 7: + return "error" + if score >= 3: + return "warning" + return "note" + + +def compile_patterns() -> ScanPatterns: + return ScanPatterns( + secret=re.compile(r"(secret|token|password|apikey|api[_-]?key|private[_-]?key)", re.IGNORECASE), + secret_assignment=re.compile(r"(secret|token|password|apikey|api[_-]?key|private[_-]?key)\s*[:=]\s*['\"][^'\"]{8,}", re.IGNORECASE), + network=re.compile(r"(curl\s|wget\s|http[s]?://|requests\.|fetch\(|http\.get|HttpClient|Invoke-RestMethod)", re.IGNORECASE), + system=re.compile(r"(Process\.Start|cmd\.exe|powershell\.exe|/bin/sh|subprocess\.|Runtime\.getRuntime\(\)\.exec)", re.IGNORECASE), + obfuscation=re.compile(r"([A-Za-z0-9+/]{120,}={0,2}|\\x[0-9a-fA-F]{2}\\x[0-9a-fA-F]{2}\\x[0-9a-fA-F]{2,})"), + ) + + +def analyze_files(added_by_file: Dict[str, List[Tuple[int, str]]]) -> List[Finding]: + patterns = compile_patterns() + findings: List[Finding] = [] + + for file_path, added_lines in added_by_file.items(): + findings.extend(analyze_added_lines(file_path, added_lines, patterns)) + + return deduplicate_findings(findings) + + +def analyze_added_lines(file_path: str, added_lines: List[Tuple[int, str]], patterns: ScanPatterns) -> List[Finding]: + added_text = "\n".join(text for _, text in added_lines) + findings: List[Finding] = [] + + has_secret = bool(patterns.secret.search(added_text)) + has_secret_assignment = bool(patterns.secret_assignment.search(added_text)) + has_network = bool(patterns.network.search(added_text)) + + if has_secret_assignment and has_network: + findings.append(secret_exfiltration_finding(file_path, added_lines, patterns)) + if has_network and not has_secret: + findings.append(network_finding(file_path, added_lines, patterns.network)) + if patterns.system.search(added_text): + findings.append(system_access_finding(file_path, added_lines, patterns.system)) + if patterns.obfuscation.search(added_text): + findings.append(obfuscation_finding(file_path, added_lines, patterns.obfuscation)) + + return findings + + +def secret_exfiltration_finding(file_path: str, added_lines: List[Tuple[int, str]], patterns: ScanPatterns) -> Finding: + return Finding( + rule_id="malicious-code-scanner/secret-exfiltration", + message="Potential secret exfiltration pattern detected", + severity=map_severity(9), + file_path=file_path, + start_line=min(first_match_line(added_lines, patterns.secret_assignment), first_match_line(added_lines, patterns.network)), + description=( + "Threat score: 9/10. This file contains both secret-related terms and network transfer patterns. " + "Review if any sensitive values are read and transmitted externally." + ), + ) + + +def network_finding(file_path: str, added_lines: List[Tuple[int, str]], pattern: Pattern[str]) -> Finding: + return Finding( + rule_id="malicious-code-scanner/suspicious-network", + message="Unusual network activity pattern in recent changes", + severity=map_severity(5), + file_path=file_path, + start_line=first_match_line(added_lines, pattern), + description=( + "Threat score: 5/10. Network-related operations were introduced in recent changes. " + "Verify destination domains and business justification." + ), + ) + + +def system_access_finding(file_path: str, added_lines: List[Tuple[int, str]], pattern: Pattern[str]) -> Finding: + return Finding( + rule_id="malicious-code-scanner/system-access", + message="Suspicious system/process execution pattern", + severity=map_severity(6), + file_path=file_path, + start_line=first_match_line(added_lines, pattern), + description=( + "Threat score: 6/10. Process or shell execution pattern detected. " + "Validate command safety and ensure no user-controlled command injection path exists." + ), + ) + + +def obfuscation_finding(file_path: str, added_lines: List[Tuple[int, str]], pattern: Pattern[str]) -> Finding: + return Finding( + rule_id="malicious-code-scanner/obfuscation", + message="Possible obfuscation or encoded payload pattern", + severity=map_severity(4), + file_path=file_path, + start_line=first_match_line(added_lines, pattern), + description=( + "Threat score: 4/10. Long encoded/obfuscated-looking strings detected. " + "Confirm these are expected assets/config blobs and not hidden payloads." + ), + ) + + +def deduplicate_findings(findings: List[Finding]) -> List[Finding]: + dedup = {} + for f in findings: + key = (f.rule_id, f.file_path, f.start_line) + if key not in dedup: + dedup[key] = f + return list(dedup.values()) + + +def make_sarif(findings: List[Finding]) -> dict: + return { + "version": "2.1.0", + "$schema": "https://json.schemastore.org/sarif-2.1.0.json", + "runs": [{ + "tool": {"driver": make_sarif_driver(findings)}, + "results": [make_sarif_result(f) for f in findings], + }], + } + + +def make_sarif_driver(findings: List[Finding]) -> dict: + rules = {} + for f in findings: + if f.rule_id not in rules: + rules[f.rule_id] = { + "id": f.rule_id, + "name": f.rule_id.split("/")[-1], + "shortDescription": {"text": f.message}, + "help": {"text": f.description}, + "properties": {"tags": ["security", "malicious-code-scan"]}, + } + return {"name": "Malicious Code Scanner", "informationUri": "https://github.com", "rules": list(rules.values())} + + +def make_sarif_result(finding: Finding) -> dict: + return { + "ruleId": finding.rule_id, + "level": finding.severity, + "message": {"text": finding.message}, + "locations": [{ + "physicalLocation": { + "artifactLocation": {"uri": finding.file_path.replace('\\', '/')}, + "region": {"startLine": max(1, finding.start_line)}, + } + }], + } + + +def parse_args() -> argparse.Namespace: + parser = argparse.ArgumentParser() + parser.add_argument("--days", type=int, default=3) + parser.add_argument("--output", required=True) + parser.add_argument("--summary", required=True) + return parser.parse_args() + + +def run_scan(days: int) -> Tuple[List[str], List[str], List[Finding], dict]: + commits = git_recent_commits(days) + files = [f for f in git_changed_files(days) if is_scannable(Path(f))] + findings = analyze_files(git_added_lines(days)) + return commits, files, findings, make_sarif(findings) + + +def write_scan_outputs(output: str, summary: str, days: int, commits: List[str], files: List[str], findings: List[Finding], sarif: dict) -> None: + Path(output).write_text(json.dumps(sarif, indent=2), encoding="utf-8") + summary_text = build_summary(days, commits, files, findings) + Path(summary).write_text(summary_text + "\n", encoding="utf-8") + print(summary_text) + + +def build_summary(days: int, commits: List[str], files: List[str], findings: List[Finding]) -> str: + summary_lines = [ + "Daily malicious code scan completed.", + f"Analysis window: last {days} days", + f"Commits reviewed: {len(commits)}", + f"Files analyzed: {len(files)}", + f"Findings: {len(findings)}", + "Patterns checked: secret-exfiltration, suspicious-network, system-access, obfuscation", + ] + append_commit_summary(summary_lines, commits) + append_finding_summary(summary_lines, findings) + return "\n".join(summary_lines) + + +def append_commit_summary(summary_lines: List[str], commits: List[str]) -> None: + if commits: + summary_lines.append("") + summary_lines.append("Recent commits:") + summary_lines.extend([f"- {c}" for c in commits[:30]]) + + +def append_finding_summary(summary_lines: List[str], findings: List[Finding]) -> None: + summary_lines.append("") + if not findings: + summary_lines.append("No suspicious patterns detected.") + return + + summary_lines.append("Findings:") + for f in findings: + summary_lines.append(f"- [{f.severity}] {f.rule_id} :: {f.file_path}:{f.start_line}") + + +def make_error_sarif(message: str) -> dict: + return { + "version": "2.1.0", + "$schema": "https://json.schemastore.org/sarif-2.1.0.json", + "runs": [{ + "tool": {"driver": {"name": "Malicious Code Scanner"}}, + "results": [{ + "ruleId": "malicious-code-scanner/system-access", + "level": "warning", + "message": {"text": message}, + "locations": [{ + "physicalLocation": { + "artifactLocation": {"uri": ".github/scripts/malicious_scan.py"}, + "region": {"startLine": 1}, + } + }], + }], + }], + } + + +def main() -> int: + args = parse_args() + try: + commits, files, findings, sarif = run_scan(args.days) + write_scan_outputs(args.output, args.summary, args.days, commits, files, findings, sarif) + return 0 + except Exception as ex: + message = f"Scanner execution error: {ex}" + Path(args.output).write_text(json.dumps(make_error_sarif(message), indent=2), encoding="utf-8") + Path(args.summary).write_text(f"Scanner failed: {ex}\n", encoding="utf-8") + print(f"Scanner failed: {ex}") + return 0 + + +if __name__ == "__main__": + raise SystemExit(main()) diff --git a/.forgejo/workflows/build-and-release.yml b/.forgejo/workflows/build-and-release.yml deleted file mode 100644 index 2dac7c0..0000000 --- a/.forgejo/workflows/build-and-release.yml +++ /dev/null @@ -1,418 +0,0 @@ -name: Build & Release - -# Dual CI: Forgejo Actions (.forgejo/workflows/) + Gitea Actions -# (.gitea/workflows/). Both directories MUST stay byte-identical — the -# `parity` job below fails the run when the copies drift. -# .github/workflows/ does not exist on purpose: GitHub is a read-only -# archive mirror, so no automation runs there. -# -# Rust restart: the C# / Avalonia sources are frozen under -# .reference/modmanager-old/ and no longer build on main — all build jobs -# below compile the Rust workspace (crates/* + xtask). Portable artifacts -# come straight out of `cargo xtask dist`. -# macOS has no runner on this instance (all jobs run ubuntu-latest) and -# cannot be cross-built from Linux without the Apple SDK — macOS assets -# are pending a macOS runner, they are NOT faked. -# -# No hardcoded instance URL is needed — links use github.server_url, and the -# container registry host is derived from it. Secrets to configure per -# instance (Forgejo AND Gitea): -# TELEMETRY_ENDPOINT / TELEMETRY_USER / TELEMETRY_API_KEY / TELEMETRY_TENANT, -# DISCORD_WEBHOOK_URL (single notification per run, see `notify` job). -# -# Windows installer is best-effort (Wine + ISCC); the portable ZIP always -# ships. The Inno script registers the `greg://` protocol and skips the -# VC++ redist for Rust builds (/DSkipVCRedist). - -on: - push: - branches: [main] - tags: ['v*'] - pull_request: - branches: [main] - workflow_dispatch: - inputs: - signing: - description: 'Signing mode (Linux hosts: self-signed via osslsigncode if installed, else unsigned)' - type: choice - options: - - none - - self-signed - default: 'none' - -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true - -permissions: - contents: read - -jobs: - version: - name: Resolve Version - runs-on: ubuntu-latest - timeout-minutes: 5 - outputs: - version: ${{ steps.resolve.outputs.version }} - numeric_version: ${{ steps.resolve.outputs.numeric_version }} - is_release: ${{ steps.resolve.outputs.is_release }} - is_pre: ${{ steps.resolve.outputs.is_pre }} - steps: - - uses: actions/checkout@v7 - - id: resolve - shell: bash - run: | - # VERSION file is the single source of truth, workspace Cargo.toml is the fallback. - ver="$(cat VERSION 2>/dev/null | tr -d '\r' | xargs)" - if [ -z "$ver" ]; then - ver=$(sed -n 's:^version = "\(.*\)":\1:p' Cargo.toml | head -n 1 | tr -d '\r' | xargs) - fi - [ -n "$ver" ] || ver='1.6.1' - numeric="${ver%%-*}" - if [[ "$numeric" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then - numeric="$numeric.0" - elif [[ ! "$numeric" =~ ^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+$ ]]; then - numeric='1.6.1.0' - fi - is_release=false - [[ "$GITHUB_REF_NAME" =~ ^v[0-9] ]] && is_release=true - is_pre=false - [[ "$ver" == *-* || "$GITHUB_REF_NAME" == *-* ]] && is_pre=true - { - echo "version=$ver" - echo "numeric_version=$numeric" - echo "is_release=$is_release" - echo "is_pre=$is_pre" - } >> "$GITHUB_OUTPUT" - echo "Version=$ver Numeric=$numeric IsRelease=$is_release IsPre=$is_pre" - - parity: - name: Workflow Parity (.forgejo == .gitea) - runs-on: ubuntu-latest - timeout-minutes: 5 - steps: - - uses: actions/checkout@v7 - - name: Fail when Forgejo/Gitea workflow copies drift - shell: bash - run: | - if ! diff -r .forgejo/workflows .gitea/workflows; then - echo "::error::.forgejo/workflows and .gitea/workflows differ — keep both copies byte-identical." - exit 1 - fi - echo "Workflow copies in sync." - - test: - name: Test - needs: [version, parity] - runs-on: ubuntu-latest - timeout-minutes: 15 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo test --workspace - - build-windows-cross: - name: Build Windows (cross-compiled on Linux) - needs: [version, test] - if: github.event_name != 'pull_request' || github.event.pull_request.draft == false - runs-on: ubuntu-latest - timeout-minutes: 30 - steps: - - uses: actions/checkout@v7 - with: - fetch-depth: 0 - - - uses: dtolnay/rust-toolchain@stable - with: - targets: x86_64-pc-windows-gnu - - - name: Install mingw + zip - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends gcc-mingw-w64-x86-64 zip - - - uses: Swatinem/rust-cache@v2 - - - name: Dist Windows x64 - run: cargo run -p xtask -- dist --target x86_64-pc-windows-gnu - - - name: Self-sign (osslsigncode, best-effort) - if: ${{ inputs.signing == 'self-signed' }} - run: | - STAGE="$(ls -d dist/gregmodmanager-*-win-x64 | head -n 1)" - if command -v osslsigncode >/dev/null 2>&1 && [ -n "${{ secrets.WINDOWS_SIGN_PFX_B64 }}" ]; then - echo "${{ secrets.WINDOWS_SIGN_PFX_B64 }}" | base64 -d > /tmp/sign.pfx - # Primary project URL (Forgejo main repo); GitHub archive mirror as fallback. - info_url="https://git.datacentermods.com/teamGreg/gregModmanager" - # Fallback: https://github.com/mleem97/gregModmanager - osslsigncode sign -pkcs12 /tmp/sign.pfx -pass "${{ secrets.WINDOWS_SIGN_PASSWORD }}" \ - -n "gregModmanager" -i "$info_url" \ - -in "$STAGE/gregmodmanager.exe" -out "$STAGE/gregmodmanager-signed.exe" - mv "$STAGE/gregmodmanager-signed.exe" "$STAGE/gregmodmanager.exe" - rm -f /tmp/sign.pfx - # Re-zip (the xtask archive predates signing) + refresh the hash sidecar. - (cd dist && rm -f ./*.zip ./*.sha256 && zip -r "$(basename "$STAGE").zip" "$(basename "$STAGE")" && sha256sum "$(basename "$STAGE").zip" > "$(basename "$STAGE").zip.sha256") - else - echo "::warning::self-signed requested but osslsigncode or WINDOWS_SIGN_PFX_B64 secret missing — shipping unsigned." - fi - - - name: Inno Setup EXE (Wine, best-effort) - run: | - STAGE="$(ls -d dist/gregmodmanager-*-win-x64 | head -n 1)" - if command -v wine >/dev/null 2>&1 && { command -v iscc >/dev/null 2>&1 || [ -f "$HOME/.wine/drive_c/Program Files (x86)/Inno Setup 6/ISCC.exe" ]; }; then - echo "Attempting Inno Setup build under Wine..." - ISCC_BIN="$(command -v iscc || echo "$HOME/.wine/drive_c/Program Files (x86)/Inno Setup 6/ISCC.exe")" - SRC_WIN="$(winepath -w "$PWD/$STAGE")" - wine "$ISCC_BIN" "build/installer/gregModmanager.iss" \ - "/DAppVersion=${{ needs.version.outputs.version }}" \ - "/DAppNumericVersion=${{ needs.version.outputs.numeric_version }}" \ - "/DSourceDir=${SRC_WIN}" \ - "/DMyAppExeName=gregmodmanager.exe" \ - "/DSkipVCRedist" || echo "::warning::Inno Setup build failed — shipping portable ZIP only." - else - echo "::notice::Wine/ISCC not available — skipping installer EXE, shipping portable ZIP only." - fi - shell: bash - - - name: Upload Windows artifacts - uses: actions/upload-artifact@v7 - with: - name: windows-portable - path: | - dist/gregmodmanager-*-win-x64.zip - dist/gregmodmanager-*-win-x64.zip.sha256 - build/installer/Output/*.exe - if-no-files-found: error - - build-linux: - name: Build Linux - needs: [version, test] - if: github.event_name != 'pull_request' || github.event.pull_request.draft == false - runs-on: ubuntu-latest - timeout-minutes: 30 - steps: - - uses: actions/checkout@v7 - - - uses: dtolnay/rust-toolchain@stable - - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - - uses: Swatinem/rust-cache@v2 - - - name: Dist Linux x64 - run: cargo run -p xtask -- dist - - - name: Upload tarball - uses: actions/upload-artifact@v7 - with: - name: linux-portable - path: | - dist/gregmodmanager-*-linux-x64.tar.gz - dist/gregmodmanager-*-linux-x64.tar.gz.sha256 - if-no-files-found: error - - build-linux-packages: - name: Build Linux Packages (DEB/RPM) - needs: [version, build-linux] - runs-on: ubuntu-latest - timeout-minutes: 15 - steps: - - uses: actions/checkout@v7 - - - name: Install nfpm - run: | - echo 'deb [trusted=yes] https://repo.goreleaser.com/apt/ /' | sudo tee /etc/apt/sources.list.d/goreleaser.list - sudo apt update - sudo apt install -y nfpm - nfpm --version - - - name: Download Linux portable - uses: actions/download-artifact@v8 - with: - name: linux-portable - path: ./artifacts/dl - - - name: Build packages - run: | - mkdir -p ./artifacts/stage ./artifacts/packages - tar -xzf ./artifacts/dl/gregmodmanager-*-linux-x64.tar.gz -C ./artifacts/stage - chmod +x ./build/scripts/linux/build-rust-packages.sh - ./build/scripts/linux/build-rust-packages.sh ./artifacts/stage ${{ needs.version.outputs.version }} ${{ needs.version.outputs.is_pre }} ./artifacts/packages - - - name: Upload packages - uses: actions/upload-artifact@v7 - with: - name: linux-packages - path: artifacts/packages/gregmodmanager-* - if-no-files-found: error - - - name: Build & Push Container (instance registry) - if: github.event_name != 'pull_request' - run: | - # Derive registry host from the instance URL (no hardcoded host). - REGISTRY_HOST="$(echo "${{ github.server_url }}" | sed -e 's|^https\?://||' -e 's|/.*$||')" - IMAGE="oci://${REGISTRY_HOST}/${{ github.repository_owner }}/gregmodmanager" - echo "${{ secrets.GITHUB_TOKEN }}" | docker login "$REGISTRY_HOST" -u ${{ github.actor }} --password-stdin - docker build -t "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:${{ needs.version.outputs.version }}" -t "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:latest" -f - . <<'EOF' - FROM debian:bookworm-slim - RUN apt-get update && apt-get install -y --no-install-recommends fontconfig libfreetype6 && rm -rf /var/lib/apt/lists/* - WORKDIR /opt/gregmodmanager - COPY artifacts/stage/ ./ - RUN chmod +x /opt/gregmodmanager/gregmodmanager - ENTRYPOINT ["/opt/gregmodmanager/gregmodmanager"] - EOF - docker push "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:${{ needs.version.outputs.version }}" - docker push "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:latest" - - release: - name: Release - needs: [version, build-windows-cross, build-linux, build-linux-packages] - runs-on: ubuntu-latest - if: needs.version.outputs.is_release == 'true' && github.event_name != 'pull_request' - timeout-minutes: 10 - permissions: - contents: write - steps: - - name: Download Windows Portable - uses: actions/download-artifact@v8 - with: - name: windows-portable - path: ./dist - - - name: Download Linux Portable - uses: actions/download-artifact@v8 - with: - name: linux-portable - path: ./dist - - - name: Download Linux Packages - uses: actions/download-artifact@v8 - with: - name: linux-packages - path: ./dist - - - name: Create Forgejo release & upload assets - env: - FORGEJO_TOKEN: ${{ secrets.GITHUB_TOKEN }} - TAG_NAME: ${{ github.ref_name }} - IS_PRE: ${{ needs.version.outputs.is_pre }} - run: | - python3 - "$FORGEJO_TOKEN" "${{ github.server_url }}" "${{ github.repository }}" "$TAG_NAME" "$IS_PRE" <<'EOF' - import json, mimetypes, os, sys, urllib.request - - token, server, repo, tag, is_pre = sys.argv[1:6] - api = server.rstrip('/') + '/api/v1' - headers = {'Authorization': f'token {token}', 'Content-Type': 'application/json'} - - def call(method, path, payload=None, raw=None, ctype=None): - data = raw if raw is not None else (json.dumps(payload).encode() if payload is not None else None) - h = dict(headers) - if ctype: - h['Content-Type'] = ctype - req = urllib.request.Request(api + path, data=data, headers=h, method=method) - with urllib.request.urlopen(req) as res: - body = res.read() - return json.loads(body) if body and res.headers.get_content_type() == 'application/json' else body - - release = call('POST', f'/repos/{repo}/releases', { - 'tag_name': tag, - 'name': tag, - 'prerelease': is_pre.lower() == 'true', - 'draft': False, - 'body': f'Release {tag} — built by Forgejo/Gitea Actions.', - }) - rid = release['id'] - print(f"Release id={rid}") - - dist = 'dist' - for root, _, files in os.walk(dist): - for name in sorted(files): - path = os.path.join(root, name) - ctype = mimetypes.guess_type(name)[0] or 'application/octet-stream' - with open(path, 'rb') as fh: - data = fh.read() - req = urllib.request.Request( - f'{api}/repos/{repo}/releases/{rid}/assets?name={name}', - data=data, - headers={'Authorization': f'token {token}', 'Content-Type': ctype}, - method='POST') - with urllib.request.urlopen(req): - print(f'Uploaded {name} ({len(data)} bytes)') - EOF - - notify: - # Exactly ONE Discord message per completed run (push/dispatch only — PR - # runs stay silent so the channel is not spammed). - name: Notify Discord (once) - needs: [version, test, build-windows-cross, build-linux, build-linux-packages, release] - if: always() && github.event_name != 'pull_request' - runs-on: ubuntu-latest - timeout-minutes: 5 - steps: - - name: Send single Discord notification - shell: bash - env: - DISCORD_WEBHOOK_URL: ${{ secrets.DISCORD_WEBHOOK_URL }} - VERSION: ${{ needs.version.outputs.version }} - RUN_URL: ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }} - EVENT: ${{ github.event_name }} - REF: ${{ github.ref_name }} - RESULTS: ${{ toJSON(needs) }} - run: | - if [ -z "$DISCORD_WEBHOOK_URL" ]; then - echo "DISCORD_WEBHOOK_URL is empty, skipping notification." - exit 0 - fi - - if echo "$RESULTS" | grep -q '"result":"failure"'; then - status="❌ Failed"; color=15158332 - elif echo "$RESULTS" | grep -q '"result":"cancelled"'; then - status="⚠️ Cancelled"; color=16776960 - else - status="✅ Success"; color=3066993 - fi - - payload=$(cat <> "$GITHUB_OUTPUT" - - build-packages: - needs: [version] - runs-on: ubuntu-latest - timeout-minutes: 30 - permissions: - contents: read - packages: write - steps: - - uses: actions/checkout@v7 - - - uses: dtolnay/rust-toolchain@stable - - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - - uses: Swatinem/rust-cache@v2 - - - name: Install nfpm - run: | - curl -fsSL -o nfpm.tar.gz "https://github.com/goreleaser/nfpm/releases/latest/download/nfpm_Linux_x86_64.tar.gz" - tar -xzf nfpm.tar.gz nfpm - sudo mv nfpm /usr/local/bin/ - nfpm --version - - - name: Build packages - run: | - cargo run -p xtask -- dist - STAGE="$(ls -d dist/gregmodmanager-*-linux-x64 | head -n 1)" - chmod +x ./build/scripts/linux/build-rust-packages.sh - ./build/scripts/linux/build-rust-packages.sh "$STAGE" ${{ needs.version.outputs.version }} ${{ needs.version.outputs.is_pre }} ./artifacts/rust-linux/packages - - - name: Upload artifacts - uses: actions/upload-artifact@v7 - with: - name: linux-packages-detailed - path: artifacts/rust-linux/packages/gregmodmanager-* - if-no-files-found: error - - - name: Build container (instance registry) - if: github.event_name != 'pull_request' - run: | - REGISTRY_HOST="$(echo "${{ github.server_url }}" | sed -e 's|^https\?://||' -e 's|/.*$||')" - echo "${{ secrets.GITHUB_TOKEN }}" | docker login "$REGISTRY_HOST" -u ${{ github.actor }} --password-stdin - STAGE="$(ls -d dist/gregmodmanager-*-linux-x64 | head -n 1)" - mkdir -p publish && cp -r "$STAGE/"* publish/ - docker build -t "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:${{ needs.version.outputs.version }}" -t "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:latest" -f - . <<'EOF' - FROM debian:bookworm-slim - RUN apt-get update && apt-get install -y --no-install-recommends fontconfig libfreetype6 && rm -rf /var/lib/apt/lists/* - WORKDIR /opt/gregmodmanager - COPY publish/ ./ - RUN chmod +x /opt/gregmodmanager/gregmodmanager - ENTRYPOINT ["/opt/gregmodmanager/gregmodmanager"] - EOF - docker push "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:${{ needs.version.outputs.version }}" - docker push "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:latest" diff --git a/.forgejo/workflows/promote-changelog.yml b/.forgejo/workflows/promote-changelog.yml deleted file mode 100644 index c034fe3..0000000 --- a/.forgejo/workflows/promote-changelog.yml +++ /dev/null @@ -1,93 +0,0 @@ -name: Promote Changelog - -# Dual CI (Forgejo + Gitea) — see build-and-release.yml header for instance notes. -# `origin` is the main instance here (GitHub is a read-only archive mirror). - -on: - workflow_dispatch: - inputs: - version: - description: 'Target version to release (e.g. 1.6.0)' - required: true - create_tag: - description: 'Create and push git tag v{version}' - type: boolean - default: true - -permissions: - contents: write - -jobs: - promote: - name: Promote Changelog & Bump Version - runs-on: ubuntu-latest - timeout-minutes: 10 - steps: - - name: Checkout main - uses: actions/checkout@v7 - with: - ref: main - fetch-depth: 0 - token: ${{ secrets.GITHUB_TOKEN }} - - - name: Validate version format - shell: bash - run: | - ver='${{ github.event.inputs.version }}' - if [[ ! "$ver" =~ ^[0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9.-]+)?$ ]]; then - echo "Invalid version format: $ver. Expected: x.y.z or x.y.z-prerelease" - exit 1 - fi - echo "Version format OK: $ver" - - - name: Promote CHANGELOG.md - shell: bash - run: | - ver='${{ github.event.inputs.version }}' - date="$(date +%F)" - changelog='CHANGELOG.md' - - if ! grep -q '## \[Unreleased\]' "$changelog"; then - echo "CHANGELOG.md does not contain an [Unreleased] section. Nothing to promote." - exit 1 - fi - - new_unreleased=$(printf '## [Unreleased]\n\n### Added\n\n### Changed\n\n### Deprecated\n\n### Removed\n\n### Fixed\n\n### Security\n\n') - python3 - "$changelog" "$ver" "$date" "$new_unreleased" <<'EOF' - import sys - path, ver, date, new_unreleased = sys.argv[1:5] - with open(path, encoding='utf-8') as fh: - content = fh.read() - versioned = f'## [{ver}] - {date}' - content = content.replace('## [Unreleased]', versioned, 1) - content = content.replace(versioned + '\n', versioned + '\n\n' + new_unreleased, 1) - with open(path, 'w', encoding='utf-8', newline='') as fh: - fh.write(content) - print(f'Promoted [Unreleased] to [{ver}] - {date}') - EOF - - - name: Bump version (VERSION file + .csproj fallback copy) - shell: bash - run: | - ver='${{ github.event.inputs.version }}' - printf '%s\n' "$ver" > VERSION - csproj='src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj' - old="$(sed -n 's:.*\([^<]*\).*:\1:p' "$csproj" | head -n 1)" - sed -i "s|[^<]*|${ver}|" "$csproj" - echo "Version: VERSION=$ver, .csproj: $old -> $ver" - - - name: Commit and push to main - run: | - git config user.name "actions[bot]" - git config user.email "actions[bot]@users.noreply.localhost" - git add CHANGELOG.md VERSION src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj - git commit -m "chore(release): promote changelog and bump version to ${{ github.event.inputs.version }}" - git push origin main - - - name: Create and push tag - if: ${{ github.event.inputs.create_tag == 'true' }} - run: | - ver='${{ github.event.inputs.version }}' - git tag "v$ver" - git push origin "v$ver" - shell: bash diff --git a/.forgejo/workflows/rust.yml b/.forgejo/workflows/rust.yml deleted file mode 100644 index d2f2a91..0000000 --- a/.forgejo/workflows/rust.yml +++ /dev/null @@ -1,124 +0,0 @@ -name: Rust - -# Dual CI (Forgejo + Gitea) — this file MUST stay byte-identical in -# .forgejo/workflows/rust.yml and .gitea/workflows/rust.yml. The `parity` -# job in build-and-release.yml fails the run when the copies drift. -# GitHub is a read-only archive mirror — no workflows there. -# -# Covers the Rust restart (crates/* + xtask): fmt, clippy, tests and -# release builds for Linux (native) and Windows (mingw cross-build). -# Steam integration tests talk to the real client when present and -# degrade to the unavailable backend otherwise — no secrets needed. - -on: - push: - branches: [main, dev] - pull_request: - branches: [main, dev] - workflow_dispatch: - -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true - -env: - CARGO_TERM_COLOR: always - -jobs: - fmt: - name: Format - runs-on: ubuntu-latest - timeout-minutes: 5 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - with: - components: rustfmt - - run: cargo fmt --all -- --check - - clippy: - name: Clippy - runs-on: ubuntu-latest - timeout-minutes: 15 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - with: - components: clippy - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo clippy --workspace --all-targets -- -D warnings - - test: - name: Test - runs-on: ubuntu-latest - timeout-minutes: 20 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo test --workspace - - audit: - name: Security audit - runs-on: ubuntu-latest - timeout-minutes: 10 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - - uses: Swatinem/rust-cache@v2 - - name: Install cargo-audit - run: cargo install cargo-audit --locked - # Vulnerabilities fail the run; unmaintained warnings only warn. - # See SECURITY.md (Verification / Secure Build). - - run: cargo audit - - build-linux: - name: Build + dist (Linux x86_64) - runs-on: ubuntu-latest - timeout-minutes: 30 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo run -p xtask -- dist - - uses: actions/upload-artifact@v7 - with: - name: gregmodmanager-linux-x64 - path: dist/*.tar.gz* - - build-windows: - name: Cross-build (Windows x86_64) - runs-on: ubuntu-latest - timeout-minutes: 30 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - with: - targets: x86_64-pc-windows-gnu - - name: Install mingw + Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - gcc-mingw-w64-x86-64 \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo build --release --target x86_64-pc-windows-gnu -p greg-app -p greg-cli diff --git a/.gitea/workflows/build-and-release.yml b/.gitea/workflows/build-and-release.yml deleted file mode 100644 index 2dac7c0..0000000 --- a/.gitea/workflows/build-and-release.yml +++ /dev/null @@ -1,418 +0,0 @@ -name: Build & Release - -# Dual CI: Forgejo Actions (.forgejo/workflows/) + Gitea Actions -# (.gitea/workflows/). Both directories MUST stay byte-identical — the -# `parity` job below fails the run when the copies drift. -# .github/workflows/ does not exist on purpose: GitHub is a read-only -# archive mirror, so no automation runs there. -# -# Rust restart: the C# / Avalonia sources are frozen under -# .reference/modmanager-old/ and no longer build on main — all build jobs -# below compile the Rust workspace (crates/* + xtask). Portable artifacts -# come straight out of `cargo xtask dist`. -# macOS has no runner on this instance (all jobs run ubuntu-latest) and -# cannot be cross-built from Linux without the Apple SDK — macOS assets -# are pending a macOS runner, they are NOT faked. -# -# No hardcoded instance URL is needed — links use github.server_url, and the -# container registry host is derived from it. Secrets to configure per -# instance (Forgejo AND Gitea): -# TELEMETRY_ENDPOINT / TELEMETRY_USER / TELEMETRY_API_KEY / TELEMETRY_TENANT, -# DISCORD_WEBHOOK_URL (single notification per run, see `notify` job). -# -# Windows installer is best-effort (Wine + ISCC); the portable ZIP always -# ships. The Inno script registers the `greg://` protocol and skips the -# VC++ redist for Rust builds (/DSkipVCRedist). - -on: - push: - branches: [main] - tags: ['v*'] - pull_request: - branches: [main] - workflow_dispatch: - inputs: - signing: - description: 'Signing mode (Linux hosts: self-signed via osslsigncode if installed, else unsigned)' - type: choice - options: - - none - - self-signed - default: 'none' - -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true - -permissions: - contents: read - -jobs: - version: - name: Resolve Version - runs-on: ubuntu-latest - timeout-minutes: 5 - outputs: - version: ${{ steps.resolve.outputs.version }} - numeric_version: ${{ steps.resolve.outputs.numeric_version }} - is_release: ${{ steps.resolve.outputs.is_release }} - is_pre: ${{ steps.resolve.outputs.is_pre }} - steps: - - uses: actions/checkout@v7 - - id: resolve - shell: bash - run: | - # VERSION file is the single source of truth, workspace Cargo.toml is the fallback. - ver="$(cat VERSION 2>/dev/null | tr -d '\r' | xargs)" - if [ -z "$ver" ]; then - ver=$(sed -n 's:^version = "\(.*\)":\1:p' Cargo.toml | head -n 1 | tr -d '\r' | xargs) - fi - [ -n "$ver" ] || ver='1.6.1' - numeric="${ver%%-*}" - if [[ "$numeric" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then - numeric="$numeric.0" - elif [[ ! "$numeric" =~ ^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+$ ]]; then - numeric='1.6.1.0' - fi - is_release=false - [[ "$GITHUB_REF_NAME" =~ ^v[0-9] ]] && is_release=true - is_pre=false - [[ "$ver" == *-* || "$GITHUB_REF_NAME" == *-* ]] && is_pre=true - { - echo "version=$ver" - echo "numeric_version=$numeric" - echo "is_release=$is_release" - echo "is_pre=$is_pre" - } >> "$GITHUB_OUTPUT" - echo "Version=$ver Numeric=$numeric IsRelease=$is_release IsPre=$is_pre" - - parity: - name: Workflow Parity (.forgejo == .gitea) - runs-on: ubuntu-latest - timeout-minutes: 5 - steps: - - uses: actions/checkout@v7 - - name: Fail when Forgejo/Gitea workflow copies drift - shell: bash - run: | - if ! diff -r .forgejo/workflows .gitea/workflows; then - echo "::error::.forgejo/workflows and .gitea/workflows differ — keep both copies byte-identical." - exit 1 - fi - echo "Workflow copies in sync." - - test: - name: Test - needs: [version, parity] - runs-on: ubuntu-latest - timeout-minutes: 15 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo test --workspace - - build-windows-cross: - name: Build Windows (cross-compiled on Linux) - needs: [version, test] - if: github.event_name != 'pull_request' || github.event.pull_request.draft == false - runs-on: ubuntu-latest - timeout-minutes: 30 - steps: - - uses: actions/checkout@v7 - with: - fetch-depth: 0 - - - uses: dtolnay/rust-toolchain@stable - with: - targets: x86_64-pc-windows-gnu - - - name: Install mingw + zip - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends gcc-mingw-w64-x86-64 zip - - - uses: Swatinem/rust-cache@v2 - - - name: Dist Windows x64 - run: cargo run -p xtask -- dist --target x86_64-pc-windows-gnu - - - name: Self-sign (osslsigncode, best-effort) - if: ${{ inputs.signing == 'self-signed' }} - run: | - STAGE="$(ls -d dist/gregmodmanager-*-win-x64 | head -n 1)" - if command -v osslsigncode >/dev/null 2>&1 && [ -n "${{ secrets.WINDOWS_SIGN_PFX_B64 }}" ]; then - echo "${{ secrets.WINDOWS_SIGN_PFX_B64 }}" | base64 -d > /tmp/sign.pfx - # Primary project URL (Forgejo main repo); GitHub archive mirror as fallback. - info_url="https://git.datacentermods.com/teamGreg/gregModmanager" - # Fallback: https://github.com/mleem97/gregModmanager - osslsigncode sign -pkcs12 /tmp/sign.pfx -pass "${{ secrets.WINDOWS_SIGN_PASSWORD }}" \ - -n "gregModmanager" -i "$info_url" \ - -in "$STAGE/gregmodmanager.exe" -out "$STAGE/gregmodmanager-signed.exe" - mv "$STAGE/gregmodmanager-signed.exe" "$STAGE/gregmodmanager.exe" - rm -f /tmp/sign.pfx - # Re-zip (the xtask archive predates signing) + refresh the hash sidecar. - (cd dist && rm -f ./*.zip ./*.sha256 && zip -r "$(basename "$STAGE").zip" "$(basename "$STAGE")" && sha256sum "$(basename "$STAGE").zip" > "$(basename "$STAGE").zip.sha256") - else - echo "::warning::self-signed requested but osslsigncode or WINDOWS_SIGN_PFX_B64 secret missing — shipping unsigned." - fi - - - name: Inno Setup EXE (Wine, best-effort) - run: | - STAGE="$(ls -d dist/gregmodmanager-*-win-x64 | head -n 1)" - if command -v wine >/dev/null 2>&1 && { command -v iscc >/dev/null 2>&1 || [ -f "$HOME/.wine/drive_c/Program Files (x86)/Inno Setup 6/ISCC.exe" ]; }; then - echo "Attempting Inno Setup build under Wine..." - ISCC_BIN="$(command -v iscc || echo "$HOME/.wine/drive_c/Program Files (x86)/Inno Setup 6/ISCC.exe")" - SRC_WIN="$(winepath -w "$PWD/$STAGE")" - wine "$ISCC_BIN" "build/installer/gregModmanager.iss" \ - "/DAppVersion=${{ needs.version.outputs.version }}" \ - "/DAppNumericVersion=${{ needs.version.outputs.numeric_version }}" \ - "/DSourceDir=${SRC_WIN}" \ - "/DMyAppExeName=gregmodmanager.exe" \ - "/DSkipVCRedist" || echo "::warning::Inno Setup build failed — shipping portable ZIP only." - else - echo "::notice::Wine/ISCC not available — skipping installer EXE, shipping portable ZIP only." - fi - shell: bash - - - name: Upload Windows artifacts - uses: actions/upload-artifact@v7 - with: - name: windows-portable - path: | - dist/gregmodmanager-*-win-x64.zip - dist/gregmodmanager-*-win-x64.zip.sha256 - build/installer/Output/*.exe - if-no-files-found: error - - build-linux: - name: Build Linux - needs: [version, test] - if: github.event_name != 'pull_request' || github.event.pull_request.draft == false - runs-on: ubuntu-latest - timeout-minutes: 30 - steps: - - uses: actions/checkout@v7 - - - uses: dtolnay/rust-toolchain@stable - - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - - uses: Swatinem/rust-cache@v2 - - - name: Dist Linux x64 - run: cargo run -p xtask -- dist - - - name: Upload tarball - uses: actions/upload-artifact@v7 - with: - name: linux-portable - path: | - dist/gregmodmanager-*-linux-x64.tar.gz - dist/gregmodmanager-*-linux-x64.tar.gz.sha256 - if-no-files-found: error - - build-linux-packages: - name: Build Linux Packages (DEB/RPM) - needs: [version, build-linux] - runs-on: ubuntu-latest - timeout-minutes: 15 - steps: - - uses: actions/checkout@v7 - - - name: Install nfpm - run: | - echo 'deb [trusted=yes] https://repo.goreleaser.com/apt/ /' | sudo tee /etc/apt/sources.list.d/goreleaser.list - sudo apt update - sudo apt install -y nfpm - nfpm --version - - - name: Download Linux portable - uses: actions/download-artifact@v8 - with: - name: linux-portable - path: ./artifacts/dl - - - name: Build packages - run: | - mkdir -p ./artifacts/stage ./artifacts/packages - tar -xzf ./artifacts/dl/gregmodmanager-*-linux-x64.tar.gz -C ./artifacts/stage - chmod +x ./build/scripts/linux/build-rust-packages.sh - ./build/scripts/linux/build-rust-packages.sh ./artifacts/stage ${{ needs.version.outputs.version }} ${{ needs.version.outputs.is_pre }} ./artifacts/packages - - - name: Upload packages - uses: actions/upload-artifact@v7 - with: - name: linux-packages - path: artifacts/packages/gregmodmanager-* - if-no-files-found: error - - - name: Build & Push Container (instance registry) - if: github.event_name != 'pull_request' - run: | - # Derive registry host from the instance URL (no hardcoded host). - REGISTRY_HOST="$(echo "${{ github.server_url }}" | sed -e 's|^https\?://||' -e 's|/.*$||')" - IMAGE="oci://${REGISTRY_HOST}/${{ github.repository_owner }}/gregmodmanager" - echo "${{ secrets.GITHUB_TOKEN }}" | docker login "$REGISTRY_HOST" -u ${{ github.actor }} --password-stdin - docker build -t "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:${{ needs.version.outputs.version }}" -t "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:latest" -f - . <<'EOF' - FROM debian:bookworm-slim - RUN apt-get update && apt-get install -y --no-install-recommends fontconfig libfreetype6 && rm -rf /var/lib/apt/lists/* - WORKDIR /opt/gregmodmanager - COPY artifacts/stage/ ./ - RUN chmod +x /opt/gregmodmanager/gregmodmanager - ENTRYPOINT ["/opt/gregmodmanager/gregmodmanager"] - EOF - docker push "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:${{ needs.version.outputs.version }}" - docker push "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:latest" - - release: - name: Release - needs: [version, build-windows-cross, build-linux, build-linux-packages] - runs-on: ubuntu-latest - if: needs.version.outputs.is_release == 'true' && github.event_name != 'pull_request' - timeout-minutes: 10 - permissions: - contents: write - steps: - - name: Download Windows Portable - uses: actions/download-artifact@v8 - with: - name: windows-portable - path: ./dist - - - name: Download Linux Portable - uses: actions/download-artifact@v8 - with: - name: linux-portable - path: ./dist - - - name: Download Linux Packages - uses: actions/download-artifact@v8 - with: - name: linux-packages - path: ./dist - - - name: Create Forgejo release & upload assets - env: - FORGEJO_TOKEN: ${{ secrets.GITHUB_TOKEN }} - TAG_NAME: ${{ github.ref_name }} - IS_PRE: ${{ needs.version.outputs.is_pre }} - run: | - python3 - "$FORGEJO_TOKEN" "${{ github.server_url }}" "${{ github.repository }}" "$TAG_NAME" "$IS_PRE" <<'EOF' - import json, mimetypes, os, sys, urllib.request - - token, server, repo, tag, is_pre = sys.argv[1:6] - api = server.rstrip('/') + '/api/v1' - headers = {'Authorization': f'token {token}', 'Content-Type': 'application/json'} - - def call(method, path, payload=None, raw=None, ctype=None): - data = raw if raw is not None else (json.dumps(payload).encode() if payload is not None else None) - h = dict(headers) - if ctype: - h['Content-Type'] = ctype - req = urllib.request.Request(api + path, data=data, headers=h, method=method) - with urllib.request.urlopen(req) as res: - body = res.read() - return json.loads(body) if body and res.headers.get_content_type() == 'application/json' else body - - release = call('POST', f'/repos/{repo}/releases', { - 'tag_name': tag, - 'name': tag, - 'prerelease': is_pre.lower() == 'true', - 'draft': False, - 'body': f'Release {tag} — built by Forgejo/Gitea Actions.', - }) - rid = release['id'] - print(f"Release id={rid}") - - dist = 'dist' - for root, _, files in os.walk(dist): - for name in sorted(files): - path = os.path.join(root, name) - ctype = mimetypes.guess_type(name)[0] or 'application/octet-stream' - with open(path, 'rb') as fh: - data = fh.read() - req = urllib.request.Request( - f'{api}/repos/{repo}/releases/{rid}/assets?name={name}', - data=data, - headers={'Authorization': f'token {token}', 'Content-Type': ctype}, - method='POST') - with urllib.request.urlopen(req): - print(f'Uploaded {name} ({len(data)} bytes)') - EOF - - notify: - # Exactly ONE Discord message per completed run (push/dispatch only — PR - # runs stay silent so the channel is not spammed). - name: Notify Discord (once) - needs: [version, test, build-windows-cross, build-linux, build-linux-packages, release] - if: always() && github.event_name != 'pull_request' - runs-on: ubuntu-latest - timeout-minutes: 5 - steps: - - name: Send single Discord notification - shell: bash - env: - DISCORD_WEBHOOK_URL: ${{ secrets.DISCORD_WEBHOOK_URL }} - VERSION: ${{ needs.version.outputs.version }} - RUN_URL: ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }} - EVENT: ${{ github.event_name }} - REF: ${{ github.ref_name }} - RESULTS: ${{ toJSON(needs) }} - run: | - if [ -z "$DISCORD_WEBHOOK_URL" ]; then - echo "DISCORD_WEBHOOK_URL is empty, skipping notification." - exit 0 - fi - - if echo "$RESULTS" | grep -q '"result":"failure"'; then - status="❌ Failed"; color=15158332 - elif echo "$RESULTS" | grep -q '"result":"cancelled"'; then - status="⚠️ Cancelled"; color=16776960 - else - status="✅ Success"; color=3066993 - fi - - payload=$(cat <> "$GITHUB_OUTPUT" - - build-packages: - needs: [version] - runs-on: ubuntu-latest - timeout-minutes: 30 - permissions: - contents: read - packages: write - steps: - - uses: actions/checkout@v7 - - - uses: dtolnay/rust-toolchain@stable - - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - - uses: Swatinem/rust-cache@v2 - - - name: Install nfpm - run: | - curl -fsSL -o nfpm.tar.gz "https://github.com/goreleaser/nfpm/releases/latest/download/nfpm_Linux_x86_64.tar.gz" - tar -xzf nfpm.tar.gz nfpm - sudo mv nfpm /usr/local/bin/ - nfpm --version - - - name: Build packages - run: | - cargo run -p xtask -- dist - STAGE="$(ls -d dist/gregmodmanager-*-linux-x64 | head -n 1)" - chmod +x ./build/scripts/linux/build-rust-packages.sh - ./build/scripts/linux/build-rust-packages.sh "$STAGE" ${{ needs.version.outputs.version }} ${{ needs.version.outputs.is_pre }} ./artifacts/rust-linux/packages - - - name: Upload artifacts - uses: actions/upload-artifact@v7 - with: - name: linux-packages-detailed - path: artifacts/rust-linux/packages/gregmodmanager-* - if-no-files-found: error - - - name: Build container (instance registry) - if: github.event_name != 'pull_request' - run: | - REGISTRY_HOST="$(echo "${{ github.server_url }}" | sed -e 's|^https\?://||' -e 's|/.*$||')" - echo "${{ secrets.GITHUB_TOKEN }}" | docker login "$REGISTRY_HOST" -u ${{ github.actor }} --password-stdin - STAGE="$(ls -d dist/gregmodmanager-*-linux-x64 | head -n 1)" - mkdir -p publish && cp -r "$STAGE/"* publish/ - docker build -t "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:${{ needs.version.outputs.version }}" -t "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:latest" -f - . <<'EOF' - FROM debian:bookworm-slim - RUN apt-get update && apt-get install -y --no-install-recommends fontconfig libfreetype6 && rm -rf /var/lib/apt/lists/* - WORKDIR /opt/gregmodmanager - COPY publish/ ./ - RUN chmod +x /opt/gregmodmanager/gregmodmanager - ENTRYPOINT ["/opt/gregmodmanager/gregmodmanager"] - EOF - docker push "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:${{ needs.version.outputs.version }}" - docker push "$REGISTRY_HOST/${{ github.repository_owner }}/gregmodmanager:latest" diff --git a/.gitea/workflows/promote-changelog.yml b/.gitea/workflows/promote-changelog.yml deleted file mode 100644 index c034fe3..0000000 --- a/.gitea/workflows/promote-changelog.yml +++ /dev/null @@ -1,93 +0,0 @@ -name: Promote Changelog - -# Dual CI (Forgejo + Gitea) — see build-and-release.yml header for instance notes. -# `origin` is the main instance here (GitHub is a read-only archive mirror). - -on: - workflow_dispatch: - inputs: - version: - description: 'Target version to release (e.g. 1.6.0)' - required: true - create_tag: - description: 'Create and push git tag v{version}' - type: boolean - default: true - -permissions: - contents: write - -jobs: - promote: - name: Promote Changelog & Bump Version - runs-on: ubuntu-latest - timeout-minutes: 10 - steps: - - name: Checkout main - uses: actions/checkout@v7 - with: - ref: main - fetch-depth: 0 - token: ${{ secrets.GITHUB_TOKEN }} - - - name: Validate version format - shell: bash - run: | - ver='${{ github.event.inputs.version }}' - if [[ ! "$ver" =~ ^[0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9.-]+)?$ ]]; then - echo "Invalid version format: $ver. Expected: x.y.z or x.y.z-prerelease" - exit 1 - fi - echo "Version format OK: $ver" - - - name: Promote CHANGELOG.md - shell: bash - run: | - ver='${{ github.event.inputs.version }}' - date="$(date +%F)" - changelog='CHANGELOG.md' - - if ! grep -q '## \[Unreleased\]' "$changelog"; then - echo "CHANGELOG.md does not contain an [Unreleased] section. Nothing to promote." - exit 1 - fi - - new_unreleased=$(printf '## [Unreleased]\n\n### Added\n\n### Changed\n\n### Deprecated\n\n### Removed\n\n### Fixed\n\n### Security\n\n') - python3 - "$changelog" "$ver" "$date" "$new_unreleased" <<'EOF' - import sys - path, ver, date, new_unreleased = sys.argv[1:5] - with open(path, encoding='utf-8') as fh: - content = fh.read() - versioned = f'## [{ver}] - {date}' - content = content.replace('## [Unreleased]', versioned, 1) - content = content.replace(versioned + '\n', versioned + '\n\n' + new_unreleased, 1) - with open(path, 'w', encoding='utf-8', newline='') as fh: - fh.write(content) - print(f'Promoted [Unreleased] to [{ver}] - {date}') - EOF - - - name: Bump version (VERSION file + .csproj fallback copy) - shell: bash - run: | - ver='${{ github.event.inputs.version }}' - printf '%s\n' "$ver" > VERSION - csproj='src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj' - old="$(sed -n 's:.*\([^<]*\).*:\1:p' "$csproj" | head -n 1)" - sed -i "s|[^<]*|${ver}|" "$csproj" - echo "Version: VERSION=$ver, .csproj: $old -> $ver" - - - name: Commit and push to main - run: | - git config user.name "actions[bot]" - git config user.email "actions[bot]@users.noreply.localhost" - git add CHANGELOG.md VERSION src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj - git commit -m "chore(release): promote changelog and bump version to ${{ github.event.inputs.version }}" - git push origin main - - - name: Create and push tag - if: ${{ github.event.inputs.create_tag == 'true' }} - run: | - ver='${{ github.event.inputs.version }}' - git tag "v$ver" - git push origin "v$ver" - shell: bash diff --git a/.gitea/workflows/rust.yml b/.gitea/workflows/rust.yml deleted file mode 100644 index d2f2a91..0000000 --- a/.gitea/workflows/rust.yml +++ /dev/null @@ -1,124 +0,0 @@ -name: Rust - -# Dual CI (Forgejo + Gitea) — this file MUST stay byte-identical in -# .forgejo/workflows/rust.yml and .gitea/workflows/rust.yml. The `parity` -# job in build-and-release.yml fails the run when the copies drift. -# GitHub is a read-only archive mirror — no workflows there. -# -# Covers the Rust restart (crates/* + xtask): fmt, clippy, tests and -# release builds for Linux (native) and Windows (mingw cross-build). -# Steam integration tests talk to the real client when present and -# degrade to the unavailable backend otherwise — no secrets needed. - -on: - push: - branches: [main, dev] - pull_request: - branches: [main, dev] - workflow_dispatch: - -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true - -env: - CARGO_TERM_COLOR: always - -jobs: - fmt: - name: Format - runs-on: ubuntu-latest - timeout-minutes: 5 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - with: - components: rustfmt - - run: cargo fmt --all -- --check - - clippy: - name: Clippy - runs-on: ubuntu-latest - timeout-minutes: 15 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - with: - components: clippy - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo clippy --workspace --all-targets -- -D warnings - - test: - name: Test - runs-on: ubuntu-latest - timeout-minutes: 20 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo test --workspace - - audit: - name: Security audit - runs-on: ubuntu-latest - timeout-minutes: 10 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - - uses: Swatinem/rust-cache@v2 - - name: Install cargo-audit - run: cargo install cargo-audit --locked - # Vulnerabilities fail the run; unmaintained warnings only warn. - # See SECURITY.md (Verification / Secure Build). - - run: cargo audit - - build-linux: - name: Build + dist (Linux x86_64) - runs-on: ubuntu-latest - timeout-minutes: 30 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - - name: Install Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo run -p xtask -- dist - - uses: actions/upload-artifact@v7 - with: - name: gregmodmanager-linux-x64 - path: dist/*.tar.gz* - - build-windows: - name: Cross-build (Windows x86_64) - runs-on: ubuntu-latest - timeout-minutes: 30 - steps: - - uses: actions/checkout@v7 - - uses: dtolnay/rust-toolchain@stable - with: - targets: x86_64-pc-windows-gnu - - name: Install mingw + Slint system dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - gcc-mingw-w64-x86-64 \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo build --release --target x86_64-pc-windows-gnu -p greg-app -p greg-cli diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md deleted file mode 100644 index 6f38ed2..0000000 --- a/.github/ISSUE_TEMPLATE/bug_report.md +++ /dev/null @@ -1,28 +0,0 @@ ---- -name: Bug report -about: Create a report to help us improve -title: '' -labels: bug -assignees: '' ---- - -**Describe the bug** -A clear and concise description of what the bug is. - -**To Reproduce** -Steps to reproduce the behavior. - -**Expected behavior** -A clear and concise description of what you expected to happen. - -**Screenshots** -If applicable, add screenshots to help explain your problem. - -**Desktop:** - -- OS: [e.g. Windows 11] -- Game Version: [e.g. 1.0.45] -- gregCore Version: [e.g. 1.0.0.30-pre] - -**Additional context** -Add any other context about the problem here. diff --git a/.github/scripts/greg-gates.sh b/.github/scripts/greg-gates.sh index 9702a24..210dc49 100644 --- a/.github/scripts/greg-gates.sh +++ b/.github/scripts/greg-gates.sh @@ -24,8 +24,6 @@ if [ "$BASELINE_FETCH_OK" != true ] || ! git rev-parse --verify "origin/$STAGE^{ fi -CHANGED="$(git diff --name-only "origin/$STAGE...HEAD" 2>/dev/null | sort -u || true)" - # ---------- build ---------- BUILD_RC=1; WARN_DEV=0; SOL="" build_dotnet() { @@ -55,7 +53,7 @@ case "$KIND" in rust) if [ -f Cargo.toml ]; then cargo build --release >build-dev.log 2>&1; BUILD_RC=$? - [ "$BUILD_RC" -eq 0 ] && gpass build "cargo build --release ok" || gfail build "cargo build failed (see build-dev.log)" + if [ "$BUILD_RC" -eq 0 ]; then gpass build "cargo build --release ok"; else gfail build "cargo build failed (see build-dev.log)"; fi else gfail build "no Cargo.toml"; fi ;; node) @@ -64,7 +62,7 @@ case "$KIND" in $PM install --frozen-lockfile >build-dev.log 2>&1 || $PM install >>build-dev.log 2>&1 if node -e "const p=require('./package.json');process.exit(p.scripts&&p.scripts.build?0:1)"; then $PM run build >>build-dev.log 2>&1; BUILD_RC=$? - [ "$BUILD_RC" -eq 0 ] && gpass build "$PM run build ok" || gfail build "$PM run build failed" + if [ "$BUILD_RC" -eq 0 ]; then gpass build "$PM run build ok"; else gfail build "$PM run build failed"; fi else gna build "no build script (lint/typecheck only)"; BUILD_RC=0; fi else gna build "no package.json"; BUILD_RC=0; fi ;; @@ -75,19 +73,23 @@ esac TESTS_RC=1; HAVE_TESTS=false case "$KIND" in dotnet*) - TP="$(find . -path ./obj -prune -o -path ./.git -prune -o -name '*Tests*.csproj' -print 2>/dev/null | grep -v -E '/(obj|bin)/' | head -n 20)" - if [ -z "$TP" ]; then gfail tests "no *Tests*.csproj found (add tests to unblock staging)"; + mapfile -t TP < <(find . -path ./obj -prune -o -path ./.git -prune -o -name '*Tests*.csproj' -print 2>/dev/null | grep -v -E '/(obj|bin)/' | head -n 20) + if [ "${#TP[@]}" -eq 0 ]; then gfail tests "no *Tests*.csproj found (add tests to unblock staging)"; else HAVE_TESTS=true # coverage-collecting run; results reused by coverage gate - dotnet test $TP -c Release --no-build --collect:"XPlat Code Coverage" --results-directory "$PWD/cov-dev" >test-dev.log 2>&1; TESTS_RC=$? - [ "$TESTS_RC" -eq 0 ] && gpass tests "dotnet test ok" || gfail tests "dotnet test failed (see test-dev.log)" + TESTS_RC=0 + : >test-dev.log + for project in "${TP[@]}"; do + dotnet test "$project" -c Release --no-build --collect:"XPlat Code Coverage" --results-directory "$PWD/cov-dev" >>test-dev.log 2>&1 || TESTS_RC=1 + done + if [ "$TESTS_RC" -eq 0 ]; then gpass tests "dotnet test ok"; else gfail tests "dotnet test failed (see test-dev.log)"; fi fi ;; rust) if [ -f Cargo.toml ]; then HAVE_TESTS=true cargo test >test-dev.log 2>&1; TESTS_RC=$? - [ "$TESTS_RC" -eq 0 ] && gpass tests "cargo test ok" || gfail tests "cargo test failed" + if [ "$TESTS_RC" -eq 0 ]; then gpass tests "cargo test ok"; else gfail tests "cargo test failed"; fi else gfail tests "no Cargo.toml"; fi ;; node) @@ -95,7 +97,7 @@ case "$KIND" in HAVE_TESTS=true if [ -f pnpm-lock.yaml ]; then pnpm test >test-dev.log 2>&1; TESTS_RC=$? else npm test >test-dev.log 2>&1; TESTS_RC=$?; fi - [ "$TESTS_RC" -eq 0 ] && gpass tests "npm/pnpm test ok" || gfail tests "tests failed" + if [ "$TESTS_RC" -eq 0 ]; then gpass tests "npm/pnpm test ok"; else gfail tests "tests failed"; fi else gna tests "no test script (annotated)"; TESTS_RC=0; fi ;; *) gna tests "generic repo (annotated)"; TESTS_RC=0 ;; @@ -114,7 +116,7 @@ if [ "$HAVE_TESTS" = true ] && [ "$TESTS_RC" -eq 0 ]; then if [ -z "$DEV_COV" ]; then gfail coverage "no cobertura output (add coverlet.collector to test projects)"; else rm -rf /tmp/gbase && git worktree add --detach /tmp/gbase "origin/$STAGE" >/dev/null 2>&1 - (cd /tmp/gbase && dotnet test $TP -c Release --collect:"XPlat Code Coverage" --results-directory /tmp/gbase/cov-base >/tmp/base-test.log 2>&1 || true) + (cd /tmp/gbase && for project in "${TP[@]}"; do dotnet test "$project" -c Release --collect:"XPlat Code Coverage" --results-directory /tmp/gbase/cov-base; done >/tmp/base-test.log 2>&1 || true) BASE_COV="$(cov_dotnet /tmp/gbase/cov-base)"; [ -z "$BASE_COV" ] && BASE_COV=0 git worktree remove --force /tmp/gbase >/dev/null 2>&1 || true DROP="$(python3 -c "print(round($BASE_COV - $DEV_COV, 2))")" @@ -159,7 +161,7 @@ case "$KIND" in dotnet*) if [ -n "$SOL" ]; then VULN=$(dotnet list "$SOL" package --vulnerable --include-transitive 2>/dev/null | grep -ciE "high|critical" || true) - [ "$VULN" -eq 0 ] && gpass security-deps "0 high/critical vulnerable packages" || gfail security-deps "$VULN high/critical findings" + if [ "$VULN" -eq 0 ]; then gpass security-deps "0 high/critical vulnerable packages"; else gfail security-deps "$VULN high/critical findings"; fi # warnings delta vs STAGE (staging log from coverage worktree run if present) WARN_BASE=0 if [ -f /tmp/base-test.log ]; then WARN_BASE=$(grep -c "warning CS" /tmp/base-test.log || true); fi @@ -168,12 +170,15 @@ case "$KIND" in else gna security-deps "no solution"; fi ;; rust) - if [ -f Cargo.lock ]; then cargo audit >cargo-audit.log 2>&1 && gpass security-deps "cargo audit clean" || gfail security-deps "cargo audit findings"; + if [ -f Cargo.lock ]; then + if cargo audit >cargo-audit.log 2>&1; then gpass security-deps "cargo audit clean"; else gfail security-deps "cargo audit findings"; fi else gfail security-deps "no Cargo.lock (cannot audit dependencies)"; fi ;; node) - if [ -f package-lock.json ]; then npm audit --audit-level=high >npm-audit.log 2>&1 && gpass security-deps "npm audit clean" || gfail security-deps "npm audit high+ findings"; - elif [ -f pnpm-lock.yaml ]; then pnpm audit --audit-level high >npm-audit.log 2>&1 && gpass security-deps "pnpm audit clean" || gfail security-deps "pnpm audit high+ findings"; + if [ -f package-lock.json ]; then + if npm audit --audit-level=high >npm-audit.log 2>&1; then gpass security-deps "npm audit clean"; else gfail security-deps "npm audit high+ findings"; fi + elif [ -f pnpm-lock.yaml ]; then + if pnpm audit --audit-level high >npm-audit.log 2>&1; then gpass security-deps "pnpm audit clean"; else gfail security-deps "pnpm audit high+ findings"; fi else gna security-deps "no lockfile"; fi ;; *) gna security-deps "generic repo" ;; diff --git a/.github/workflows/build-and-release.yml b/.github/workflows/build-and-release.yml deleted file mode 100644 index c5012b7..0000000 --- a/.github/workflows/build-and-release.yml +++ /dev/null @@ -1,247 +0,0 @@ -name: Build and Release - -on: - push: - branches: [main] - tags: ['v*'] - pull_request: - branches: [main] - workflow_dispatch: - -permissions: - contents: read - -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true - -env: - CARGO_TERM_COLOR: always - -jobs: - version: - name: Resolve Version - runs-on: ubuntu-latest - outputs: - version: ${{ steps.resolve.outputs.version }} - numeric_version: ${{ steps.resolve.outputs.numeric_version }} - is_release: ${{ steps.resolve.outputs.is_release }} - is_pre: ${{ steps.resolve.outputs.is_pre }} - steps: - - uses: actions/checkout@v4 - - id: resolve - shell: bash - run: | - version="$(tr -d '\r\n ' < VERSION 2>/dev/null || true)" - if [ -z "$version" ]; then - version="$(sed -n 's/^version = "\(.*\)"$/\1/p' Cargo.toml | head -n 1)" - fi - test -n "$version" - - numeric="${version%%-*}" - if [[ "$numeric" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then - numeric="$numeric.0" - fi - - is_release=false - [[ "$GITHUB_REF_NAME" =~ ^v[0-9] ]] && is_release=true - is_pre=false - [[ "$version" == *-* || "$GITHUB_REF_NAME" == *-* ]] && is_pre=true - - { - echo "version=$version" - echo "numeric_version=$numeric" - echo "is_release=$is_release" - echo "is_pre=$is_pre" - } >> "$GITHUB_OUTPUT" - - test: - name: Test Workspace - needs: version - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v4 - - uses: dtolnay/rust-toolchain@stable - - name: Install Linux UI dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - run: cargo test --workspace - - build-windows: - name: Windows Installer and Portable Build - needs: [version, test] - runs-on: windows-latest - steps: - - uses: actions/checkout@v4 - with: - fetch-depth: 0 - - uses: dtolnay/rust-toolchain@stable - - uses: Swatinem/rust-cache@v2 - - name: Build Windows portable package - run: cargo run -p xtask -- dist - # Inno resolves SourceDir relative to build/installer/gregModmanager.iss. - - name: Build Windows installer - uses: Minionguyjpro/Inno-Setup-Action@v1.2.2 - with: - path: build/installer/gregModmanager.iss - options: >- - /DMyAppVersion=${{ needs.version.outputs.version }} - /DMyAppNumericVersion=${{ needs.version.outputs.numeric_version }} - /DSourceDir=../../dist/gregmodmanager-${{ needs.version.outputs.version }}-win-x64 - /DMyAppExeName=gregmodmanager.exe - /DSkipVCRedist - - name: Upload Windows artifacts - uses: actions/upload-artifact@v4 - with: - name: windows - path: | - dist/gregmodmanager-*-win-x64.zip - dist/gregmodmanager-*-win-x64.zip.sha256 - build/installer/Output/*.exe - if-no-files-found: error - - build-linux: - name: Linux Portable Build - needs: [version, test] - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v4 - - uses: dtolnay/rust-toolchain@stable - - name: Install Linux UI dependencies - run: | - sudo apt-get update - sudo apt-get install -y --no-install-recommends \ - libxcb-render0-dev libxcb-shape0-dev libxcb-xfixes0-dev \ - libxkbcommon-dev libfontconfig1-dev - - uses: Swatinem/rust-cache@v2 - - name: Build Linux portable package - run: cargo run -p xtask -- dist - - name: Upload Linux portable artifacts - uses: actions/upload-artifact@v4 - with: - name: linux-portable - path: | - dist/gregmodmanager-*-linux-x64.tar.gz - dist/gregmodmanager-*-linux-x64.tar.gz.sha256 - if-no-files-found: error - - build-linux-packages: - name: Linux Distribution Packages - needs: [version, build-linux] - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v4 - - name: Install nfpm - run: | - echo 'deb [trusted=yes] https://repo.goreleaser.com/apt/ /' | - sudo tee /etc/apt/sources.list.d/goreleaser.list - sudo apt-get update - sudo apt-get install -y --no-install-recommends nfpm - - uses: actions/download-artifact@v4 - with: - name: linux-portable - path: artifacts/download - - name: Build Linux packages - shell: bash - run: | - set -euo pipefail - mkdir -p artifacts/stage artifacts/packages - tar -xzf artifacts/download/gregmodmanager-*-linux-x64.tar.gz \ - --strip-components=1 \ - -C artifacts/stage - chmod +x build/scripts/linux/build-rust-packages.sh - ./build/scripts/linux/build-rust-packages.sh \ - artifacts/stage \ - '${{ needs.version.outputs.version }}' \ - '${{ needs.version.outputs.is_pre }}' \ - artifacts/packages - - name: Upload Linux packages - uses: actions/upload-artifact@v4 - with: - name: linux-packages - path: artifacts/packages/* - if-no-files-found: error - - build-macos: - name: macOS ${{ matrix.name }} Build - needs: [version, test] - strategy: - fail-fast: false - matrix: - include: - - name: x64 - runner: macos-15-intel - target: x86_64-apple-darwin - - name: arm64 - runner: macos-15 - target: aarch64-apple-darwin - runs-on: ${{ matrix.runner }} - steps: - - uses: actions/checkout@v4 - - uses: dtolnay/rust-toolchain@stable - with: - targets: ${{ matrix.target }} - - name: Install macOS build dependencies - run: brew install pkg-config - - uses: Swatinem/rust-cache@v2 - - name: Build macOS portable package - run: cargo run -p xtask -- dist --target ${{ matrix.target }} - - name: Upload macOS artifacts - uses: actions/upload-artifact@v4 - with: - name: macos-${{ matrix.name }} - path: | - dist/gregmodmanager-*-macos-*.tar.gz - dist/gregmodmanager-*-macos-*.tar.gz.sha256 - if-no-files-found: error - - release: - name: GitHub Release - needs: [version, build-windows, build-linux-packages, build-macos] - if: needs.version.outputs.is_release == 'true' && github.event_name != 'pull_request' - runs-on: ubuntu-latest - permissions: - contents: write - steps: - - name: Download Windows artifacts - uses: actions/download-artifact@v4 - with: - name: windows - path: dist - - name: Download Linux portable artifacts - uses: actions/download-artifact@v4 - with: - name: linux-portable - path: dist - - name: Download Linux packages - uses: actions/download-artifact@v4 - with: - name: linux-packages - path: dist - - name: Download macOS x64 artifacts - uses: actions/download-artifact@v4 - with: - name: macos-x64 - path: dist - - name: Download macOS arm64 artifacts - uses: actions/download-artifact@v4 - with: - name: macos-arm64 - path: dist - - name: Publish GitHub release - env: - GH_TOKEN: ${{ github.token }} - TAG_NAME: ${{ github.ref_name }} - IS_PRE: ${{ needs.version.outputs.is_pre }} - shell: bash - run: | - set -euo pipefail - args=("$TAG_NAME" dist/* --title "$TAG_NAME" --generate-notes) - if [ "$IS_PRE" = true ]; then - args+=(--prerelease) - fi - gh release create "${args[@]}" diff --git a/.github/workflows/greg-train.yml b/.github/workflows/greg-train.yml deleted file mode 100644 index 14914eb..0000000 --- a/.github/workflows/greg-train.yml +++ /dev/null @@ -1,78 +0,0 @@ -name: greg train staging -> main - -# Second stage of the branch model: advance main from staging when ready. -# Readiness = fast-forward possible + owner actor + conventional commits. -# Quality was already gated at dev -> staging (same sha, no rebuild here). - -on: - push: - branches: [staging] - workflow_dispatch: - inputs: - dry_run: - description: 'Check readiness only (no push)' - type: boolean - default: true - -permissions: - contents: write - issues: write - -concurrency: - group: train-staging-main-gregModmanager - cancel-in-progress: false - -jobs: - readiness: - runs-on: ["self-hosted", "Linux", "X64", "shitcloud", "gregmodmanager"] - outputs: - verdict: ${{ steps.eval.outputs.verdict }} - sha: ${{ steps.eval.outputs.sha }} - steps: - - uses: actions/checkout@v4 - with: - fetch-depth: 0 - fetch-tags: true - - name: Evaluate readiness - id: eval - run: | - set -u - git fetch origin main >/dev/null 2>&1 || true - SHA="$(git rev-parse origin/staging)" - OK=true - git merge-base --is-ancestor "origin/main" "origin/staging" && echo "READY ff: main is ancestor of staging" || { echo "READY ff: FAIL (main not ancestor)"; OK=false; } - if git log --no-merges --format=%s "origin/main..origin/staging" 2>/dev/null | grep -vE "^(feat|fix|docs|style|refactor|perf|test|build|ci|chore|revert)(\(.+\))?!?: .+" | grep -q .; then - echo "READY conventional: FAIL"; OK=false - else echo "READY conventional: PASS"; fi - [ "$OK" = true ] && echo "verdict=pass" >> "$GITHUB_OUTPUT" || echo "verdict=fail" >> "$GITHUB_OUTPUT" - echo "sha=$SHA" >> "$GITHUB_OUTPUT" - - advance: - needs: readiness - if: needs.readiness.outputs.verdict == 'pass' && github.actor == 'mleem97' && (github.event_name == 'push' || inputs.dry_run == false) - runs-on: ["self-hosted", "Linux", "X64", "shitcloud", "gregmodmanager"] - steps: - - uses: actions/checkout@v4 - with: - fetch-depth: 0 - - name: Fast-forward main to gated sha - run: | - git push origin "${{ needs.readiness.outputs.sha }}:refs/heads/main" - - sync-issue: - needs: readiness - if: always() && github.event_name == 'push' - runs-on: ["self-hosted", "Linux", "X64", "shitcloud", "gregmodmanager"] - steps: - - name: Sync release-train tracking issue - env: - GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} - VERDICT: ${{ needs.readiness.outputs.verdict }} - run: | - TITLE="[release-train] staging -> main blocked" - OPEN="$(gh issue list --label release-train --state open --json number --jq '.[0].number // empty')" - if [ "$VERDICT" = "pass" ]; then - [ -n "$OPEN" ] && gh issue close "$OPEN" --comment "Train green again." || true - else - [ -z "$OPEN" ] && gh issue create --title "$TITLE" --label release-train --body "Readiness failed for run ${{ github.run_id }}." || true - fi diff --git a/.github/workflows/test-packages.yml b/.github/workflows/test-packages.yml new file mode 100644 index 0000000..0eeedc4 --- /dev/null +++ b/.github/workflows/test-packages.yml @@ -0,0 +1,118 @@ +name: Build test packages + +on: + pull_request: + workflow_dispatch: + +permissions: + contents: read + +jobs: + quality: + name: Linux quality checks + runs-on: ubuntu-24.04 + steps: + - uses: actions/checkout@v4 + - uses: dtolnay/rust-toolchain@stable + with: + components: rustfmt, clippy + - name: Install Linux UI dependencies + run: | + sudo apt-get update + sudo apt-get install -y --no-install-recommends \ + build-essential pkg-config libxcb-render0-dev libxcb-shape0-dev \ + libxcb-xfixes0-dev libxkbcommon-dev libfontconfig1-dev + - uses: Swatinem/rust-cache@v2 + - run: cargo fmt --all -- --check + - run: cargo clippy --workspace --all-targets -- -D warnings + - run: cargo test --workspace + + linux: + name: Linux test packages + needs: quality + runs-on: ubuntu-24.04 + steps: + - uses: actions/checkout@v4 + - uses: dtolnay/rust-toolchain@stable + - uses: actions/setup-go@v5 + with: + go-version: '1.25' + - name: Install build dependencies + run: | + sudo apt-get update + sudo apt-get install -y --no-install-recommends \ + build-essential pkg-config libxcb-render0-dev libxcb-shape0-dev \ + libxcb-xfixes0-dev libxkbcommon-dev libfontconfig1-dev + go install github.com/goreleaser/nfpm/v2/cmd/nfpm@v2.46.3 + echo "$(go env GOPATH)/bin" >> "$GITHUB_PATH" + - uses: Swatinem/rust-cache@v2 + - name: Build portable archive and packages + shell: bash + run: | + set -euo pipefail + version=$(tr -d '\r\n' < VERSION) + cargo xtask dist + build/scripts/linux/build-rust-packages.sh "dist/gregmodmanager-${version}-linux-x64" "$version" false dist/packages + (cd dist && sha256sum -c ./*.sha256) + (cd dist/packages && sha256sum -c ./*.sha256) + - name: Upload Linux packages + uses: actions/upload-artifact@v4 + with: + name: linux-test-packages + if-no-files-found: error + path: | + dist/*.tar.gz + dist/*.tar.gz.sha256 + dist/packages/*.deb + dist/packages/*.deb.sha256 + dist/packages/*.rpm + dist/packages/*.rpm.sha256 + dist/packages/*.pkg.tar.zst + dist/packages/*.pkg.tar.zst.sha256 + - name: Upload experimental Alpine package + uses: actions/upload-artifact@v4 + with: + name: alpine-apk-known-not-working + if-no-files-found: error + path: | + dist/packages/*.apk + dist/packages/*.apk.sha256 + + windows: + name: Windows test packages + needs: quality + runs-on: windows-latest + steps: + - uses: actions/checkout@v4 + - uses: dtolnay/rust-toolchain@stable + - uses: Swatinem/rust-cache@v2 + - name: Install installer tools + shell: pwsh + run: | + $ErrorActionPreference = 'Stop' + $iscc = Join-Path ${env:ProgramFiles(x86)} 'Inno Setup 6\ISCC.exe' + if (-not (Test-Path $iscc) -and -not (Get-Command ISCC.exe -ErrorAction SilentlyContinue)) { + choco install innosetup --yes --no-progress + if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } + } + dotnet tool install --global wix --version 5.0.2 + if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } + "$env:USERPROFILE\.dotnet\tools" | Out-File -FilePath $env:GITHUB_PATH -Encoding utf8 -Append + - name: Build portable archive and installers + shell: pwsh + run: | + $ErrorActionPreference = 'Stop' + $version = (Get-Content VERSION -Raw).Trim() + cargo xtask dist + if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } + & build/installer/build-windows.ps1 -StageDir "dist/gregmodmanager-$version-win-x64" -Version $version -OutputDir dist + - name: Upload Windows packages + uses: actions/upload-artifact@v4 + with: + name: windows-test-packages + if-no-files-found: error + path: | + dist/*.zip + dist/*.exe + dist/*.msi + dist/*.sha256 diff --git a/.gitignore b/.gitignore index c922e75..f99b24d 100644 --- a/.gitignore +++ b/.gitignore @@ -6,6 +6,12 @@ publish/ release-assets/ /target/ /dist/ +# Locally staged release packages and their tester instructions. +/gregmodmanager-*.exe +/gregmodmanager-*.msi +/gregmodmanager-*.apk +/gregmodmanager-*.sha256 +/gregmodmanager-*-TESTANLEITUNG.md # Crate-local Cargo targets when a workspace tool is invoked below the root. **/target/ crates/greg-app/ui/.generated/ diff --git a/.globalconfig b/.globalconfig deleted file mode 100644 index 4c2601b..0000000 --- a/.globalconfig +++ /dev/null @@ -1,10 +0,0 @@ -is_global = true - -# The repository intentionally keeps several generated/template-heavy UI and parser files together -# to preserve XAML/code-behind locality and Steam BBCode parser readability. Track structural -# refactors separately from security and correctness fixes. -dotnet_diagnostic.S104.severity = none -dotnet_diagnostic.S138.severity = none - -# Some public APIs preserve ergonomic overload-compatible signatures while older callers migrate. -dotnet_diagnostic.S2360.severity = none diff --git a/.jules/de-mock.md b/.jules/de-mock.md deleted file mode 100644 index b7a0617..0000000 --- a/.jules/de-mock.md +++ /dev/null @@ -1,16 +0,0 @@ -# De-Mock Journal - -## 2026-06-29 - Initial Analysis -**Mock Pattern:** Repository uses .NET 9 with Avalonia UI, Steam integration via Facepunch.Steamworks -**Learning:** Cross-platform desktop app with platform-specific code (Windows/Linux). Steam API integration is core functionality. -**Future Handling:** Focus on service stubs, placeholder implementations, and hardcoded demo data in productive code paths. - -## 2026-06-29 - AuthApiClient Mock Replacement -**Mock Pattern:** `AuthApiClient.ExchangeCallbackCodeAsync` returned hardcoded mock tokens (`mock_access_token`, `mocked User`) instead of making real API calls. `SessionManager.InitializeAsync` created mock sessions on refresh. `SessionManager.HandleProtocolCallbackAsync` stored `mock_refresh` as token. -**Learning:** Real auth API exists at `https://datacentermods.com/auth` (production) and `http://localhost:5001/auth` (local). `BetterAuthService.cs` shows existing HTTP client pattern with `HttpClient`. -**Future Handling:** Auth flow now uses real HTTP calls. Token exchange, session refresh, and logout all hit real API endpoints. Remaining mock: `InstallIntentClient.cs` accepts signatures >= 64 chars without cryptographic verification (TODO in code). - -## 2026-06-29 - InstallIntentClient Signature Verification -**Mock Pattern:** `InstallIntentClient.ValidateIntentSafelyAsync` accepted all signatures >= 64 chars without cryptographic verification. TODO comment: "Implement actual cryptographic ECDSA/HMAC signature verification against server public key". -**Learning:** Server public key must be provided via `INSTALL_INTENT_PUBLIC_KEY` environment variable (Base64-encoded SubjectPublicKeyInfo). Signed payload format: `intentId|packageId|subjectId|expiresAt`. -**Future Handling:** ECDSA P-256 with SHA-256 verification now implemented. Missing public key returns clear error instead of accepting mock. All remaining productive mocks removed. diff --git a/.maintenance/logs/20260731T101625Z-2/dep-upgrader.log b/.maintenance/logs/20260731T101625Z-2/dep-upgrader.log deleted file mode 100644 index 59296ba..0000000 --- a/.maintenance/logs/20260731T101625Z-2/dep-upgrader.log +++ /dev/null @@ -1,11 +0,0 @@ -INFO Dep Upgrader 1.0.0 · Module deps · Root /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager -WARN The Git working tree contains uncommitted changes. -INFO [Dry run] A backup would be created. -INFO Update NuGet packages: tests/GregModmanager.Tests/GregModmanager.Tests.csproj: dotnet package update --project /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager/tests/GregModmanager.Tests/GregModmanager.Tests.csproj -INFO dotnet restore with NuGet audit: dotnet restore /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager/tests/GregModmanager.Tests/GregModmanager.Tests.csproj -p:NuGetAudit=true -p:NuGetAuditMode=all -p:NuGetAuditLevel=moderate -INFO Update NuGet packages: src/GregModmanager.Melons/SubDirectoryFixer/SubDirectoryFixer.csproj: dotnet package update --project /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager/src/GregModmanager.Melons/SubDirectoryFixer/SubDirectoryFixer.csproj -INFO dotnet restore with NuGet audit: dotnet restore /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager/src/GregModmanager.Melons/SubDirectoryFixer/SubDirectoryFixer.csproj -p:NuGetAudit=true -p:NuGetAuditMode=all -p:NuGetAuditLevel=moderate -INFO Update NuGet packages: src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj: dotnet package update --project /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager/src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj -INFO dotnet restore with NuGet audit: dotnet restore /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager/src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj -p:NuGetAudit=true -p:NuGetAuditMode=all -p:NuGetAuditLevel=moderate -INFO Update NuGet packages: src/GregModmanager.Core/GregModmanager.Core.csproj: dotnet package update --project /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager/src/GregModmanager.Core/GregModmanager.Core.csproj -INFO dotnet restore with NuGet audit: dotnet restore /home/marvin/Dokumente/GregFramework/AppRepositories/gregApp.Modmanager/src/GregModmanager.Core/GregModmanager.Core.csproj -p:NuGetAudit=true -p:NuGetAuditMode=all -p:NuGetAuditLevel=moderate diff --git a/.maintenance/logs/20260731T101625Z-2/git-status-before.txt b/.maintenance/logs/20260731T101625Z-2/git-status-before.txt deleted file mode 100644 index de96957..0000000 --- a/.maintenance/logs/20260731T101625Z-2/git-status-before.txt +++ /dev/null @@ -1,36 +0,0 @@ -A .dockerignore -M .github/workflows/build-and-release.yml -D .gitmodules -M AGENTS.md -M CHANGELOG.md -M EXTERNAL_DEPENDENCIES.md -M ModStoreAndManager-Roadmap.md -M README.md -M TOOLS.md -M USER.md -M api-compatibility.md -M build/builder.ps1 -M build/builder.sh -M build/installer/CODE_SIGNING.md -M build/scripts/README.md -M build/scripts/build.ps1 -A build/scripts/macos/run-remote-manual-test.sh -M current_features.md -M desktop-gap-matrix.md -A docker-bake.hcl -A docker/Dockerfile -A docker/Dockerfile.windows -A docker/README.md -M docs/01_END_USER_GUIDE.md -M docs/02_MOD_CREATOR_GUIDE.md -M docs/03_CONTRIBUTOR_GUIDE.md -M docs/INDEX.md -M docs/README.md -M docs/codebase/CONCERNS.md -M docs/codebase/INTEGRATIONS.md -M docs/codebase/STRUCTURE.md -M docs/codebase/TESTING.md -A docs/examples/manifests/README.md -M functions.md -M src/GregModmanager.Melons/gregPlugin.ModmanagerCompanion/goal.md -?? .maintenance/ diff --git a/.reference/README.md b/.reference/README.md deleted file mode 100644 index cdce614..0000000 --- a/.reference/README.md +++ /dev/null @@ -1,14 +0,0 @@ -# .reference/ - -Reference material for the Rust rewrite. Not built, not extended. - -## modmanager-old/ - -Frozen C# / Avalonia (.NET) implementation of gregModmanager, moved here when -the project restarted in Rust. See `RUST_GRAPH.md` (repo root) for the new -workspace plan and `AGENTS.md` for current agent instructions. - -- Buildable snapshot: `modmanager-old/GregModmanager.sln` (`global.json` pins the SDK). -- Layout: `src/` (Core, Avalonia UI, platform shims, Melons) + `tests/`. -- History is preserved via `git mv` — use `git log --follow` on any file. -- Do not extend. Bugfixes, if ever needed, go through the maintainer first. diff --git a/.reference/modmanager-old/GregModmanager.sln b/.reference/modmanager-old/GregModmanager.sln deleted file mode 100644 index a68b9ff..0000000 --- a/.reference/modmanager-old/GregModmanager.sln +++ /dev/null @@ -1,62 +0,0 @@ - -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio Version 17 -VisualStudioVersion = 17.0.31903.59 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GregModmanager.Core", "src\GregModmanager.Core\GregModmanager.Core.csproj", "{BF379205-BC69-4114-9119-5A9F789D2D06}" -EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GregModmanager.Tests", "tests\GregModmanager.Tests\GregModmanager.Tests.csproj", "{440B5885-F5E8-473F-B561-C559A6E3019C}" -EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GregModmanager.Avalonia", "src\GregModmanager.Avalonia\GregModmanager.Avalonia.csproj", "{00D72EE3-0C58-4A5D-9B03-4F76D1B26924}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Any CPU = Debug|Any CPU - Debug|x64 = Debug|x64 - Debug|x86 = Debug|x86 - Release|Any CPU = Release|Any CPU - Release|x64 = Release|x64 - Release|x86 = Release|x86 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {BF379205-BC69-4114-9119-5A9F789D2D06}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Debug|Any CPU.Build.0 = Debug|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Debug|x64.ActiveCfg = Debug|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Debug|x64.Build.0 = Debug|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Debug|x86.ActiveCfg = Debug|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Debug|x86.Build.0 = Debug|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Release|Any CPU.ActiveCfg = Release|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Release|Any CPU.Build.0 = Release|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Release|x64.ActiveCfg = Release|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Release|x64.Build.0 = Release|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Release|x86.ActiveCfg = Release|Any CPU - {BF379205-BC69-4114-9119-5A9F789D2D06}.Release|x86.Build.0 = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Debug|Any CPU.Build.0 = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Debug|x64.ActiveCfg = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Debug|x64.Build.0 = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Debug|x86.ActiveCfg = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Debug|x86.Build.0 = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Release|Any CPU.ActiveCfg = Release|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Release|Any CPU.Build.0 = Release|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Release|x64.ActiveCfg = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Release|x64.Build.0 = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Release|x86.ActiveCfg = Debug|Any CPU - {440B5885-F5E8-473F-B561-C559A6E3019C}.Release|x86.Build.0 = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Debug|Any CPU.Build.0 = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Debug|x64.ActiveCfg = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Debug|x64.Build.0 = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Debug|x86.ActiveCfg = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Debug|x86.Build.0 = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Release|Any CPU.ActiveCfg = Release|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Release|Any CPU.Build.0 = Release|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Release|x64.ActiveCfg = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Release|x64.Build.0 = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Release|x86.ActiveCfg = Debug|Any CPU - {00D72EE3-0C58-4A5D-9B03-4F76D1B26924}.Release|x86.Build.0 = Debug|Any CPU - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection -EndGlobal diff --git a/.reference/modmanager-old/global.json b/.reference/modmanager-old/global.json deleted file mode 100644 index 3ffd6b3..0000000 --- a/.reference/modmanager-old/global.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "sdk": { - "version": "10.0.110", - "rollForward": "latestMajor" - } -} diff --git a/.reference/modmanager-old/src/GregModmanager.Avalonia/App.axaml b/.reference/modmanager-old/src/GregModmanager.Avalonia/App.axaml deleted file mode 100644 index edc431d..0000000 --- a/.reference/modmanager-old/src/GregModmanager.Avalonia/App.axaml +++ /dev/null @@ -1,10 +0,0 @@ - - - - - - diff --git a/.reference/modmanager-old/src/GregModmanager.Avalonia/App.axaml.cs b/.reference/modmanager-old/src/GregModmanager.Avalonia/App.axaml.cs deleted file mode 100644 index 1491fab..0000000 --- a/.reference/modmanager-old/src/GregModmanager.Avalonia/App.axaml.cs +++ /dev/null @@ -1,94 +0,0 @@ -using Avalonia; -using Avalonia.Controls.ApplicationLifetimes; -using Avalonia.Markup.Xaml; -using Microsoft.Extensions.DependencyInjection; -using GregModmanager.Services; -using GregModmanager.Models; - -namespace GregModmanager.Avalonia; - -public partial class App : Application -{ - public static IServiceProvider Services { get; private set; } = null!; - - public override void Initialize() - { - AvaloniaXamlLoader.Load(this); - } - - public override void OnFrameworkInitializationCompleted() - { - try - { - Services = Program.BuildServices(); - } - catch (Exception ex) - { - AppFileLog.MarkCrash("App.BuildServices", ex); - AppFileLog.Error("Failed to build DI container", ex); - ShowFatalError(ex); - return; - } - - try - { - var telemetry = Services.GetRequiredService(); - _ = telemetry.ReportCrashesAsync(); - _ = telemetry.TrackEventAsync("startup", new TelemetryStartupEvent - { - SteamActive = GregModmanager.Steam.SteamApiNativeLoader.IsLoaded, - Culture = System.Globalization.CultureInfo.CurrentCulture.Name, - OsDescription = System.Runtime.InteropServices.RuntimeInformation.OSDescription, - DotNetVersion = System.Runtime.InteropServices.RuntimeInformation.FrameworkDescription - }); - } - catch (Exception ex) - { - AppFileLog.Error("Telemetry init failed (non-fatal)", ex); - } - - if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop) - { - try - { - var mainWindow = Services.GetRequiredService(); - desktop.MainWindow = mainWindow; - } - catch (Exception ex) - { - AppFileLog.MarkCrash("App.MainWindow", ex); - AppFileLog.Error("Failed to create MainWindow", ex); - ShowFatalError(ex); - return; - } - } - - base.OnFrameworkInitializationCompleted(); - } - - private static void ShowFatalError(Exception ex) - { -#if WINDOWS - if (OperatingSystem.IsWindows()) - { - try - { - var logDir = Path.Combine( - Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), - "GregModmanager", "logs"); - var msg = $"gregModmanager could not start.\n\nError: {ex.Message}\n\nLogs: {logDir}"; - Win32MessageBox(IntPtr.Zero, msg, "gregModmanager - Startup Error", 0x10); - } - catch - { - // Last resort: silent exit - } - } -#endif - } - -#if WINDOWS - [System.Runtime.InteropServices.DllImport("user32.dll", EntryPoint = "MessageBoxW", CharSet = System.Runtime.InteropServices.CharSet.Unicode)] - private static extern int Win32MessageBox(IntPtr hWnd, string text, string caption, uint type); -#endif -} diff --git a/.reference/modmanager-old/src/GregModmanager.Avalonia/Assets/SubDirectoryFixer/README.txt b/.reference/modmanager-old/src/GregModmanager.Avalonia/Assets/SubDirectoryFixer/README.txt deleted file mode 100644 index fa3667c..0000000 --- a/.reference/modmanager-old/src/GregModmanager.Avalonia/Assets/SubDirectoryFixer/README.txt +++ /dev/null @@ -1,9 +0,0 @@ -Place the compiled MelonLoader helper mod here: - - SubDirectoryFixer.dll - -At runtime, gregModmanager installs this DLL on first app start to: - - \Mods\SubDirectoryFixer.dll - -If the DLL is missing, installation is skipped and logged. \ No newline at end of file diff --git a/.reference/modmanager-old/src/GregModmanager.Avalonia/Assets/SubDirectoryFixer/SubDirectoryFixer.dll b/.reference/modmanager-old/src/GregModmanager.Avalonia/Assets/SubDirectoryFixer/SubDirectoryFixer.dll deleted file mode 100644 index 77317ef..0000000 Binary files a/.reference/modmanager-old/src/GregModmanager.Avalonia/Assets/SubDirectoryFixer/SubDirectoryFixer.dll and /dev/null differ diff --git a/.reference/modmanager-old/src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj b/.reference/modmanager-old/src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj deleted file mode 100644 index ffacbcf..0000000 --- a/.reference/modmanager-old/src/GregModmanager.Avalonia/GregModmanager.Avalonia.csproj +++ /dev/null @@ -1,93 +0,0 @@ - - - WinExe - net10.0 - enable - enable - app.manifest - GregModmanager - GregModmanager.Avalonia - 1.6.1 - - - true - full - true - - true - true - none - false - true - en;de;fr;es;it;ja;pl;ru;zh - - - - - - - - - - win-x64 - $(DefineConstants);WINDOWS - - - linux-x64 - $(DefineConstants);LINUX - - - osx-x64 - $(DefineConstants);OSX - - - - - - - - - - - - - - - - - - - - - - steam_api64.dll - PreserveNewest - PreserveNewest - true - - - libsteam_api64.so - PreserveNewest - PreserveNewest - true - - - libsteam_api.so - PreserveNewest - PreserveNewest - true - - - SubDirectoryFixer\README.txt - PreserveNewest - PreserveNewest - - - SubDirectoryFixer\SubDirectoryFixer.dll - PreserveNewest - Always - true - - - diff --git a/.reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml b/.reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml deleted file mode 100644 index 63b7171..0000000 --- a/.reference/modmanager-old/src/GregModmanager.Avalonia/MainWindow.axaml +++ /dev/null @@ -1,155 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -