@opencodereview/core 1.9.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/ai/anthropic-provider.d.ts +41 -0
- package/dist/ai/anthropic-provider.d.ts.map +1 -0
- package/dist/ai/anthropic-provider.js +139 -0
- package/dist/ai/anthropic-provider.js.map +1 -0
- package/dist/ai/index.d.ts +39 -0
- package/dist/ai/index.d.ts.map +1 -0
- package/dist/ai/index.js +41 -0
- package/dist/ai/index.js.map +1 -0
- package/dist/ai/ollama-provider.d.ts +46 -0
- package/dist/ai/ollama-provider.d.ts.map +1 -0
- package/dist/ai/ollama-provider.js +149 -0
- package/dist/ai/ollama-provider.js.map +1 -0
- package/dist/ai/openai-provider.d.ts +44 -0
- package/dist/ai/openai-provider.d.ts.map +1 -0
- package/dist/ai/openai-provider.js +137 -0
- package/dist/ai/openai-provider.js.map +1 -0
- package/dist/ai/orchestrator.d.ts +60 -0
- package/dist/ai/orchestrator.d.ts.map +1 -0
- package/dist/ai/orchestrator.js +188 -0
- package/dist/ai/orchestrator.js.map +1 -0
- package/dist/ai/prompts.d.ts +27 -0
- package/dist/ai/prompts.d.ts.map +1 -0
- package/dist/ai/prompts.js +112 -0
- package/dist/ai/prompts.js.map +1 -0
- package/dist/ai/types.d.ts +75 -0
- package/dist/ai/types.d.ts.map +1 -0
- package/dist/ai/types.js +10 -0
- package/dist/ai/types.js.map +1 -0
- package/dist/ai/v4/embedding/index.d.ts +10 -0
- package/dist/ai/v4/embedding/index.d.ts.map +1 -0
- package/dist/ai/v4/embedding/index.js +10 -0
- package/dist/ai/v4/embedding/index.js.map +1 -0
- package/dist/ai/v4/embedding/local.d.ts +68 -0
- package/dist/ai/v4/embedding/local.d.ts.map +1 -0
- package/dist/ai/v4/embedding/local.js +167 -0
- package/dist/ai/v4/embedding/local.js.map +1 -0
- package/dist/ai/v4/embedding/ollama.d.ts +58 -0
- package/dist/ai/v4/embedding/ollama.d.ts.map +1 -0
- package/dist/ai/v4/embedding/ollama.js +101 -0
- package/dist/ai/v4/embedding/ollama.js.map +1 -0
- package/dist/ai/v4/embedding/openai.d.ts +36 -0
- package/dist/ai/v4/embedding/openai.d.ts.map +1 -0
- package/dist/ai/v4/embedding/openai.js +76 -0
- package/dist/ai/v4/embedding/openai.js.map +1 -0
- package/dist/ai/v4/embedding/similarity.d.ts +36 -0
- package/dist/ai/v4/embedding/similarity.d.ts.map +1 -0
- package/dist/ai/v4/embedding/similarity.js +60 -0
- package/dist/ai/v4/embedding/similarity.js.map +1 -0
- package/dist/ai/v4/index.d.ts +51 -0
- package/dist/ai/v4/index.d.ts.map +1 -0
- package/dist/ai/v4/index.js +54 -0
- package/dist/ai/v4/index.js.map +1 -0
- package/dist/ai/v4/llm/anthropic.d.ts +38 -0
- package/dist/ai/v4/llm/anthropic.d.ts.map +1 -0
- package/dist/ai/v4/llm/anthropic.js +86 -0
- package/dist/ai/v4/llm/anthropic.js.map +1 -0
- package/dist/ai/v4/llm/index.d.ts +9 -0
- package/dist/ai/v4/llm/index.d.ts.map +1 -0
- package/dist/ai/v4/llm/index.js +9 -0
- package/dist/ai/v4/llm/index.js.map +1 -0
- package/dist/ai/v4/llm/ollama.d.ts +39 -0
- package/dist/ai/v4/llm/ollama.d.ts.map +1 -0
- package/dist/ai/v4/llm/ollama.js +95 -0
- package/dist/ai/v4/llm/ollama.js.map +1 -0
- package/dist/ai/v4/llm/openai.d.ts +38 -0
- package/dist/ai/v4/llm/openai.d.ts.map +1 -0
- package/dist/ai/v4/llm/openai.js +88 -0
- package/dist/ai/v4/llm/openai.js.map +1 -0
- package/dist/ai/v4/patterns/defect-patterns.d.ts +57 -0
- package/dist/ai/v4/patterns/defect-patterns.d.ts.map +1 -0
- package/dist/ai/v4/patterns/defect-patterns.js +331 -0
- package/dist/ai/v4/patterns/defect-patterns.js.map +1 -0
- package/dist/ai/v4/patterns/index.d.ts +8 -0
- package/dist/ai/v4/patterns/index.d.ts.map +1 -0
- package/dist/ai/v4/patterns/index.js +7 -0
- package/dist/ai/v4/patterns/index.js.map +1 -0
- package/dist/ai/v4/pipeline.d.ts +74 -0
- package/dist/ai/v4/pipeline.d.ts.map +1 -0
- package/dist/ai/v4/pipeline.js +381 -0
- package/dist/ai/v4/pipeline.js.map +1 -0
- package/dist/ai/v4/sla.d.ts +62 -0
- package/dist/ai/v4/sla.d.ts.map +1 -0
- package/dist/ai/v4/sla.js +136 -0
- package/dist/ai/v4/sla.js.map +1 -0
- package/dist/ai/v4/types.d.ts +117 -0
- package/dist/ai/v4/types.d.ts.map +1 -0
- package/dist/ai/v4/types.js +16 -0
- package/dist/ai/v4/types.js.map +1 -0
- package/dist/ai-healer/prompt-builder.d.ts +33 -0
- package/dist/ai-healer/prompt-builder.d.ts.map +1 -0
- package/dist/ai-healer/prompt-builder.js +89 -0
- package/dist/ai-healer/prompt-builder.js.map +1 -0
- package/dist/config/defaults.d.ts +14 -0
- package/dist/config/defaults.d.ts.map +1 -0
- package/dist/config/defaults.js +57 -0
- package/dist/config/defaults.js.map +1 -0
- package/dist/config/index.d.ts +8 -0
- package/dist/config/index.d.ts.map +1 -0
- package/dist/config/index.js +6 -0
- package/dist/config/index.js.map +1 -0
- package/dist/config/loader.d.ts +33 -0
- package/dist/config/loader.d.ts.map +1 -0
- package/dist/config/loader.js +245 -0
- package/dist/config/loader.js.map +1 -0
- package/dist/config/types.d.ts +58 -0
- package/dist/config/types.d.ts.map +1 -0
- package/dist/config/types.js +7 -0
- package/dist/config/types.js.map +1 -0
- package/dist/config/v4-config.d.ts +77 -0
- package/dist/config/v4-config.d.ts.map +1 -0
- package/dist/config/v4-config.js +336 -0
- package/dist/config/v4-config.js.map +1 -0
- package/dist/detectors/ai-detector.d.ts +38 -0
- package/dist/detectors/ai-detector.d.ts.map +1 -0
- package/dist/detectors/ai-detector.js +62 -0
- package/dist/detectors/ai-detector.js.map +1 -0
- package/dist/detectors/context-break.d.ts +57 -0
- package/dist/detectors/context-break.d.ts.map +1 -0
- package/dist/detectors/context-break.js +199 -0
- package/dist/detectors/context-break.js.map +1 -0
- package/dist/detectors/deep-hallucination.d.ts +42 -0
- package/dist/detectors/deep-hallucination.d.ts.map +1 -0
- package/dist/detectors/deep-hallucination.js +297 -0
- package/dist/detectors/deep-hallucination.js.map +1 -0
- package/dist/detectors/duplication.d.ts +61 -0
- package/dist/detectors/duplication.d.ts.map +1 -0
- package/dist/detectors/duplication.js +204 -0
- package/dist/detectors/duplication.js.map +1 -0
- package/dist/detectors/hallucination.d.ts +80 -0
- package/dist/detectors/hallucination.d.ts.map +1 -0
- package/dist/detectors/hallucination.js +350 -0
- package/dist/detectors/hallucination.js.map +1 -0
- package/dist/detectors/index.d.ts +35 -0
- package/dist/detectors/index.d.ts.map +1 -0
- package/dist/detectors/index.js +33 -0
- package/dist/detectors/index.js.map +1 -0
- package/dist/detectors/logic-gap.d.ts +58 -0
- package/dist/detectors/logic-gap.d.ts.map +1 -0
- package/dist/detectors/logic-gap.js +284 -0
- package/dist/detectors/logic-gap.js.map +1 -0
- package/dist/detectors/over-engineering.d.ts +44 -0
- package/dist/detectors/over-engineering.d.ts.map +1 -0
- package/dist/detectors/over-engineering.js +257 -0
- package/dist/detectors/over-engineering.js.map +1 -0
- package/dist/detectors/security-pattern.d.ts +43 -0
- package/dist/detectors/security-pattern.d.ts.map +1 -0
- package/dist/detectors/security-pattern.js +235 -0
- package/dist/detectors/security-pattern.js.map +1 -0
- package/dist/detectors/stale-api.d.ts +44 -0
- package/dist/detectors/stale-api.d.ts.map +1 -0
- package/dist/detectors/stale-api.js +160 -0
- package/dist/detectors/stale-api.js.map +1 -0
- package/dist/detectors/type-safety.d.ts +41 -0
- package/dist/detectors/type-safety.d.ts.map +1 -0
- package/dist/detectors/type-safety.js +306 -0
- package/dist/detectors/type-safety.js.map +1 -0
- package/dist/detectors/v4/context-coherence.d.ts +67 -0
- package/dist/detectors/v4/context-coherence.d.ts.map +1 -0
- package/dist/detectors/v4/context-coherence.js +319 -0
- package/dist/detectors/v4/context-coherence.js.map +1 -0
- package/dist/detectors/v4/hallucinated-import.d.ts +52 -0
- package/dist/detectors/v4/hallucinated-import.d.ts.map +1 -0
- package/dist/detectors/v4/hallucinated-import.js +206 -0
- package/dist/detectors/v4/hallucinated-import.js.map +1 -0
- package/dist/detectors/v4/index.d.ts +28 -0
- package/dist/detectors/v4/index.d.ts.map +1 -0
- package/dist/detectors/v4/index.js +40 -0
- package/dist/detectors/v4/index.js.map +1 -0
- package/dist/detectors/v4/over-engineering.d.ts +69 -0
- package/dist/detectors/v4/over-engineering.d.ts.map +1 -0
- package/dist/detectors/v4/over-engineering.js +234 -0
- package/dist/detectors/v4/over-engineering.js.map +1 -0
- package/dist/detectors/v4/security-pattern.d.ts +46 -0
- package/dist/detectors/v4/security-pattern.d.ts.map +1 -0
- package/dist/detectors/v4/security-pattern.js +233 -0
- package/dist/detectors/v4/security-pattern.js.map +1 -0
- package/dist/detectors/v4/stale-api.d.ts +59 -0
- package/dist/detectors/v4/stale-api.d.ts.map +1 -0
- package/dist/detectors/v4/stale-api.js +470 -0
- package/dist/detectors/v4/stale-api.js.map +1 -0
- package/dist/detectors/v4/types.d.ts +74 -0
- package/dist/detectors/v4/types.d.ts.map +1 -0
- package/dist/detectors/v4/types.js +10 -0
- package/dist/detectors/v4/types.js.map +1 -0
- package/dist/diff/filter.d.ts +35 -0
- package/dist/diff/filter.d.ts.map +1 -0
- package/dist/diff/filter.js +65 -0
- package/dist/diff/filter.js.map +1 -0
- package/dist/diff/index.d.ts +9 -0
- package/dist/diff/index.d.ts.map +1 -0
- package/dist/diff/index.js +8 -0
- package/dist/diff/index.js.map +1 -0
- package/dist/diff/parser.d.ts +61 -0
- package/dist/diff/parser.d.ts.map +1 -0
- package/dist/diff/parser.js +203 -0
- package/dist/diff/parser.js.map +1 -0
- package/dist/i18n/en.d.ts +18 -0
- package/dist/i18n/en.d.ts.map +1 -0
- package/dist/i18n/en.js +83 -0
- package/dist/i18n/en.js.map +1 -0
- package/dist/i18n/index.d.ts +13 -0
- package/dist/i18n/index.d.ts.map +1 -0
- package/dist/i18n/index.js +14 -0
- package/dist/i18n/index.js.map +1 -0
- package/dist/i18n/provider.d.ts +54 -0
- package/dist/i18n/provider.d.ts.map +1 -0
- package/dist/i18n/provider.js +88 -0
- package/dist/i18n/provider.js.map +1 -0
- package/dist/i18n/types.d.ts +37 -0
- package/dist/i18n/types.d.ts.map +1 -0
- package/dist/i18n/types.js +10 -0
- package/dist/i18n/types.js.map +1 -0
- package/dist/i18n/zh.d.ts +14 -0
- package/dist/i18n/zh.d.ts.map +1 -0
- package/dist/i18n/zh.js +83 -0
- package/dist/i18n/zh.js.map +1 -0
- package/dist/index.d.ts +113 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +106 -0
- package/dist/index.js.map +1 -0
- package/dist/ir/index.d.ts +10 -0
- package/dist/ir/index.d.ts.map +1 -0
- package/dist/ir/index.js +9 -0
- package/dist/ir/index.js.map +1 -0
- package/dist/ir/types.d.ts +126 -0
- package/dist/ir/types.d.ts.map +1 -0
- package/dist/ir/types.js +33 -0
- package/dist/ir/types.js.map +1 -0
- package/dist/languages/go/index.d.ts +7 -0
- package/dist/languages/go/index.d.ts.map +1 -0
- package/dist/languages/go/index.js +7 -0
- package/dist/languages/go/index.js.map +1 -0
- package/dist/languages/go/parser.d.ts +89 -0
- package/dist/languages/go/parser.d.ts.map +1 -0
- package/dist/languages/go/parser.js +509 -0
- package/dist/languages/go/parser.js.map +1 -0
- package/dist/languages/index.d.ts +13 -0
- package/dist/languages/index.d.ts.map +1 -0
- package/dist/languages/index.js +14 -0
- package/dist/languages/index.js.map +1 -0
- package/dist/languages/java/index.d.ts +7 -0
- package/dist/languages/java/index.d.ts.map +1 -0
- package/dist/languages/java/index.js +7 -0
- package/dist/languages/java/index.js.map +1 -0
- package/dist/languages/java/parser.d.ts +82 -0
- package/dist/languages/java/parser.d.ts.map +1 -0
- package/dist/languages/java/parser.js +492 -0
- package/dist/languages/java/parser.js.map +1 -0
- package/dist/languages/kotlin/index.d.ts +7 -0
- package/dist/languages/kotlin/index.d.ts.map +1 -0
- package/dist/languages/kotlin/index.js +7 -0
- package/dist/languages/kotlin/index.js.map +1 -0
- package/dist/languages/kotlin/parser.d.ts +84 -0
- package/dist/languages/kotlin/parser.d.ts.map +1 -0
- package/dist/languages/kotlin/parser.js +507 -0
- package/dist/languages/kotlin/parser.js.map +1 -0
- package/dist/languages/python/index.d.ts +7 -0
- package/dist/languages/python/index.d.ts.map +1 -0
- package/dist/languages/python/index.js +7 -0
- package/dist/languages/python/index.js.map +1 -0
- package/dist/languages/python/parser.d.ts +91 -0
- package/dist/languages/python/parser.d.ts.map +1 -0
- package/dist/languages/python/parser.js +375 -0
- package/dist/languages/python/parser.js.map +1 -0
- package/dist/languages/registry.d.ts +81 -0
- package/dist/languages/registry.d.ts.map +1 -0
- package/dist/languages/registry.js +150 -0
- package/dist/languages/registry.js.map +1 -0
- package/dist/languages/types.d.ts +137 -0
- package/dist/languages/types.d.ts.map +1 -0
- package/dist/languages/types.js +10 -0
- package/dist/languages/types.js.map +1 -0
- package/dist/languages/typescript/index.d.ts +7 -0
- package/dist/languages/typescript/index.d.ts.map +1 -0
- package/dist/languages/typescript/index.js +7 -0
- package/dist/languages/typescript/index.js.map +1 -0
- package/dist/languages/typescript/parser.d.ts +51 -0
- package/dist/languages/typescript/parser.d.ts.map +1 -0
- package/dist/languages/typescript/parser.js +286 -0
- package/dist/languages/typescript/parser.js.map +1 -0
- package/dist/license/generator.d.ts +43 -0
- package/dist/license/generator.d.ts.map +1 -0
- package/dist/license/generator.js +72 -0
- package/dist/license/generator.js.map +1 -0
- package/dist/license/index.d.ts +11 -0
- package/dist/license/index.d.ts.map +1 -0
- package/dist/license/index.js +12 -0
- package/dist/license/index.js.map +1 -0
- package/dist/license/types.d.ts +85 -0
- package/dist/license/types.d.ts.map +1 -0
- package/dist/license/types.js +10 -0
- package/dist/license/types.js.map +1 -0
- package/dist/license/validator.d.ts +77 -0
- package/dist/license/validator.d.ts.map +1 -0
- package/dist/license/validator.js +275 -0
- package/dist/license/validator.js.map +1 -0
- package/dist/parser/extractor.d.ts +31 -0
- package/dist/parser/extractor.d.ts.map +1 -0
- package/dist/parser/extractor.js +10 -0
- package/dist/parser/extractor.js.map +1 -0
- package/dist/parser/extractors/go.d.ts +21 -0
- package/dist/parser/extractors/go.d.ts.map +1 -0
- package/dist/parser/extractors/go.js +569 -0
- package/dist/parser/extractors/go.js.map +1 -0
- package/dist/parser/extractors/index.d.ts +13 -0
- package/dist/parser/extractors/index.d.ts.map +1 -0
- package/dist/parser/extractors/index.js +13 -0
- package/dist/parser/extractors/index.js.map +1 -0
- package/dist/parser/extractors/java.d.ts +24 -0
- package/dist/parser/extractors/java.d.ts.map +1 -0
- package/dist/parser/extractors/java.js +611 -0
- package/dist/parser/extractors/java.js.map +1 -0
- package/dist/parser/extractors/kotlin.d.ts +25 -0
- package/dist/parser/extractors/kotlin.d.ts.map +1 -0
- package/dist/parser/extractors/kotlin.js +665 -0
- package/dist/parser/extractors/kotlin.js.map +1 -0
- package/dist/parser/extractors/python.d.ts +21 -0
- package/dist/parser/extractors/python.d.ts.map +1 -0
- package/dist/parser/extractors/python.js +514 -0
- package/dist/parser/extractors/python.js.map +1 -0
- package/dist/parser/extractors/typescript.d.ts +23 -0
- package/dist/parser/extractors/typescript.d.ts.map +1 -0
- package/dist/parser/extractors/typescript.js +664 -0
- package/dist/parser/extractors/typescript.js.map +1 -0
- package/dist/parser/index.d.ts +15 -0
- package/dist/parser/index.d.ts.map +1 -0
- package/dist/parser/index.js +14 -0
- package/dist/parser/index.js.map +1 -0
- package/dist/parser/manager.d.ts +50 -0
- package/dist/parser/manager.d.ts.map +1 -0
- package/dist/parser/manager.js +159 -0
- package/dist/parser/manager.js.map +1 -0
- package/dist/registry/builtins/go-builtins.d.ts +13 -0
- package/dist/registry/builtins/go-builtins.d.ts.map +1 -0
- package/dist/registry/builtins/go-builtins.js +63 -0
- package/dist/registry/builtins/go-builtins.js.map +1 -0
- package/dist/registry/builtins/java-builtins.d.ts +10 -0
- package/dist/registry/builtins/java-builtins.d.ts.map +1 -0
- package/dist/registry/builtins/java-builtins.js +59 -0
- package/dist/registry/builtins/java-builtins.js.map +1 -0
- package/dist/registry/builtins/kotlin-builtins.d.ts +10 -0
- package/dist/registry/builtins/kotlin-builtins.d.ts.map +1 -0
- package/dist/registry/builtins/kotlin-builtins.js +38 -0
- package/dist/registry/builtins/kotlin-builtins.js.map +1 -0
- package/dist/registry/builtins/node-builtins.d.ts +10 -0
- package/dist/registry/builtins/node-builtins.d.ts.map +1 -0
- package/dist/registry/builtins/node-builtins.js +36 -0
- package/dist/registry/builtins/node-builtins.js.map +1 -0
- package/dist/registry/builtins/python-builtins.d.ts +10 -0
- package/dist/registry/builtins/python-builtins.d.ts.map +1 -0
- package/dist/registry/builtins/python-builtins.js +43 -0
- package/dist/registry/builtins/python-builtins.js.map +1 -0
- package/dist/registry/cache.d.ts +53 -0
- package/dist/registry/cache.d.ts.map +1 -0
- package/dist/registry/cache.js +147 -0
- package/dist/registry/cache.js.map +1 -0
- package/dist/registry/go-registry.d.ts +52 -0
- package/dist/registry/go-registry.d.ts.map +1 -0
- package/dist/registry/go-registry.js +148 -0
- package/dist/registry/go-registry.js.map +1 -0
- package/dist/registry/index.d.ts +18 -0
- package/dist/registry/index.d.ts.map +1 -0
- package/dist/registry/index.js +21 -0
- package/dist/registry/index.js.map +1 -0
- package/dist/registry/maven-registry.d.ts +57 -0
- package/dist/registry/maven-registry.d.ts.map +1 -0
- package/dist/registry/maven-registry.js +155 -0
- package/dist/registry/maven-registry.js.map +1 -0
- package/dist/registry/npm-registry.d.ts +40 -0
- package/dist/registry/npm-registry.d.ts.map +1 -0
- package/dist/registry/npm-registry.js +155 -0
- package/dist/registry/npm-registry.js.map +1 -0
- package/dist/registry/pypi-registry.d.ts +49 -0
- package/dist/registry/pypi-registry.d.ts.map +1 -0
- package/dist/registry/pypi-registry.js +175 -0
- package/dist/registry/pypi-registry.js.map +1 -0
- package/dist/registry/registry-manager.d.ts +45 -0
- package/dist/registry/registry-manager.d.ts.map +1 -0
- package/dist/registry/registry-manager.js +107 -0
- package/dist/registry/registry-manager.js.map +1 -0
- package/dist/registry/types.d.ts +83 -0
- package/dist/registry/types.d.ts.map +1 -0
- package/dist/registry/types.js +12 -0
- package/dist/registry/types.js.map +1 -0
- package/dist/reporter/html-reporter.d.ts +20 -0
- package/dist/reporter/html-reporter.d.ts.map +1 -0
- package/dist/reporter/html-reporter.js +612 -0
- package/dist/reporter/html-reporter.js.map +1 -0
- package/dist/reporter/index.d.ts +28 -0
- package/dist/reporter/index.d.ts.map +1 -0
- package/dist/reporter/index.js +48 -0
- package/dist/reporter/index.js.map +1 -0
- package/dist/reporter/markdown-reporter.d.ts +16 -0
- package/dist/reporter/markdown-reporter.d.ts.map +1 -0
- package/dist/reporter/markdown-reporter.js +182 -0
- package/dist/reporter/markdown-reporter.js.map +1 -0
- package/dist/reporter/sarif-reporter.d.ts +67 -0
- package/dist/reporter/sarif-reporter.d.ts.map +1 -0
- package/dist/reporter/sarif-reporter.js +73 -0
- package/dist/reporter/sarif-reporter.js.map +1 -0
- package/dist/reporter/terminal-reporter.d.ts +14 -0
- package/dist/reporter/terminal-reporter.d.ts.map +1 -0
- package/dist/reporter/terminal-reporter.js +126 -0
- package/dist/reporter/terminal-reporter.js.map +1 -0
- package/dist/reporter/types.d.ts +43 -0
- package/dist/reporter/types.d.ts.map +1 -0
- package/dist/reporter/types.js +10 -0
- package/dist/reporter/types.js.map +1 -0
- package/dist/reporter/v4-html.d.ts +24 -0
- package/dist/reporter/v4-html.d.ts.map +1 -0
- package/dist/reporter/v4-html.js +359 -0
- package/dist/reporter/v4-html.js.map +1 -0
- package/dist/reporter/v4-terminal.d.ts +55 -0
- package/dist/reporter/v4-terminal.d.ts.map +1 -0
- package/dist/reporter/v4-terminal.js +199 -0
- package/dist/reporter/v4-terminal.js.map +1 -0
- package/dist/scanner/index.d.ts +9 -0
- package/dist/scanner/index.d.ts.map +1 -0
- package/dist/scanner/index.js +9 -0
- package/dist/scanner/index.js.map +1 -0
- package/dist/scanner/v4-scanner.d.ts +162 -0
- package/dist/scanner/v4-scanner.d.ts.map +1 -0
- package/dist/scanner/v4-scanner.js +327 -0
- package/dist/scanner/v4-scanner.js.map +1 -0
- package/dist/scorer/report.d.ts +52 -0
- package/dist/scorer/report.d.ts.map +1 -0
- package/dist/scorer/report.js +347 -0
- package/dist/scorer/report.js.map +1 -0
- package/dist/scorer/scoring-engine.d.ts +170 -0
- package/dist/scorer/scoring-engine.d.ts.map +1 -0
- package/dist/scorer/scoring-engine.js +308 -0
- package/dist/scorer/scoring-engine.js.map +1 -0
- package/dist/scorer/v4-adapter.d.ts +87 -0
- package/dist/scorer/v4-adapter.d.ts.map +1 -0
- package/dist/scorer/v4-adapter.js +145 -0
- package/dist/scorer/v4-adapter.js.map +1 -0
- package/dist/sla/index.d.ts +7 -0
- package/dist/sla/index.d.ts.map +1 -0
- package/dist/sla/index.js +6 -0
- package/dist/sla/index.js.map +1 -0
- package/dist/sla/tracker.d.ts +70 -0
- package/dist/sla/tracker.d.ts.map +1 -0
- package/dist/sla/tracker.js +151 -0
- package/dist/sla/tracker.js.map +1 -0
- package/dist/sla/types.d.ts +67 -0
- package/dist/sla/types.d.ts.map +1 -0
- package/dist/sla/types.js +42 -0
- package/dist/sla/types.js.map +1 -0
- package/dist/types.d.ts +172 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +69 -0
- package/dist/types.js.map +1 -0
- package/package.json +97 -0
|
@@ -0,0 +1,284 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Logic Gap Detector (V3)
|
|
3
|
+
*
|
|
4
|
+
* Detects AI-generated code logic discontinuities:
|
|
5
|
+
* 1. Empty catch blocks (swallowed errors)
|
|
6
|
+
* 2. Unreachable code after return/throw
|
|
7
|
+
* 3. Missing else branches in critical conditions
|
|
8
|
+
* 4. Unused variables that suggest incomplete logic
|
|
9
|
+
* 5. TODO/FIXME markers left by AI (incomplete implementation)
|
|
10
|
+
* 6. Functions that declare parameters but never use them
|
|
11
|
+
*
|
|
12
|
+
* Implements the unified Detector interface.
|
|
13
|
+
*
|
|
14
|
+
* @since 0.2.0 (original)
|
|
15
|
+
* @since 0.3.0 (V3 unified interface)
|
|
16
|
+
*/
|
|
17
|
+
import { AIDefectCategory } from '../types.js';
|
|
18
|
+
// ─── Internal Detection Functions ───
|
|
19
|
+
function detectEmptyCatch(lines, filePath) {
|
|
20
|
+
const issues = [];
|
|
21
|
+
for (let i = 0; i < lines.length; i++) {
|
|
22
|
+
const line = lines[i].trim();
|
|
23
|
+
if (/catch\s*(\([^)]*\))?\s*\{/.test(line)) {
|
|
24
|
+
let j = i + 1;
|
|
25
|
+
let blockContent = '';
|
|
26
|
+
let braceDepth = 0;
|
|
27
|
+
let foundOpen = false;
|
|
28
|
+
for (const ch of line) {
|
|
29
|
+
if (ch === '{') {
|
|
30
|
+
braceDepth++;
|
|
31
|
+
foundOpen = true;
|
|
32
|
+
}
|
|
33
|
+
if (ch === '}')
|
|
34
|
+
braceDepth--;
|
|
35
|
+
}
|
|
36
|
+
if (foundOpen && braceDepth === 0) {
|
|
37
|
+
const afterCatch = line.replace(/catch\s*(\([^)]*\))?\s*\{/, '').replace('}', '').trim();
|
|
38
|
+
if (!afterCatch) {
|
|
39
|
+
issues.push({
|
|
40
|
+
type: 'empty-catch',
|
|
41
|
+
severity: 'warning',
|
|
42
|
+
file: filePath,
|
|
43
|
+
line: i + 1,
|
|
44
|
+
message: 'Empty catch block — errors are silently swallowed',
|
|
45
|
+
suggestion: 'Log the error or handle it explicitly. AI-generated code often leaves empty catch blocks.',
|
|
46
|
+
});
|
|
47
|
+
continue;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
if (braceDepth > 0) {
|
|
51
|
+
while (j < lines.length && braceDepth > 0) {
|
|
52
|
+
for (const ch of lines[j]) {
|
|
53
|
+
if (ch === '{')
|
|
54
|
+
braceDepth++;
|
|
55
|
+
if (ch === '}')
|
|
56
|
+
braceDepth--;
|
|
57
|
+
}
|
|
58
|
+
blockContent += lines[j].trim();
|
|
59
|
+
j++;
|
|
60
|
+
}
|
|
61
|
+
blockContent = blockContent.replace(/}$/, '').trim();
|
|
62
|
+
if (!blockContent || blockContent === '// TODO' || blockContent === '// ignore') {
|
|
63
|
+
issues.push({
|
|
64
|
+
type: 'empty-catch',
|
|
65
|
+
severity: 'warning',
|
|
66
|
+
file: filePath,
|
|
67
|
+
line: i + 1,
|
|
68
|
+
message: 'Empty or trivial catch block — errors are silently swallowed',
|
|
69
|
+
suggestion: 'Log the error or handle it explicitly.',
|
|
70
|
+
});
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
return issues;
|
|
76
|
+
}
|
|
77
|
+
function detectIncompleteImpl(lines, filePath) {
|
|
78
|
+
const issues = [];
|
|
79
|
+
const markers = [
|
|
80
|
+
{ pattern: /\/\/\s*TODO/i, label: 'TODO' },
|
|
81
|
+
{ pattern: /\/\/\s*FIXME/i, label: 'FIXME' },
|
|
82
|
+
{ pattern: /\/\/\s*HACK/i, label: 'HACK' },
|
|
83
|
+
{ pattern: /\/\/\s*XXX/i, label: 'XXX' },
|
|
84
|
+
{ pattern: /throw\s+new\s+Error\s*\(\s*['"]not\s+implemented['"]/i, label: 'Not implemented' },
|
|
85
|
+
{ pattern: /throw\s+new\s+Error\s*\(\s*['"]todo['"]/i, label: 'TODO throw' },
|
|
86
|
+
{ pattern: /\/\/\s*\.\.\./i, label: 'Ellipsis comment' },
|
|
87
|
+
];
|
|
88
|
+
for (let i = 0; i < lines.length; i++) {
|
|
89
|
+
for (const marker of markers) {
|
|
90
|
+
if (marker.pattern.test(lines[i])) {
|
|
91
|
+
issues.push({
|
|
92
|
+
type: 'incomplete-implementation',
|
|
93
|
+
severity: 'warning',
|
|
94
|
+
file: filePath,
|
|
95
|
+
line: i + 1,
|
|
96
|
+
message: `Incomplete implementation marker found: ${marker.label}`,
|
|
97
|
+
suggestion: 'AI-generated code often leaves placeholder markers. Implement the missing logic.',
|
|
98
|
+
});
|
|
99
|
+
break;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
return issues;
|
|
104
|
+
}
|
|
105
|
+
function detectUnreachableCode(lines, filePath) {
|
|
106
|
+
const issues = [];
|
|
107
|
+
for (let i = 0; i < lines.length - 1; i++) {
|
|
108
|
+
const line = lines[i].trim();
|
|
109
|
+
if (/^(return|throw)\s/.test(line) || /^(return|throw);?$/.test(line)) {
|
|
110
|
+
let j = i + 1;
|
|
111
|
+
while (j < lines.length) {
|
|
112
|
+
const next = lines[j].trim();
|
|
113
|
+
if (!next || next.startsWith('//') || next.startsWith('*')) {
|
|
114
|
+
j++;
|
|
115
|
+
continue;
|
|
116
|
+
}
|
|
117
|
+
if (next === '}' || next.startsWith('case ') || next.startsWith('default:'))
|
|
118
|
+
break;
|
|
119
|
+
if (/^(function|class|export|const|let|var|interface|type|enum)/.test(next))
|
|
120
|
+
break;
|
|
121
|
+
issues.push({
|
|
122
|
+
type: 'unreachable-code',
|
|
123
|
+
severity: 'warning',
|
|
124
|
+
file: filePath,
|
|
125
|
+
line: j + 1,
|
|
126
|
+
message: 'Potentially unreachable code after return/throw statement',
|
|
127
|
+
suggestion: 'This code will never execute. AI may have added logic after a return statement.',
|
|
128
|
+
});
|
|
129
|
+
break;
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
return issues;
|
|
134
|
+
}
|
|
135
|
+
function detectMissingErrorHandling(lines, filePath) {
|
|
136
|
+
const issues = [];
|
|
137
|
+
const source = lines.join('\n');
|
|
138
|
+
const asyncFuncPattern = /async\s+(?:function\s+)?(\w+)?\s*\([^)]*\)\s*(?::\s*[^{]+)?\s*\{/g;
|
|
139
|
+
let match;
|
|
140
|
+
while ((match = asyncFuncPattern.exec(source)) !== null) {
|
|
141
|
+
const startIdx = match.index;
|
|
142
|
+
const lineNum = source.substring(0, startIdx).split('\n').length;
|
|
143
|
+
let braceDepth = 0;
|
|
144
|
+
let hasTryCatch = false;
|
|
145
|
+
let searchStart = source.indexOf('{', startIdx);
|
|
146
|
+
if (searchStart === -1)
|
|
147
|
+
continue;
|
|
148
|
+
for (let k = searchStart; k < source.length; k++) {
|
|
149
|
+
if (source[k] === '{')
|
|
150
|
+
braceDepth++;
|
|
151
|
+
if (source[k] === '}') {
|
|
152
|
+
braceDepth--;
|
|
153
|
+
if (braceDepth === 0)
|
|
154
|
+
break;
|
|
155
|
+
}
|
|
156
|
+
if (braceDepth === 1 && source.substring(k).startsWith('try')) {
|
|
157
|
+
hasTryCatch = true;
|
|
158
|
+
break;
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
const funcBody = source.substring(searchStart, source.indexOf('}', searchStart + 1) + 1);
|
|
162
|
+
if (funcBody.includes('.catch(') || funcBody.includes('.catch (')) {
|
|
163
|
+
hasTryCatch = true;
|
|
164
|
+
}
|
|
165
|
+
if (!hasTryCatch) {
|
|
166
|
+
const funcName = match[1] || 'anonymous';
|
|
167
|
+
if (funcBody.includes('await ')) {
|
|
168
|
+
issues.push({
|
|
169
|
+
type: 'missing-error-handling',
|
|
170
|
+
severity: 'warning',
|
|
171
|
+
file: filePath,
|
|
172
|
+
line: lineNum,
|
|
173
|
+
message: `Async function '${funcName}' lacks try-catch error handling`,
|
|
174
|
+
suggestion: 'Wrap async operations in try-catch blocks. AI often generates happy-path-only code.',
|
|
175
|
+
});
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
return issues;
|
|
180
|
+
}
|
|
181
|
+
// ─── Severity & Category Mapping ───
|
|
182
|
+
function mapSeverity(type) {
|
|
183
|
+
switch (type) {
|
|
184
|
+
case 'empty-catch':
|
|
185
|
+
case 'missing-error-handling':
|
|
186
|
+
return 'medium';
|
|
187
|
+
case 'unreachable-code':
|
|
188
|
+
case 'dead-code':
|
|
189
|
+
return 'low';
|
|
190
|
+
case 'incomplete-implementation':
|
|
191
|
+
return 'medium';
|
|
192
|
+
case 'unused-variable':
|
|
193
|
+
return 'low';
|
|
194
|
+
case 'missing-return':
|
|
195
|
+
return 'medium';
|
|
196
|
+
default:
|
|
197
|
+
return 'low';
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
function mapCategory(type) {
|
|
201
|
+
switch (type) {
|
|
202
|
+
case 'empty-catch':
|
|
203
|
+
case 'missing-error-handling':
|
|
204
|
+
return AIDefectCategory.ERROR_HANDLING;
|
|
205
|
+
case 'incomplete-implementation':
|
|
206
|
+
case 'missing-return':
|
|
207
|
+
return AIDefectCategory.INCOMPLETE_IMPL;
|
|
208
|
+
case 'unreachable-code':
|
|
209
|
+
case 'dead-code':
|
|
210
|
+
case 'unused-variable':
|
|
211
|
+
return AIDefectCategory.CONTEXT_LOSS;
|
|
212
|
+
default:
|
|
213
|
+
return AIDefectCategory.INCOMPLETE_IMPL;
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
function toUnifiedIssue(issue, index) {
|
|
217
|
+
return {
|
|
218
|
+
id: `logic-gap:${index}`,
|
|
219
|
+
detector: 'logic-gap',
|
|
220
|
+
category: mapCategory(issue.type),
|
|
221
|
+
severity: mapSeverity(issue.type),
|
|
222
|
+
message: issue.message,
|
|
223
|
+
file: issue.file,
|
|
224
|
+
line: issue.line,
|
|
225
|
+
fix: issue.suggestion ? {
|
|
226
|
+
description: issue.suggestion,
|
|
227
|
+
autoFixable: false,
|
|
228
|
+
} : undefined,
|
|
229
|
+
};
|
|
230
|
+
}
|
|
231
|
+
// ─── Main Detector ───
|
|
232
|
+
/**
|
|
233
|
+
* LogicGapDetector — detects AI-generated code logic gaps.
|
|
234
|
+
*
|
|
235
|
+
* V3: Implements the unified Detector interface.
|
|
236
|
+
* V2 (deprecated): Old analyze() signature still works.
|
|
237
|
+
*/
|
|
238
|
+
export class LogicGapDetector {
|
|
239
|
+
name = 'logic-gap';
|
|
240
|
+
version = '2.0.0';
|
|
241
|
+
tier = 1;
|
|
242
|
+
// ─── V3 Unified Interface ───
|
|
243
|
+
/**
|
|
244
|
+
* V3 unified detect method.
|
|
245
|
+
*/
|
|
246
|
+
async detect(files) {
|
|
247
|
+
const allIssues = [];
|
|
248
|
+
let globalIndex = 0;
|
|
249
|
+
for (const file of files) {
|
|
250
|
+
const result = this.analyze(file.path, file.content);
|
|
251
|
+
for (const issue of result.issues) {
|
|
252
|
+
allIssues.push(toUnifiedIssue(issue, globalIndex++));
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
return allIssues;
|
|
256
|
+
}
|
|
257
|
+
// ─── V2 Legacy Interface (Deprecated) ───
|
|
258
|
+
/**
|
|
259
|
+
* Analyze a single file for logic gap issues.
|
|
260
|
+
* @deprecated Use detect(files) instead. Will be removed in v0.4.0.
|
|
261
|
+
*/
|
|
262
|
+
analyze(filePath, source) {
|
|
263
|
+
const lines = source.split('\n');
|
|
264
|
+
const rawIssues = [
|
|
265
|
+
...detectEmptyCatch(lines, filePath),
|
|
266
|
+
...detectIncompleteImpl(lines, filePath),
|
|
267
|
+
...detectUnreachableCode(lines, filePath),
|
|
268
|
+
...detectMissingErrorHandling(lines, filePath),
|
|
269
|
+
];
|
|
270
|
+
const issues = rawIssues.filter(issue => {
|
|
271
|
+
if (issue.line <= 0)
|
|
272
|
+
return true;
|
|
273
|
+
const prevLine = lines[issue.line - 2] || '';
|
|
274
|
+
return !prevLine.includes('// ai-validator-ignore') && !prevLine.includes('// ai-validator-disable');
|
|
275
|
+
});
|
|
276
|
+
const errorCount = issues.filter(i => i.severity === 'error').length;
|
|
277
|
+
const warningCount = issues.filter(i => i.severity === 'warning').length;
|
|
278
|
+
const deductions = (errorCount * 15) + (warningCount * 5);
|
|
279
|
+
const score = Math.max(0, 100 - deductions);
|
|
280
|
+
return { file: filePath, issues, score };
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
export default LogicGapDetector;
|
|
284
|
+
//# sourceMappingURL=logic-gap.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"logic-gap.js","sourceRoot":"","sources":["../../src/detectors/logic-gap.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Over-Engineering Detector (V3)
|
|
3
|
+
*
|
|
4
|
+
* Detects overly complex code patterns commonly generated by AI models.
|
|
5
|
+
* AI tends to produce unnecessarily complex solutions with:
|
|
6
|
+
* - High cyclomatic complexity
|
|
7
|
+
* - Excessively long functions
|
|
8
|
+
* - Deep nesting
|
|
9
|
+
* - Too many function parameters
|
|
10
|
+
*
|
|
11
|
+
* Uses pure text/regex analysis (no AST required).
|
|
12
|
+
*
|
|
13
|
+
* Implements the unified Detector interface.
|
|
14
|
+
*
|
|
15
|
+
* @since 0.3.0
|
|
16
|
+
*/
|
|
17
|
+
import type { Detector, UnifiedIssue, FileAnalysis } from '../types.js';
|
|
18
|
+
/** Extracted function metadata for over-engineering analysis. */
|
|
19
|
+
export interface FunctionInfo {
|
|
20
|
+
name: string;
|
|
21
|
+
startLine: number;
|
|
22
|
+
endLine: number;
|
|
23
|
+
paramCount: number;
|
|
24
|
+
lines: string[];
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* OverEngineeringDetector — detects overly complex AI-generated code.
|
|
28
|
+
*
|
|
29
|
+
* Analyzes:
|
|
30
|
+
* - Cyclomatic complexity per function
|
|
31
|
+
* - Function length (line count)
|
|
32
|
+
* - Maximum nesting depth
|
|
33
|
+
* - Parameter count
|
|
34
|
+
*/
|
|
35
|
+
export declare class OverEngineeringDetector implements Detector {
|
|
36
|
+
readonly name = "over-engineering";
|
|
37
|
+
readonly version = "1.0.0";
|
|
38
|
+
readonly tier: 1;
|
|
39
|
+
detect(files: FileAnalysis[]): Promise<UnifiedIssue[]>;
|
|
40
|
+
private analyzeFile;
|
|
41
|
+
private makeIssue;
|
|
42
|
+
}
|
|
43
|
+
export default OverEngineeringDetector;
|
|
44
|
+
//# sourceMappingURL=over-engineering.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"over-engineering.d.ts","sourceRoot":"","sources":["../../src/detectors/over-engineering.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH,OAAO,KAAK,EAAE,QAAQ,EAAE,YAAY,EAAE,YAAY,EAAY,MAAM,aAAa,CAAC;AAKlF,iEAAiE;AACjE,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,KAAK,EAAE,MAAM,EAAE,CAAC;CACjB;AAwKD;;;;;;;;GAQG;AACH,qBAAa,uBAAwB,YAAW,QAAQ;IACtD,QAAQ,CAAC,IAAI,sBAAsB;IACnC,QAAQ,CAAC,OAAO,WAAW;IAC3B,QAAQ,CAAC,IAAI,EAAG,CAAC,CAAU;IAIrB,MAAM,CAAC,KAAK,EAAE,YAAY,EAAE,GAAG,OAAO,CAAC,YAAY,EAAE,CAAC;IAiB5D,OAAO,CAAC,WAAW;IAyEnB,OAAO,CAAC,SAAS;CA2BlB;AAED,eAAe,uBAAuB,CAAC"}
|
|
@@ -0,0 +1,257 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Over-Engineering Detector (V3)
|
|
3
|
+
*
|
|
4
|
+
* Detects overly complex code patterns commonly generated by AI models.
|
|
5
|
+
* AI tends to produce unnecessarily complex solutions with:
|
|
6
|
+
* - High cyclomatic complexity
|
|
7
|
+
* - Excessively long functions
|
|
8
|
+
* - Deep nesting
|
|
9
|
+
* - Too many function parameters
|
|
10
|
+
*
|
|
11
|
+
* Uses pure text/regex analysis (no AST required).
|
|
12
|
+
*
|
|
13
|
+
* Implements the unified Detector interface.
|
|
14
|
+
*
|
|
15
|
+
* @since 0.3.0
|
|
16
|
+
*/
|
|
17
|
+
import { AIDefectCategory } from '../types.js';
|
|
18
|
+
// ─── Function Extraction ───
|
|
19
|
+
/**
|
|
20
|
+
* Extract function boundaries from source code using brace matching.
|
|
21
|
+
* Handles: function declarations, arrow functions, methods.
|
|
22
|
+
*/
|
|
23
|
+
function extractFunctions(source) {
|
|
24
|
+
const functions = [];
|
|
25
|
+
const lines = source.split('\n');
|
|
26
|
+
for (let i = 0; i < lines.length; i++) {
|
|
27
|
+
const line = lines[i];
|
|
28
|
+
// Match function/method declarations
|
|
29
|
+
const funcMatch = line.match(/(?:(?:export\s+)?(?:default\s+)?(?:async\s+)?function\s+(\w+)|(?:(?:public|private|protected|static|async|override|get|set)\s+)*(\w+)\s*\([^)]*\)\s*(?::\s*[^{]+)?\s*\{|(?:const|let|var)\s+(\w+)\s*=\s*(?:async\s*)?\([^)]*\)\s*(?::\s*[^{=]+)?\s*=>)/);
|
|
30
|
+
if (!funcMatch)
|
|
31
|
+
continue;
|
|
32
|
+
const name = funcMatch[1] || funcMatch[2] || funcMatch[3] || 'anonymous';
|
|
33
|
+
// Skip destructuring assignments or simple variable declarations
|
|
34
|
+
if (/(?:const|let|var)\s*[\[{]/.test(line))
|
|
35
|
+
continue;
|
|
36
|
+
if (/(?:const|let|var)\s+\w+\s*=\s*(?:['"`\d\[{]|new\s|null|undefined|true|false)/.test(line) && !line.includes('=>'))
|
|
37
|
+
continue;
|
|
38
|
+
// Count parameters
|
|
39
|
+
const paramMatch = line.match(/\(([^)]*)\)/);
|
|
40
|
+
let paramCount = 0;
|
|
41
|
+
if (paramMatch && paramMatch[1].trim()) {
|
|
42
|
+
paramCount = paramMatch[1].split(',').length;
|
|
43
|
+
}
|
|
44
|
+
// Find function body end using brace matching
|
|
45
|
+
let braceDepth = 0;
|
|
46
|
+
let started = false;
|
|
47
|
+
let endLine = i;
|
|
48
|
+
// For arrow functions without braces, it's a single expression
|
|
49
|
+
if (line.includes('=>') && !line.includes('{')) {
|
|
50
|
+
// Single-expression arrow function
|
|
51
|
+
endLine = i;
|
|
52
|
+
// Check if it spans multiple lines (parenthesized expression)
|
|
53
|
+
let parenDepth = 0;
|
|
54
|
+
for (let j = i; j < lines.length; j++) {
|
|
55
|
+
for (const ch of lines[j]) {
|
|
56
|
+
if (ch === '(')
|
|
57
|
+
parenDepth++;
|
|
58
|
+
if (ch === ')')
|
|
59
|
+
parenDepth--;
|
|
60
|
+
}
|
|
61
|
+
endLine = j;
|
|
62
|
+
if (parenDepth <= 0 && j > i)
|
|
63
|
+
break;
|
|
64
|
+
if (j === i && !lines[j].includes('('))
|
|
65
|
+
break;
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
else {
|
|
69
|
+
// Brace-delimited function body
|
|
70
|
+
for (let j = i; j < lines.length; j++) {
|
|
71
|
+
for (const ch of lines[j]) {
|
|
72
|
+
if (ch === '{') {
|
|
73
|
+
braceDepth++;
|
|
74
|
+
started = true;
|
|
75
|
+
}
|
|
76
|
+
if (ch === '}')
|
|
77
|
+
braceDepth--;
|
|
78
|
+
}
|
|
79
|
+
if (started && braceDepth === 0) {
|
|
80
|
+
endLine = j;
|
|
81
|
+
break;
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
if (endLine > i) {
|
|
86
|
+
functions.push({
|
|
87
|
+
name,
|
|
88
|
+
startLine: i + 1,
|
|
89
|
+
endLine: endLine + 1,
|
|
90
|
+
paramCount,
|
|
91
|
+
lines: lines.slice(i, endLine + 1),
|
|
92
|
+
});
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
return functions;
|
|
96
|
+
}
|
|
97
|
+
// ─── Complexity Metrics ───
|
|
98
|
+
/**
|
|
99
|
+
* Compute cyclomatic complexity for a function body.
|
|
100
|
+
* CC = 1 + count of decision points.
|
|
101
|
+
*/
|
|
102
|
+
function computeCyclomaticComplexity(bodyLines) {
|
|
103
|
+
let cc = 1;
|
|
104
|
+
const body = bodyLines.join('\n');
|
|
105
|
+
// Count branching keywords
|
|
106
|
+
const patterns = [
|
|
107
|
+
/\bif\s*\(/g,
|
|
108
|
+
/\belse\s+if\s*\(/g,
|
|
109
|
+
/\bfor\s*\(/g,
|
|
110
|
+
/\bfor\s+(?:const|let|var)\s+\w+\s+(?:of|in)\b/g,
|
|
111
|
+
/\bwhile\s*\(/g,
|
|
112
|
+
/\bdo\s*\{/g,
|
|
113
|
+
/\bcase\s+[^:]+:/g,
|
|
114
|
+
/\bcatch\s*\(/g,
|
|
115
|
+
/\?\s*(?![:.])/g, // ternary operator (but not ?. or ?:)
|
|
116
|
+
/&&/g,
|
|
117
|
+
/\|\|/g,
|
|
118
|
+
/\?\?/g,
|
|
119
|
+
];
|
|
120
|
+
for (const pattern of patterns) {
|
|
121
|
+
const matches = body.match(pattern);
|
|
122
|
+
if (matches) {
|
|
123
|
+
cc += matches.length;
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
// Subtract double-counted 'else if' (already counted by 'if')
|
|
127
|
+
const elseIfMatches = body.match(/\belse\s+if\s*\(/g);
|
|
128
|
+
if (elseIfMatches) {
|
|
129
|
+
cc -= elseIfMatches.length;
|
|
130
|
+
}
|
|
131
|
+
return cc;
|
|
132
|
+
}
|
|
133
|
+
/**
|
|
134
|
+
* Compute maximum nesting depth for a function body.
|
|
135
|
+
*/
|
|
136
|
+
function computeMaxNesting(bodyLines) {
|
|
137
|
+
let maxDepth = 0;
|
|
138
|
+
let currentDepth = 0;
|
|
139
|
+
// Start at -1 to account for the function's own opening brace
|
|
140
|
+
let functionBrace = true;
|
|
141
|
+
for (const line of bodyLines) {
|
|
142
|
+
const trimmed = line.trim();
|
|
143
|
+
// Skip comments
|
|
144
|
+
if (trimmed.startsWith('//') || trimmed.startsWith('*') || trimmed.startsWith('/*'))
|
|
145
|
+
continue;
|
|
146
|
+
for (const ch of line) {
|
|
147
|
+
if (ch === '{') {
|
|
148
|
+
if (functionBrace) {
|
|
149
|
+
functionBrace = false;
|
|
150
|
+
continue;
|
|
151
|
+
}
|
|
152
|
+
currentDepth++;
|
|
153
|
+
maxDepth = Math.max(maxDepth, currentDepth);
|
|
154
|
+
}
|
|
155
|
+
if (ch === '}') {
|
|
156
|
+
currentDepth = Math.max(0, currentDepth - 1);
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
return maxDepth;
|
|
161
|
+
}
|
|
162
|
+
// ─── Thresholds ───
|
|
163
|
+
const THRESHOLDS = {
|
|
164
|
+
complexity: { medium: 15, high: 25 },
|
|
165
|
+
functionLength: { low: 80, medium: 150 },
|
|
166
|
+
nestingDepth: { medium: 4, high: 6 },
|
|
167
|
+
paramCount: { low: 5, medium: 8 },
|
|
168
|
+
};
|
|
169
|
+
// ─── Main Detector ───
|
|
170
|
+
/**
|
|
171
|
+
* OverEngineeringDetector — detects overly complex AI-generated code.
|
|
172
|
+
*
|
|
173
|
+
* Analyzes:
|
|
174
|
+
* - Cyclomatic complexity per function
|
|
175
|
+
* - Function length (line count)
|
|
176
|
+
* - Maximum nesting depth
|
|
177
|
+
* - Parameter count
|
|
178
|
+
*/
|
|
179
|
+
export class OverEngineeringDetector {
|
|
180
|
+
name = 'over-engineering';
|
|
181
|
+
version = '1.0.0';
|
|
182
|
+
tier = 1;
|
|
183
|
+
// ─── V3 Unified Interface ───
|
|
184
|
+
async detect(files) {
|
|
185
|
+
const allIssues = [];
|
|
186
|
+
let globalIndex = 0;
|
|
187
|
+
for (const file of files) {
|
|
188
|
+
const issues = this.analyzeFile(file.path, file.content);
|
|
189
|
+
for (const issue of issues) {
|
|
190
|
+
issue.id = `over-engineering:${globalIndex++}`;
|
|
191
|
+
allIssues.push(issue);
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
return allIssues;
|
|
195
|
+
}
|
|
196
|
+
// ─── Internal Analysis ───
|
|
197
|
+
analyzeFile(filePath, source) {
|
|
198
|
+
const issues = [];
|
|
199
|
+
const functions = extractFunctions(source);
|
|
200
|
+
for (const fn of functions) {
|
|
201
|
+
const functionLength = fn.endLine - fn.startLine + 1;
|
|
202
|
+
// 1. Cyclomatic Complexity
|
|
203
|
+
const cc = computeCyclomaticComplexity(fn.lines);
|
|
204
|
+
if (cc > THRESHOLDS.complexity.high) {
|
|
205
|
+
issues.push(this.makeIssue(filePath, fn, 'high-complexity', 'high', `Function '${fn.name}' has cyclomatic complexity of ${cc} (threshold: ${THRESHOLDS.complexity.high})`, `Refactor into smaller functions. AI often generates monolithic functions with too many branches.`));
|
|
206
|
+
}
|
|
207
|
+
else if (cc > THRESHOLDS.complexity.medium) {
|
|
208
|
+
issues.push(this.makeIssue(filePath, fn, 'high-complexity', 'medium', `Function '${fn.name}' has cyclomatic complexity of ${cc} (threshold: ${THRESHOLDS.complexity.medium})`, `Consider breaking this function into smaller, more focused functions.`));
|
|
209
|
+
}
|
|
210
|
+
// 2. Function Length
|
|
211
|
+
if (functionLength > THRESHOLDS.functionLength.medium) {
|
|
212
|
+
issues.push(this.makeIssue(filePath, fn, 'long-function', 'medium', `Function '${fn.name}' is ${functionLength} lines long (threshold: ${THRESHOLDS.functionLength.medium})`, `Break into smaller functions. AI tends to generate long, monolithic functions.`));
|
|
213
|
+
}
|
|
214
|
+
else if (functionLength > THRESHOLDS.functionLength.low) {
|
|
215
|
+
issues.push(this.makeIssue(filePath, fn, 'long-function', 'low', `Function '${fn.name}' is ${functionLength} lines long (threshold: ${THRESHOLDS.functionLength.low})`, `Consider extracting some logic into helper functions.`));
|
|
216
|
+
}
|
|
217
|
+
// 3. Nesting Depth
|
|
218
|
+
const depth = computeMaxNesting(fn.lines);
|
|
219
|
+
if (depth > THRESHOLDS.nestingDepth.high) {
|
|
220
|
+
issues.push(this.makeIssue(filePath, fn, 'deep-nesting', 'high', `Function '${fn.name}' has nesting depth of ${depth} (threshold: ${THRESHOLDS.nestingDepth.high})`, `Use early returns, guard clauses, or extract nested blocks into separate functions.`));
|
|
221
|
+
}
|
|
222
|
+
else if (depth > THRESHOLDS.nestingDepth.medium) {
|
|
223
|
+
issues.push(this.makeIssue(filePath, fn, 'deep-nesting', 'medium', `Function '${fn.name}' has nesting depth of ${depth} (threshold: ${THRESHOLDS.nestingDepth.medium})`, `Consider using early returns or extracting deeply nested logic.`));
|
|
224
|
+
}
|
|
225
|
+
// 4. Parameter Count
|
|
226
|
+
if (fn.paramCount > THRESHOLDS.paramCount.medium) {
|
|
227
|
+
issues.push(this.makeIssue(filePath, fn, 'too-many-params', 'medium', `Function '${fn.name}' has ${fn.paramCount} parameters (threshold: ${THRESHOLDS.paramCount.medium})`, `Use an options object pattern: function ${fn.name}(options: Options) instead.`));
|
|
228
|
+
}
|
|
229
|
+
else if (fn.paramCount > THRESHOLDS.paramCount.low) {
|
|
230
|
+
issues.push(this.makeIssue(filePath, fn, 'too-many-params', 'low', `Function '${fn.name}' has ${fn.paramCount} parameters (threshold: ${THRESHOLDS.paramCount.low})`, `Consider using an options object to group related parameters.`));
|
|
231
|
+
}
|
|
232
|
+
}
|
|
233
|
+
return issues;
|
|
234
|
+
}
|
|
235
|
+
makeIssue(filePath, fn, type, severity, message, suggestion) {
|
|
236
|
+
return {
|
|
237
|
+
id: '', // set in detect()
|
|
238
|
+
detector: this.name,
|
|
239
|
+
type,
|
|
240
|
+
category: AIDefectCategory.OVER_ENGINEERING,
|
|
241
|
+
severity,
|
|
242
|
+
message,
|
|
243
|
+
file: filePath,
|
|
244
|
+
line: fn.startLine,
|
|
245
|
+
endLine: fn.endLine,
|
|
246
|
+
suggestion,
|
|
247
|
+
fix: {
|
|
248
|
+
description: suggestion,
|
|
249
|
+
autoFixable: false,
|
|
250
|
+
},
|
|
251
|
+
confidence: 0.85,
|
|
252
|
+
detectionSource: 'static',
|
|
253
|
+
};
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
export default OverEngineeringDetector;
|
|
257
|
+
//# sourceMappingURL=over-engineering.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"over-engineering.js","sourceRoot":"","sources":["../../src/detectors/over-engineering.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Security Pattern Detector (V3)
|
|
3
|
+
*
|
|
4
|
+
* Detects AI-generated security anti-patterns:
|
|
5
|
+
* 1. Hardcoded secrets/credentials (CWE-798)
|
|
6
|
+
* 2. eval/Function constructor usage (CWE-95)
|
|
7
|
+
* 3. SQL injection via string concatenation/template literals (CWE-89)
|
|
8
|
+
* 4. Insecure cryptography: Math.random(), MD5/SHA1 for passwords (CWE-328/338)
|
|
9
|
+
* 5. Insecure defaults: cors origin '*', disabled security headers (CWE-942)
|
|
10
|
+
*
|
|
11
|
+
* AI models frequently generate code with these patterns from training data.
|
|
12
|
+
*
|
|
13
|
+
* Implements the unified Detector interface.
|
|
14
|
+
*
|
|
15
|
+
* @since 0.3.0
|
|
16
|
+
*/
|
|
17
|
+
import type { Detector, UnifiedIssue, FileAnalysis, Severity } from '../types.js';
|
|
18
|
+
/** Security pattern definition for detecting vulnerabilities in code. */
|
|
19
|
+
export interface SecurityPattern {
|
|
20
|
+
type: string;
|
|
21
|
+
regex: RegExp;
|
|
22
|
+
severity: Severity;
|
|
23
|
+
message: string;
|
|
24
|
+
suggestion: string;
|
|
25
|
+
cweId?: string;
|
|
26
|
+
/** Skip in test files */
|
|
27
|
+
skipTests?: boolean;
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* SecurityPatternDetector — detects common security anti-patterns in AI-generated code.
|
|
31
|
+
*
|
|
32
|
+
* Scans source code with regex patterns for 5 categories:
|
|
33
|
+
* hardcoded secrets, eval usage, SQL injection, insecure crypto, insecure defaults.
|
|
34
|
+
*/
|
|
35
|
+
export declare class SecurityPatternDetector implements Detector {
|
|
36
|
+
readonly name = "security-pattern";
|
|
37
|
+
readonly version = "1.0.0";
|
|
38
|
+
readonly tier: 1;
|
|
39
|
+
detect(files: FileAnalysis[]): Promise<UnifiedIssue[]>;
|
|
40
|
+
private analyzeFile;
|
|
41
|
+
}
|
|
42
|
+
export default SecurityPatternDetector;
|
|
43
|
+
//# sourceMappingURL=security-pattern.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"security-pattern.d.ts","sourceRoot":"","sources":["../../src/detectors/security-pattern.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH,OAAO,KAAK,EAAE,QAAQ,EAAE,YAAY,EAAE,YAAY,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAKlF,yEAAyE;AACzE,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,QAAQ,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,yBAAyB;IACzB,SAAS,CAAC,EAAE,OAAO,CAAC;CACrB;AAwID;;;;;GAKG;AACH,qBAAa,uBAAwB,YAAW,QAAQ;IACtD,QAAQ,CAAC,IAAI,sBAAsB;IACnC,QAAQ,CAAC,OAAO,WAAW;IAC3B,QAAQ,CAAC,IAAI,EAAG,CAAC,CAAU;IAIrB,MAAM,CAAC,KAAK,EAAE,YAAY,EAAE,GAAG,OAAO,CAAC,YAAY,EAAE,CAAC;IAiB5D,OAAO,CAAC,WAAW;CAgFpB;AAED,eAAe,uBAAuB,CAAC"}
|