{"version": "2.1.0", "$schema": "https://json.schemastore.org/sarif-2.1.0.json", "runs": [{"tool": {"driver": {"name": "Repobility", "informationUri": "https://repobility.com", "rules": [{"id": "foundry_blueprint_gap", "name": "Foundry mined blueprint gap alignment: stephmadfx/winelio-app", "shortDescription": {"text": "Foundry mined blueprint gap alignment: stephmadfx/winelio-app"}, "fullDescription": {"text": "Graph query export: Human feedback aligned with blueprint or architecture gaps\nQuery id: blueprint_gap_alignment\nQuery type: motif_query\nIntent: Curriculum-gap examples connecting issue threads to helicopter-view gaps.\nMotif: blueprint_gap_alignment\nTraining usage: curriculum_gap\nGraph gold label: weak_supervision_needs_review\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nEvidence:\nGraph motif: Human feedback aligns with blueprint or architecture gaps\nMotif id: blueprint_gap_alignment\nPolarity: mixed\nTraining usage: curriculum_gap\nSeverity: medium\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nGraph gold label: weak_supervision_needs_review\nThread graph evidence:\nGitHub issue/PR evidence subgraph\nThread: stephmadfx/winelio-app#2\nRepo: stephmadfx/winelio-app\nIssue/PR number: 2\nGraph consistency label: weak_supervision_needs_review\nNodes: 20\nEdges: 27\nNode types: {'link_quality': 6, 'alignment': 3, 'blueprint_finding': 3, 'thread': 1, 'repo': 1, 'comment': "}, "properties": {"scanner": "foundry_dataset", "category": "tech_debt", "severity": "medium", "confidence": 0.7, "cwe": "", "owasp": ""}}, {"id": "foundry_assumption_check", "name": "Foundry mined assumption checks: stephmadfx/winelio-app", "shortDescription": {"text": "Foundry mined assumption checks: stephmadfx/winelio-app"}, "fullDescription": {"text": "Comment chain pattern product: assumption_checks\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#3\nOutcome: claimed_resolved_unverified\nThread label: thread_has_human_issue_and_fix_context\nSource graph label: source_backed_multi_signal_graph\nReasons: source_graph_has_real_artifacts, source_graph_has_verification_artifacts, repo_has_isolated_helicopter_views, link_quality_weak_supervision\nChain evidence:\nIssue/PR evidence chain: stephmadfx/winelio-app#3\nRepo: stephmadfx/winelio-app\nThread label: thread_has_human_issue_and_fix_context\nOutcome: claimed_resolved_unverified\nComment count: 1\nLinked commit count: 5\nLinked CI commit count: 0\nLinked CI labels: {}\nChanged file count: 2\nLabels: {'agent_instruction_gap': 1}\nPolarities: {'bad': 1}\nChanged file labels: {'ui_or_frontend': 2}\nExamples:\n[\n  {\n    \"id\": \"github-feedback-comment-6a089e92aaeec2eb\",\n    \"kind\": \"pull_request_body\",\n    \"label\": \"agent_instruction_gap\",\n    \"polarity\": \"bad\",\n    \"url\": \"https://github.com/steph"}, "properties": {"scanner": "foundry_dataset", "category": "practices", "severity": "medium", "confidence": 0.62, "cwe": "", "owasp": ""}}, {"id": "foundry_test_ci_gap", "name": "Foundry mined test ci gap after feedback: stephmadfx/winelio-app", "shortDescription": {"text": "Foundry mined test ci gap after feedback: stephmadfx/winelio-app"}, "fullDescription": {"text": "Graph query export: Feedback exposes missing tests or CI\nQuery id: test_ci_gap_after_feedback\nQuery type: motif_query\nIntent: Hard negatives for feedback/fix chains without adequate guardrails.\nMotif: test_ci_gap_after_feedback\nTraining usage: hard_negative\nGraph gold label: weak_supervision_needs_review\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nEvidence:\nGraph motif: Feedback or fix context exposes missing test/CI guardrails\nMotif id: test_ci_gap_after_feedback\nPolarity: bad\nTraining usage: hard_negative\nSeverity: high\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nGraph gold label: weak_supervision_needs_review\nThread graph evidence:\nGitHub issue/PR evidence subgraph\nThread: stephmadfx/winelio-app#2\nRepo: stephmadfx/winelio-app\nIssue/PR number: 2\nGraph consistency label: weak_supervision_needs_review\nNodes: 20\nEdges: 27\nNode types: {'link_quality': 6, 'alignment': 3, 'blueprint_finding': 3, 'thread': 1, 'repo': 1, 'comment': 1, 'pr_file': 1, 'commen"}, "properties": {"scanner": "foundry_dataset", "category": "testing", "severity": "high", "confidence": 0.78, "cwe": "", "owasp": ""}}, {"id": "scanner-bead75b0f9233e05", "name": "No API endpoints detected", "shortDescription": {"text": "No API endpoints detected"}, "fullDescription": {"text": "The scanner did not find FastAPI/Flask/Express/NestJS/GraphQL/gRPC routes. If this repo exposes APIs, the framework may be unsupported."}, "properties": {"scanner": "scanner-primary", "layer": "api", "severity": "info", "confidence": 1.0}}, {"id": "scanner-35296945768b36b1", "name": "Stray `console.log` in TS/JS \u2014 scripts/backfill-aliases.ts:34", "shortDescription": {"text": "Stray `console.log` in TS/JS \u2014 scripts/backfill-aliases.ts:34"}, "fullDescription": {"text": "Replace with the toast helper, an error boundary, or remove. `console.warn` / `console.error` are acceptable.\n\nWhy: Hygiene \u2014 easy to leak debug output.\nRule id: fq.console-leak"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-5818ab701c52ba47", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/network-tree.tsx:307", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/network-tree.tsx:307"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-09e3e4c1d363c8b6", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/sidebar.tsx:113", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/sidebar.tsx:113"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-66ab2d7ed064fc13", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/mobile-header.tsx:193", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/mobile-header.tsx:193"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-6903050badd15d9d", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/referral-buttons.tsx:297", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/referral-buttons.tsx:297"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-59632fc10be90214", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/activity-feed.tsx:339", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/activity-feed.tsx:339"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-2a81f744addc7115", "name": "Icon-only button without accessible name \u2014 src/components/DemoSeedBanner.tsx:52", "shortDescription": {"text": "Icon-only button without accessible name \u2014 src/components/DemoSeedBanner.tsx:52"}, "fullDescription": {"text": "A `<button>` whose only child is a single glyph or symbol needs `title=` or `aria-label=` so screen readers (and tooltips on hover) work.\n\nWhy: P3 in CHECKLIST.md \u2014 icon-only buttons skipped a title.\nRule id: fq.button.no-label"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-6dd79222e356d281", "name": "Icon-only button without accessible name \u2014 src/components/network-graph.tsx:373", "shortDescription": {"text": "Icon-only button without accessible name \u2014 src/components/network-graph.tsx:373"}, "fullDescription": {"text": "A `<button>` whose only child is a single glyph or symbol needs `title=` or `aria-label=` so screen readers (and tooltips on hover) work.\n\nWhy: P3 in CHECKLIST.md \u2014 icon-only buttons skipped a title.\nRule id: fq.button.no-label"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-65570d4f2f05faa9", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/network-graph.tsx:523", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/network-graph.tsx:523"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-0a48e75d45cd7fc6", "name": "`dangerouslySetInnerHTML` used in a React component \u2014 src/components/ui/chart.tsx:95", "shortDescription": {"text": "`dangerouslySetInnerHTML` used in a React component \u2014 src/components/ui/chart.tsx:95"}, "fullDescription": {"text": "Open XSS surface unless the input is provably trusted. Replace with explicit JSX or sanitize via a vetted library.\n\nWhy: OWASP basics. Already partially flagged by the security analyzer.\nRule id: fq.dangerous-html"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-3bc229fe2573b354", "name": "Icon-only button without accessible name \u2014 src/components/admin/EmailPreviewDialog.tsx:59", "shortDescription": {"text": "Icon-only button without accessible name \u2014 src/components/admin/EmailPreviewDialog.tsx:59"}, "fullDescription": {"text": "A `<button>` whose only child is a single glyph or symbol needs `title=` or `aria-label=` so screen readers (and tooltips on hover) work.\n\nWhy: P3 in CHECKLIST.md \u2014 icon-only buttons skipped a title.\nRule id: fq.button.no-label"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-50bab95a58dc1fea", "name": "React Flow <MiniMap> without dark background \u2014 src/components/admin/NetworkTree.tsx:780", "shortDescription": {"text": "React Flow <MiniMap> without dark background \u2014 src/components/admin/NetworkTree.tsx:780"}, "fullDescription": {"text": "A bare <MiniMap> renders with the vendor's white default in dark themes. Wrap the canvas in a class that overrides `.react-flow__minimap` background, or pass an explicit `style`/`maskColor`/`bgColor`.\n\nWhy: P1 in CHECKLIST.md \u2014 vendor defaults bleed light through.\nRule id: fq.minimap.no-bg"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-116e6d62d10be77e", "name": "React Flow <Controls> without dark theming \u2014 src/components/admin/NetworkTree.tsx:779", "shortDescription": {"text": "React Flow <Controls> without dark theming \u2014 src/components/admin/NetworkTree.tsx:779"}, "fullDescription": {"text": "`<Controls>` ships with white buttons. Override `.react-flow__controls` and `.react-flow__controls-button` in your stylesheet or pass a styled wrapper.\n\nWhy: P1 in CHECKLIST.md \u2014 vendor defaults bleed light through.\nRule id: fq.controls.no-bg"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-921ed6b1bcf7b072", "name": "Icon-only button without accessible name \u2014 src/components/admin/NetworkTree.tsx:271", "shortDescription": {"text": "Icon-only button without accessible name \u2014 src/components/admin/NetworkTree.tsx:271"}, "fullDescription": {"text": "A `<button>` whose only child is a single glyph or symbol needs `title=` or `aria-label=` so screen readers (and tooltips on hover) work.\n\nWhy: P3 in CHECKLIST.md \u2014 icon-only buttons skipped a title.\nRule id: fq.button.no-label"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-b4b51fe68c6d74f5", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/AdminLayoutShell.tsx:118", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/AdminLayoutShell.tsx:118"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-7f3890a40f608867", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/AnnotationPanel.tsx:74", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/AnnotationPanel.tsx:74"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-dd440b67e1512526", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/BugTrackerBoard.tsx:376", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/BugTrackerBoard.tsx:376"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-2126861a4cc28a0d", "name": "Icon-only button without accessible name \u2014 src/components/admin/ProfessionnelsTable.tsx:191", "shortDescription": {"text": "Icon-only button without accessible name \u2014 src/components/admin/ProfessionnelsTable.tsx:191"}, "fullDescription": {"text": "A `<button>` whose only child is a single glyph or symbol needs `title=` or `aria-label=` so screen readers (and tooltips on hover) work.\n\nWhy: P3 in CHECKLIST.md \u2014 icon-only buttons skipped a title.\nRule id: fq.button.no-label"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-d8fc0ffa888f1aa1", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/ProfessionnelsTable.tsx:254", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/ProfessionnelsTable.tsx:254"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-6c236c9cd3cd040f", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/newsletters/NewsletterPreviewDialog.tsx:32", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/newsletters/NewsletterPreviewDialog.tsx:32"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-c8d7c8838de691a3", "name": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/newsletters/NewsletterEditor.tsx:1033", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/newsletters/NewsletterEditor.tsx:1033"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-d393813b163d03e7", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/utilisateurs/page.tsx:204", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/utilisateurs/page.tsx:204"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-427102a75d433ed7", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/utilisateurs/[id]/page.tsx:154", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/utilisateurs/[id]/page.tsx:154"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-0a4fac9df170449b", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/recommandations/page.tsx:127", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/recommandations/page.tsx:127"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-dfe1c2b4a1a86628", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/reseau/AdminNetworkContent.tsx:169", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/reseau/AdminNetworkContent.tsx:169"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-6e1904901b72dc0e", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/newsletters/page.tsx:53", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/newsletters/page.tsx:53"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-f66f50e7fc1956ed", "name": "Icon-only button without accessible name \u2014 src/app/gestion-reseau/retraits/page.tsx:127", "shortDescription": {"text": "Icon-only button without accessible name \u2014 src/app/gestion-reseau/retraits/page.tsx:127"}, "fullDescription": {"text": "A `<button>` whose only child is a single glyph or symbol needs `title=` or `aria-label=` so screen readers (and tooltips on hover) work.\n\nWhy: P3 in CHECKLIST.md \u2014 icon-only buttons skipped a title.\nRule id: fq.button.no-label"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-877b171bcd483cc6", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/retraits/page.tsx:77", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/retraits/page.tsx:77"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-af5dabf162f04670", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/page.tsx:341", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/page.tsx:341"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-b474ecf182750061", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/new/StepContact.tsx:123", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/new/StepContact.tsx:123"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-b9122a9c44f5cbce", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/[id]/page.tsx:294", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/[id]/page.tsx:294"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-f772d96ba83369d3", "name": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/network/page.tsx:147", "shortDescription": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/network/page.tsx:147"}, "fullDescription": {"text": "A truncated value should reveal the full text on hover. Pass the full string via `title={...}` so the user can read it.\n\nWhy: P2 in CHECKLIST.md \u2014 truncate without hover-reveal.\nRule id: fq.truncate.no-title"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "info", "confidence": 1.0}}, {"id": "scanner-a90108750906049f", "name": "Stray `console.log` in TS/JS \u2014 src/app/(protected)/test-recommendation/page.tsx:27", "shortDescription": {"text": "Stray `console.log` in TS/JS \u2014 src/app/(protected)/test-recommendation/page.tsx:27"}, "fullDescription": {"text": "Replace with the toast helper, an error boundary, or remove. `console.warn` / `console.error` are acceptable.\n\nWhy: Hygiene \u2014 easy to leak debug output.\nRule id: fq.console-leak"}, "properties": {"scanner": "scanner-primary", "layer": "frontend", "severity": "low", "confidence": 1.0}}, {"id": "scanner-c7e254d4ccddc63c", "name": "Privileged port 195 in use", "shortDescription": {"text": "Privileged port 195 in use"}, "fullDescription": {"text": "Port 195 is privileged (<1024). Make sure the service runs with the right caps or front it with a non-privileged port via a load balancer."}, "properties": {"scanner": "scanner-primary", "layer": "network", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-f2c6d165af64636e", "name": "Docker base image is tag-pinned but not digest-pinned: node:22.22.2-alpine", "shortDescription": {"text": "Docker base image is tag-pinned but not digest-pinned: node:22.22.2-alpine"}, "fullDescription": {"text": "Container tags can be retagged upstream. Pin production base images to a reviewed digest (`image@sha256:...`) when reproducibility and supply-chain integrity matter."}, "properties": {"scanner": "scanner-primary", "layer": "hardware", "severity": "low", "confidence": 1.0}}, {"id": "scanner-aa5acaa49eb8315b", "name": "Containers defined but no K8s/orchestration manifest found", "shortDescription": {"text": "Containers defined but no K8s/orchestration manifest found"}, "fullDescription": {"text": "Repo has Dockerfiles/compose but no Kubernetes/Nomad manifests. If the target deployment is K8s, the manifests may live in a separate ops repo."}, "properties": {"scanner": "scanner-primary", "layer": "hardware", "severity": "low", "confidence": 1.0}}, {"id": "scanner-a22d2ac060c1bbb9", "name": "Possible secret in tmp-test-login.cjs", "shortDescription": {"text": "Possible secret in tmp-test-login.cjs"}, "fullDescription": {"text": "Detected pattern matching password_literal. Rotate the credential and move to a secret manager."}, "properties": {"scanner": "scanner-primary", "layer": "security", "severity": "critical", "confidence": 1.0}}, {"id": "scanner-f36756e4816e3f59", "name": "Insecure pattern 'dangerous_innerhtml' in src/components/ui/chart.tsx:95", "shortDescription": {"text": "Insecure pattern 'dangerous_innerhtml' in src/components/ui/chart.tsx:95"}, "fullDescription": {"text": "Found a known-risky pattern (dangerous_innerhtml). Review and replace if possible."}, "properties": {"scanner": "scanner-primary", "layer": "security", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-43362c89c1299779", "name": "Insecure pattern 'node_child_process' in src/lib/generate-signed-pdf.ts:2", "shortDescription": {"text": "Insecure pattern 'node_child_process' in src/lib/generate-signed-pdf.ts:2"}, "fullDescription": {"text": "Found a known-risky pattern (node_child_process). Review and replace if possible."}, "properties": {"scanner": "scanner-primary", "layer": "security", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-84a3022c0c33da03", "name": "Insecure pattern 'node_child_process' in video/scripts/generate-audio.mjs:10", "shortDescription": {"text": "Insecure pattern 'node_child_process' in video/scripts/generate-audio.mjs:10"}, "fullDescription": {"text": "Found a known-risky pattern (node_child_process). Review and replace if possible."}, "properties": {"scanner": "scanner-primary", "layer": "security", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-f7fa3da12bd977cb", "name": "Insecure pattern 'node_child_process' in video/editor/server.mjs:5", "shortDescription": {"text": "Insecure pattern 'node_child_process' in video/editor/server.mjs:5"}, "fullDescription": {"text": "Found a known-risky pattern (node_child_process). Review and replace if possible."}, "properties": {"scanner": "scanner-primary", "layer": "security", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-67ef737a6c5314f1", "name": "Insecure pattern 'cors_wildcard' in video/editor/server.mjs:49", "shortDescription": {"text": "Insecure pattern 'cors_wildcard' in video/editor/server.mjs:49"}, "fullDescription": {"text": "Found a known-risky pattern (cors_wildcard). Review and replace if possible."}, "properties": {"scanner": "scanner-primary", "layer": "security", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-908d126fb67d173a", "name": "Insecure pattern 'direct_innerhtml_assignment' in video/editor/index.html:365", "shortDescription": {"text": "Insecure pattern 'direct_innerhtml_assignment' in video/editor/index.html:365"}, "fullDescription": {"text": "Found a known-risky pattern (direct_innerhtml_assignment). Review and replace if possible."}, "properties": {"scanner": "scanner-primary", "layer": "security", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-81656bbb1e8a5439", "name": "Very large file: src/components/admin/newsletters/NewsletterEditor.tsx (1071 lines)", "shortDescription": {"text": "Very large file: src/components/admin/newsletters/NewsletterEditor.tsx (1071 lines)"}, "fullDescription": {"text": "Files with >800 lines often hide complexity hotspots and discourage tests."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "low", "confidence": 1.0}}, {"id": "scanner-6893a6c8b0861585", "name": "Very low test-to-source ratio", "shortDescription": {"text": "Very low test-to-source ratio"}, "fullDescription": {"text": "8 test file(s) for 247 source file(s) (ratio 0.03). Consider adding integration or unit tests for critical paths."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-141b30a41e03817b", "name": "No license file detected", "shortDescription": {"text": "No license file detected"}, "fullDescription": {"text": "No LICENSE/COPYING/NOTICE file was found. Generated repositories often omit licensing, which blocks reuse and automated intake."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "low", "confidence": 1.0}}, {"id": "scanner-01f96f71d9907a8c", "name": "README lacks setup or run instructions", "shortDescription": {"text": "README lacks setup or run instructions"}, "fullDescription": {"text": "A README exists, but it does not contain common install/setup/run markers. This matches a frequent generated-code pattern: UI is present, operational handoff is thin."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "low", "confidence": 1.0}}, {"id": "scanner-3ab5d313dda8e5f9", "name": "Debug logging residue appears in source files", "shortDescription": {"text": "Debug logging residue appears in source files"}, "fullDescription": {"text": "Found 201 console/debugger/print-style debug statements in non-test source. This is a common fast-generation residue before production cleanup."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "low", "confidence": 1.0}}, {"id": "scanner-72b2a6250083a784", "name": "Placeholder or mock-heavy implementation detected", "shortDescription": {"text": "Placeholder or mock-heavy implementation detected"}, "fullDescription": {"text": "Found 95 placeholder/mock markers across 37 source files. This often means the repo looks complete while core flows still use generated scaffolding or fake data."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-9d79c4077342a7d0", "name": "Runtime service client appears to use placeholder configuration", "shortDescription": {"text": "Runtime service client appears to use placeholder configuration"}, "fullDescription": {"text": "A runtime source file appears to wire Supabase/Firebase/AI/payment-style clients to placeholder URLs, keys, or fallback values. In the Fable corpus this often means the UI/API shape is present while the backend service is not actually configured."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-2d0c7b7ab8f8aacf", "name": "Critical user flow still appears backed by mock or placeholder data", "shortDescription": {"text": "Critical user flow still appears backed by mock or placeholder data"}, "fullDescription": {"text": "A payment/auth/admin/order/billing-style flow contains mock, fake, TODO, dummy, or placeholder markers in runtime source. In the Fable corpus this is a high-leverage completeness smell: the app can look finished while the money, identity, or tenant flow is still scaffolded."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-11825279136b53a3", "name": "CI is configured but no tests are detected", "shortDescription": {"text": "CI is configured but no tests are detected"}, "fullDescription": {"text": "A CI pipeline exists, but the scan found no test files to gate. Opus labeled this generated-code pattern as config theater: release machinery exists, but it has little behavioral signal."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-b9088664ace7f748", "name": "Composite production-readiness gap", "shortDescription": {"text": "Composite production-readiness gap"}, "fullDescription": {"text": "Multiple low-cost hardening controls are missing together: license, tests, operator-readme. Opus verification showed these co-occurring gaps are a better readiness signal than reading each flag in isolation."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-749d4bc1bd66df5f", "name": "Agent instructions exist but release-hardening basics are missing", "shortDescription": {"text": "Agent instructions exist but release-hardening basics are missing"}, "fullDescription": {"text": "AI-coder instruction files were found, but the repo is missing license, tests, operator-readme. Treat this as a contract gap: the agent is guided, but the generated output is not yet guarded by the controls that make it repeatable."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-ea8f3013f588db25", "name": "Shallow git history limits provenance confidence", "shortDescription": {"text": "Shallow git history limits provenance confidence"}, "fullDescription": {"text": "The repository is a shallow clone. Origin/evolution analysis cannot distinguish fresh generation, imported legacy code, or long-lived human code with high confidence."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "low", "confidence": 1.0}}, {"id": "scanner-8424db9c75e04ba4", "name": "Very short observed git history", "shortDescription": {"text": "Very short observed git history"}, "fullDescription": {"text": "The repo has multiple source files but two or fewer visible commits. This is not a failure by itself, but it lowers confidence in evolution-based diagnosis."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "info", "confidence": 1.0}}, {"id": "scanner-e725d2ab884fbd49", "name": "Multiple root agent instruction files without precedence", "shortDescription": {"text": "Multiple root agent instruction files without precedence"}, "fullDescription": {"text": "The repo has multiple top-level AI-coder instruction files. Without precedence rules, different agents may follow different policies."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "low", "confidence": 1.0}}, {"id": "scanner-b2cd03a11bb175c0", "name": "`fetch()` without try/.catch or AbortSignal \u2014 scripts/scrape-google-places.mjs:122", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 scripts/scrape-google-places.mjs:122"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-0f8a471b0ccff6a6", "name": "Commented-code block (7 lines) in scripts/seed-sandrine.mjs:84", "shortDescription": {"text": "Commented-code block (7 lines) in scripts/seed-sandrine.mjs:84"}, "fullDescription": {"text": "A long run of `//` or `#` lines usually means abandoned code. Delete or move to git history. Keeps the canvas + dead-code detection honest."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "info", "confidence": 1.0}}, {"id": "scanner-3a35b3c89e35ba2c", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/save-payment-method-dialog.tsx:42", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/save-payment-method-dialog.tsx:42"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-05e8ecfe2530369e", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/network-graph.tsx:278", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/network-graph.tsx:278"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-fde945aa3463ddfc", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/sign-out-button.tsx:16", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/sign-out-button.tsx:16"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-1d6c7d5123e608cf", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/admin/newsletters/NewsletterEditor.tsx:253", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/admin/newsletters/NewsletterEditor.tsx:253"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-f0442795e9a96c20", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/bug-report/ReportFormDialog.tsx:109", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/bug-report/ReportFormDialog.tsx:109"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-1d357525847f3cb6", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/auth/login/page.tsx:111", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/auth/login/page.tsx:111"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-157682329a54c05a", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/api/auth/verify-code/route.ts:194", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/api/auth/verify-code/route.ts:194"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-afa18034f9cbce1e", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/settings/page.tsx:117", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/settings/page.tsx:117"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-e6734f90ac73cee5", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/recommendations/page.tsx:123", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/recommendations/page.tsx:123"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-84eb1447c70a9f49", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/recommendations/[id]/page.tsx:118", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/recommendations/[id]/page.tsx:118"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-07622773aeed9056", "name": "`fetch()` without try/.catch or AbortSignal \u2014 src/lib/siren.ts:42", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/lib/siren.ts:42"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}, {"id": "scanner-c35938cd7cf1222b", "name": "`fetch()` without try/.catch or AbortSignal \u2014 video/scripts/generate-audio.mjs:83", "shortDescription": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 video/scripts/generate-audio.mjs:83"}, "fullDescription": {"text": "Bare `fetch(...)` will throw an unhandled rejection on network failure. Wrap in try/catch, attach a `.catch(...)`, or pass an AbortSignal with a timeout."}, "properties": {"scanner": "scanner-primary", "layer": "quality", "severity": "medium", "confidence": 1.0}}]}}, "automationDetails": {"id": "repobility/20306"}, "properties": {"repository": "stephmadfx/winelio-app", "repoUrl": "https://github.com/stephmadfx/winelio-app", "branch": "main"}, "results": [{"ruleId": "foundry_blueprint_gap", "level": "warning", "message": {"text": "Foundry mined blueprint gap alignment: stephmadfx/winelio-app"}, "properties": {"repobilityId": 403995, "scanner": "foundry_dataset", "fingerprint": "6de0719dbdb4c53326974a77836868bd5c94edbdde558246d4970e98ca87e5be", "category": "tech_debt", "severity": "medium", "confidence": 0.7, "triageState": "open", "verdict": "needs_review", "isResolved": false, "reason": "Imported from mined Foundry/Fable5 evidence with real GitHub/source provenance. Review source_id before acting.", "evidence": {"meta": {"kind": "graph_query_record", "title": "Human feedback aligned with blueprint or architecture gaps", "intent": "Curriculum-gap examples connecting issue threads to helicopter-view gaps.", "labels": {"bug_fix": 1, "test_or_ci": 1, "test_ci_gap": 1, "partial blueprint fit": 2, "mostly follows blueprint": 1, "claimed_resolved_unverified": 3, "issue_or_pull_request_thread": 1, "blueprint_human_gap_alignment": 2, "blueprint_human_gap_disagreement": 1, "human_reported_issue_then_fix_attempt": 1, "thread_has_human_issue_and_fix_context": 2}, "source": "graph_query_export", "motif_id": "blueprint_gap_alignment", "outcomes": {"claimed_resolved_unverified": 6}, "polarity": "mixed", "query_id": "blueprint_gap_alignment", "severity": "medium", "ci_labels": {}, "synthetic": false, "edge_count": 27, "edge_types": {"repo_has_thread": 1, "comment_has_chain": 1, "thread_has_comment": 1, "thread_touches_file": 1, "alignment_uses_comment": 3, "alignment_uses_finding": 3, "chain_has_link_quality": 6, "comment_aligns_finding": 3, "thread_has_fix_outcome": 1, "thread_has_issue_chain": 1, "issue_chain_touches_file": 1, "thread_has_comment_chain": 1, "comment_chain_links_commit": 1, "comment_chain_touches_file": 1, "issue_chain_has_fix_outcome": 1, "issue_chain_has_comment_chain": 1}, "node_count": 20, "node_types": {"repo": 1, "commit": 1, "thread": 1, "comment": 1, "pr_file": 1, "alignment": 3, "fix_outcome": 1, "issue_chain": 1, "link_quality": 6, "comment_chain": 1, "blueprint_finding": 3}, "query_type": "motif_query", "thread_key": "stephmadfx/winelio-app#2", "issue_number": "2", "quality_tiers": {"assumption_check": 3, "weak_supervision": 3}, "repo_full_name": "stephmadfx/winelio-app", "training_usage": "curriculum_gap", "source_motif_id": "graph-pattern-motif-thread-843200a5e8fe3989", "graph_gold_label": "weak_supervision_needs_review", "changed_file_labels": {"test_or_ci": 4}}, "text": "Graph query export: Human feedback aligned with blueprint or architecture gaps\nQuery id: blueprint_gap_alignment\nQuery type: motif_query\nIntent: Curriculum-gap examples connecting issue threads to helicopter-view gaps.\nMotif: blueprint_gap_alignment\nTraining usage: curriculum_gap\nGraph gold label: weak_supervision_needs_review\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nEvidence:\nGraph motif: Human feedback aligns with blueprint or architecture gaps\nMotif id: blueprint_gap_alignment\nPolarity: mixed\nTraining usage: curriculum_gap\nSeverity: medium\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nGraph gold label: weak_supervision_needs_review\nThread graph evidence:\nGitHub issue/PR evidence subgraph\nThread: stephmadfx/winelio-app#2\nRepo: stephmadfx/winelio-app\nIssue/PR number: 2\nGraph consistency label: weak_supervision_needs_review\nNodes: 20\nEdges: 27\nNode types: {'link_quality': 6, 'alignment': 3, 'blueprint_finding': 3, 'thread': 1, 'repo': 1, 'comment': 1, 'pr_file': 1, 'comment_chain': 1, 'commit': 1, 'issue_chain': 1, 'fix_outcome': 1}\nEdge types: {'chain_has_link_quality': 6, 'alignment_uses_comment': 3, 'alignment_uses_finding': 3, 'comment_aligns_finding': 3, 'repo_has_thread': 1, 'thread_has_comment': 1, 'thread_touches_file': 1, 'thread_has_comment_chain': 1, 'comment_has_chain': 1, 'comment_chain_links_commit': 1, 'comment_chain_touches_file': 1, 'thread_has_issue_chain': 1, 'issue_chain_has_comment_chain': 1, 'issue_chain_touches_file': 1, 'thread_has_fix_outcome': 1, 'issue_chain_has_fix_outcome': 1}\nLabels: {'claimed_resolved_unverified': 3, 'thread_has_human_issue_and_fix_context': 2, 'blueprint_human_gap_alignment': 2, 'partial blueprint fit': 2, 'issue_or_pull_request_thread': 1, 'test_ci_gap': 1, 'test_or_ci': 1, 'human_reported_issue_then_fix_attempt': 1, 'bug_fix': 1, 'blueprint_human_gap_disagreement': 1, 'mostly follows blueprint': 1}\nOutcomes: {'claimed_resolved_unverified': 6}\nQuality tiers: {'weak_supervision': 3, 'assumption_check': 3}\nCI labels: {}\nCurriculum targets:\n- Use helicopter-view architecture/schema/design evidence beside issue threads.\n- Teach models to compare requested product class against implementation layers.\nAssumption checks:\n- Which blueprint layer is absent: frontend, API, data, auth, tests, or deployment?\n- Does human feedback confirm the same architectural gap?", "source": "foundry_mined_dataset", "repo_url": "https://github.com/stephmadfx/winelio-app", "source_id": "graph-query-motif_query-2b1cb6f77634435b", "synthetic": false, "gold_label": "", "graph_label": "", "source_path": "/data/distillate/foundry_data/graph_queries/blueprint_gap_alignment/shard-0.jsonl", "bundle_label": "", "priority_band": "", "priority_score": 0, "repo_full_name": "stephmadfx/winelio-app", "source_dataset": "graph_queries/blueprint_gap_alignment", "training_usage": "curriculum_gap"}}}, {"ruleId": "foundry_blueprint_gap", "level": "warning", "message": {"text": "Foundry mined blueprint gap alignment: stephmadfx/winelio-app"}, "properties": {"repobilityId": 403994, "scanner": "foundry_dataset", "fingerprint": "277cbf2681ccae8e89e0fd99ead63e19449e81953eb298f21c343328c6257704", "category": "tech_debt", "severity": "medium", "confidence": 0.7, "triageState": "open", "verdict": "needs_review", "isResolved": false, "reason": "Imported from mined Foundry/Fable5 evidence with real GitHub/source provenance. Review source_id before acting.", "evidence": {"meta": {"kind": "graph_query_record", "title": "Human feedback aligned with blueprint or architecture gaps", "intent": "Curriculum-gap examples connecting issue threads to helicopter-view gaps.", "labels": {"bug_fix": 4, "test_ci_gap": 1, "partial blueprint fit": 2, "verification_or_tests": 1, "mostly follows blueprint": 1, "issue_or_pull_request_thread": 1, "blueprint_human_gap_alignment": 2, "blueprint_human_gap_disagreement": 1, "thread_has_human_issue_and_fix_context": 2, "claimed_resolved_with_verification_signal": 3, "human_reported_issue_then_verified_fix_attempt": 1}, "source": "graph_query_export", "motif_id": "blueprint_gap_alignment", "outcomes": {"claimed_resolved_with_verification_signal": 6}, "polarity": "mixed", "query_id": "blueprint_gap_alignment", "severity": "medium", "ci_labels": {}, "synthetic": false, "edge_count": 28, "edge_types": {"repo_has_thread": 1, "comment_has_chain": 1, "thread_has_comment": 1, "alignment_uses_comment": 3, "alignment_uses_finding": 3, "chain_has_link_quality": 6, "comment_aligns_finding": 3, "thread_has_fix_outcome": 1, "thread_has_issue_chain": 1, "thread_has_comment_chain": 1, "comment_chain_links_commit": 5, "issue_chain_has_fix_outcome": 1, "issue_chain_has_comment_chain": 1}, "node_count": 23, "node_types": {"repo": 1, "commit": 5, "thread": 1, "comment": 1, "alignment": 3, "fix_outcome": 1, "issue_chain": 1, "link_quality": 6, "comment_chain": 1, "blueprint_finding": 3}, "query_type": "motif_query", "thread_key": "stephmadfx/winelio-app#1", "issue_number": "1", "quality_tiers": {"assumption_check": 3, "weak_supervision": 3}, "repo_full_name": "stephmadfx/winelio-app", "training_usage": "curriculum_gap", "source_motif_id": "graph-pattern-motif-thread-3e93f643372b59c7", "graph_gold_label": "supported_by_verification_signal", "changed_file_labels": {}}, "text": "Graph query export: Human feedback aligned with blueprint or architecture gaps\nQuery id: blueprint_gap_alignment\nQuery type: motif_query\nIntent: Curriculum-gap examples connecting issue threads to helicopter-view gaps.\nMotif: blueprint_gap_alignment\nTraining usage: curriculum_gap\nGraph gold label: supported_by_verification_signal\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#1\nEvidence:\nGraph motif: Human feedback aligns with blueprint or architecture gaps\nMotif id: blueprint_gap_alignment\nPolarity: mixed\nTraining usage: curriculum_gap\nSeverity: medium\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#1\nGraph gold label: supported_by_verification_signal\nThread graph evidence:\nGitHub issue/PR evidence subgraph\nThread: stephmadfx/winelio-app#1\nRepo: stephmadfx/winelio-app\nIssue/PR number: 1\nGraph consistency label: supported_by_verification_signal\nNodes: 23\nEdges: 28\nNode types: {'link_quality': 6, 'commit': 5, 'alignment': 3, 'blueprint_finding': 3, 'thread': 1, 'repo': 1, 'comment': 1, 'comment_chain': 1, 'issue_chain': 1, 'fix_outcome': 1}\nEdge types: {'chain_has_link_quality': 6, 'comment_chain_links_commit': 5, 'alignment_uses_comment': 3, 'alignment_uses_finding': 3, 'comment_aligns_finding': 3, 'repo_has_thread': 1, 'thread_has_comment': 1, 'thread_has_comment_chain': 1, 'comment_has_chain': 1, 'thread_has_issue_chain': 1, 'issue_chain_has_comment_chain': 1, 'thread_has_fix_outcome': 1, 'issue_chain_has_fix_outcome': 1}\nLabels: {'bug_fix': 4, 'claimed_resolved_with_verification_signal': 3, 'thread_has_human_issue_and_fix_context': 2, 'blueprint_human_gap_alignment': 2, 'partial blueprint fit': 2, 'issue_or_pull_request_thread': 1, 'test_ci_gap': 1, 'human_reported_issue_then_verified_fix_attempt': 1, 'verification_or_tests': 1, 'blueprint_human_gap_disagreement': 1, 'mostly follows blueprint': 1}\nOutcomes: {'claimed_resolved_with_verification_signal': 6}\nQuality tiers: {'weak_supervision': 3, 'assumption_check': 3}\nCI labels: {}\nCurriculum targets:\n- Use helicopter-view architecture/schema/design evidence beside issue threads.\n- Teach models to compare requested product class against implementation layers.\nAssumption checks:\n- Which blueprint layer is absent: frontend, API, data, auth, tests, or deployment?\n- Does human feedback confirm the same architectural gap?", "source": "foundry_mined_dataset", "repo_url": "https://github.com/stephmadfx/winelio-app", "source_id": "graph-query-motif_query-d2f35e57085f2a1e", "synthetic": false, "gold_label": "", "graph_label": "", "source_path": "/data/distillate/foundry_data/graph_queries/blueprint_gap_alignment/shard-0.jsonl", "bundle_label": "", "priority_band": "", "priority_score": 0, "repo_full_name": "stephmadfx/winelio-app", "source_dataset": "graph_queries/blueprint_gap_alignment", "training_usage": "curriculum_gap"}}}, {"ruleId": "foundry_assumption_check", "level": "warning", "message": {"text": "Foundry mined assumption checks: stephmadfx/winelio-app"}, "properties": {"repobilityId": 382478, "scanner": "foundry_dataset", "fingerprint": "cc6161ecdd12d77470a14b3cb65f6b17c28bac7d9280b4bcd3cbf47c549bc0a2", "category": "practices", "severity": "medium", "confidence": 0.62, "triageState": "open", "verdict": "needs_review", "isResolved": false, "reason": "Imported from mined Foundry/Fable5 evidence with real GitHub/source provenance. Review source_id before acting.", "evidence": {"meta": {"kind": "comment_chain_pattern_product", "source": "comment_chain_pattern_miner", "product": "assumption_checks", "synthetic": false, "thread_key": "stephmadfx/winelio-app#3", "human_labels": ["agent_instruction_gap", "ui_or_frontend"], "issue_number": "3", "thread_label": "thread_has_human_issue_and_fix_context", "outcome_label": "claimed_resolved_unverified", "source_backed": true, "max_confidence": 0.642, "repo_full_name": "stephmadfx/winelio-app", "training_usage": "weak_supervision", "confidence_tier": "weak_supervision", "source_chain_id": "evidence-chain-issue_chain-245a0dfb9753e5ed", "helicopter_views": {"graphs": 2, "schemas": 2}, "artifact_families": {"ci": 3, "docs": 3, "routes_api": 1, "generated_claims": 1}, "source_chain_kind": "issue_chain", "changed_file_count": 2, "source_graph_label": "source_backed_multi_signal_graph", "changed_file_labels": {"ui_or_frontend": 2}, "linked_commit_count": 5, "helicopter_view_count": 4, "source_artifact_count": 8, "classification_reasons": ["source_graph_has_real_artifacts", "source_graph_has_verification_artifacts", "repo_has_isolated_helicopter_views", "link_quality_weak_supervision"], "linked_ci_commit_count": 0, "verification_artifact_count": 3, "design_schema_api_artifact_count": 1}, "text": "Comment chain pattern product: assumption_checks\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#3\nOutcome: claimed_resolved_unverified\nThread label: thread_has_human_issue_and_fix_context\nSource graph label: source_backed_multi_signal_graph\nReasons: source_graph_has_real_artifacts, source_graph_has_verification_artifacts, repo_has_isolated_helicopter_views, link_quality_weak_supervision\nChain evidence:\nIssue/PR evidence chain: stephmadfx/winelio-app#3\nRepo: stephmadfx/winelio-app\nThread label: thread_has_human_issue_and_fix_context\nOutcome: claimed_resolved_unverified\nComment count: 1\nLinked commit count: 5\nLinked CI commit count: 0\nLinked CI labels: {}\nChanged file count: 2\nLabels: {'agent_instruction_gap': 1}\nPolarities: {'bad': 1}\nChanged file labels: {'ui_or_frontend': 2}\nExamples:\n[\n  {\n    \"id\": \"github-feedback-comment-6a089e92aaeec2eb\",\n    \"kind\": \"pull_request_body\",\n    \"label\": \"agent_instruction_gap\",\n    \"polarity\": \"bad\",\n    \"url\": \"https://github.com/stephmadfx/winelio-app/pull/3\",\n    \"text\": \"GitHub feedback: agent_instruction_gap\\nPolarity: bad\\nKind: pull_request_body\\nRepo: stephmadfx/winelio-app\\nAuthor: stephmadfx (User)\\nURL: https://github.com/stephmadfx/winelio-app/pull/3\\nTitle: feat(onboarding): SIRET obligatoire pour les comptes pro\\nBody:\\n## Summary\\n\\n- Supprime le lien \u00ab Je n'ai pas encore de SIRET \u00bb dans l'\u00e9tape 2 du wizard d'onboarding pro\\n- Rend le champ SIRET obligatoire c\u00f4t\u00e9 client (bouton \u00ab Suivant \u00bb d\u00e9sactiv\u00e9 si vide)\\n- Ajoute une validation serveur dans `completeProOnboarding` : retour d'erreur si SIRET absent\\n- Met \u00e0 jour le label du champ (\u00e9toile obligatoire + message explicatif)\\n\\n## Test plan\\n\\n- [ ] Ouvrir l'onboarding pro \u2192 \u00e9tape 2 \u2192 v\u00e9rifier que le bouton \u00ab Suivant \u00bb est gris\u00e9 sans SIRET\\n- [ ] Saisir un SIRET \u2192 v\u00e9rifier que le bouton s'active\\n- [ ] Tenter de soumettre sans SIRET via les DevTools (supprimer la validation client) \u2192 v\u00e9rifier que le serveur retourne une erreur\\n- [ ] Parcours complet avec SIRET valide \u2192 v\u00e9rifier l'activation du compte pro\\n\\n\ud83e\udd16 Generated with [Claude Code](https://claude.com/claude-code)\"\n  }\n]\nChanged files:\n[\n  {\n    \"id\": \"github-pr-file-file-75f72c49cf911232\",\n    \"filename\": \"src/app/(protected)/profile/actions.ts\",\n    \"label\": \"ui_or_frontend\",\n    \"status\": \"modified\",\n    \"additions\": 4,\n    \"deletions\": 0,\n    \"changes\": 4,\n    \"blob_url\": \"https://github.com/stephmadfx/winelio-app/blob/55b7b35676ac65d10885ebbde04a21fa4ef656b0/src%2Fapp%2F(protected)%2Fprofile%2Factions.ts\"\n  },\n  {\n    \"id\": \"github-pr-file-file-150ad95a03bfdce0\",\n    \"filename\": \"src/components/ProOnboardingWizard.tsx\",\n    \"label\": \"ui_or_frontend\",\n    \"status\": \"modified\",\n    \"additions\": 8,\n    \"deletions\": 20,\n    \"changes\": 28,\n    \"blob_url\": \"https://github.com/stephmadfx/winelio-app/blob/55b7b35676ac65d10885ebbde04a21fa4ef656b0/src%2Fcomponents%2FProOnboardingWizard.tsx\"\n  }\n]\nLinked chain ids:\n[\"evidence-chain-comment_to_commit-7\n[truncated by importer]", "source": "foundry_mined_dataset", "repo_url": "https://github.com/stephmadfx/winelio-app", "source_id": "comment-chain-pattern-assumption_checks-7a085bb2ac8120ef", "synthetic": false, "gold_label": "", "graph_label": "source_backed_multi_signal_graph", "source_path": "/data/distillate/foundry_data/comment_chain_patterns/assumption_checks/shard-0.jsonl", "bundle_label": "", "priority_band": "", "priority_score": 0, "repo_full_name": "stephmadfx/winelio-app", "source_dataset": "comment_chain_patterns/assumption_checks", "training_usage": "weak_supervision"}}}, {"ruleId": "foundry_assumption_check", "level": "warning", "message": {"text": "Foundry mined assumption checks: stephmadfx/winelio-app"}, "properties": {"repobilityId": 382477, "scanner": "foundry_dataset", "fingerprint": "12102d716c42046434e142c4cf992350f42a35070e44bd69493b5f0604ecabeb", "category": "practices", "severity": "medium", "confidence": 0.62, "triageState": "open", "verdict": "needs_review", "isResolved": false, "reason": "Imported from mined Foundry/Fable5 evidence with real GitHub/source provenance. Review source_id before acting.", "evidence": {"meta": {"kind": "comment_chain_pattern_product", "source": "comment_chain_pattern_miner", "product": "assumption_checks", "synthetic": false, "thread_key": "stephmadfx/winelio-app#2", "human_labels": ["test_ci_gap", "test_or_ci"], "issue_number": "2", "thread_label": "thread_has_human_issue_and_fix_context", "outcome_label": "claimed_resolved_unverified", "source_backed": true, "max_confidence": 0.59, "repo_full_name": "stephmadfx/winelio-app", "training_usage": "weak_supervision", "confidence_tier": "weak_supervision", "source_chain_id": "evidence-chain-issue_chain-7e5d90afba6f29d4", "helicopter_views": {"graphs": 2, "schemas": 2}, "artifact_families": {"ci": 3, "docs": 3, "routes_api": 1, "generated_claims": 1}, "source_chain_kind": "issue_chain", "changed_file_count": 1, "source_graph_label": "source_backed_multi_signal_graph", "changed_file_labels": {"test_or_ci": 1}, "linked_commit_count": 1, "helicopter_view_count": 4, "source_artifact_count": 8, "classification_reasons": ["source_graph_has_real_artifacts", "source_graph_has_verification_artifacts", "repo_has_isolated_helicopter_views", "link_quality_weak_supervision", "high_risk_human_feedback_label"], "linked_ci_commit_count": 0, "verification_artifact_count": 3, "design_schema_api_artifact_count": 1}, "text": "Comment chain pattern product: assumption_checks\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nOutcome: claimed_resolved_unverified\nThread label: thread_has_human_issue_and_fix_context\nSource graph label: source_backed_multi_signal_graph\nReasons: source_graph_has_real_artifacts, source_graph_has_verification_artifacts, repo_has_isolated_helicopter_views, link_quality_weak_supervision, high_risk_human_feedback_label\nChain evidence:\nIssue/PR evidence chain: stephmadfx/winelio-app#2\nRepo: stephmadfx/winelio-app\nThread label: thread_has_human_issue_and_fix_context\nOutcome: claimed_resolved_unverified\nComment count: 1\nLinked commit count: 1\nLinked CI commit count: 0\nLinked CI labels: {}\nChanged file count: 1\nLabels: {'test_ci_gap': 1}\nPolarities: {'bad': 1}\nChanged file labels: {'test_or_ci': 1}\nExamples:\n[\n  {\n    \"id\": \"github-feedback-comment-a60151d91fa88cca\",\n    \"kind\": \"pull_request_body\",\n    \"label\": \"test_ci_gap\",\n    \"polarity\": \"bad\",\n    \"url\": \"https://github.com/stephmadfx/winelio-app/pull/2\",\n    \"text\": \"GitHub feedback: test_ci_gap\\nPolarity: bad\\nKind: pull_request_body\\nRepo: stephmadfx/winelio-app\\nAuthor: stephmadfx (User)\\nURL: https://github.com/stephmadfx/winelio-app/pull/2\\nTitle: fix(ci): imap-poll pointe vers la prod (fix 307 staging)\\nBody:\\n## Summary\\n- Le cron GitHub Actions `IMAP Poll \u2014 Bug Replies` \u00e9chouait avec HTTP 307 redirect vers `/staging-login`\\n- `dev2.winelio.app` est prot\u00e9g\u00e9 par Coolify staging login, bloquant la requ\u00eate avant d'atteindre l'API\\n- L'URL du cron pointe maintenant sur `winelio.app` (production)\\n\\n## Test plan\\n- [ ] V\u00e9rifier que le prochain run du workflow retourne HTTP 200\\n- [ ] Confirmer que les emails de failure GitHub s'arr\u00eatent\\n\\n\ud83e\udd16 Generated with [Claude Code](https://claude.com/claude-code)\"\n  }\n]\nChanged files:\n[\n  {\n    \"id\": \"github-pr-file-file-47b02c87144c1f18\",\n    \"filename\": \".github/workflows/imap-poll.yml\",\n    \"label\": \"test_or_ci\",\n    \"status\": \"modified\",\n    \"additions\": 1,\n    \"deletions\": 1,\n    \"changes\": 2,\n    \"blob_url\": \"https://github.com/stephmadfx/winelio-app/blob/d1c8dc2c1259a0badec9d720784444771d5fc73a/.github%2Fworkflows%2Fimap-poll.yml\"\n  }\n]\nLinked chain ids:\n[\"evidence-chain-comment_to_commit-00c162b4eb1551c9\"]\nSource graph evidence:\nSource evidence repo graph summary\nRepo: stephmadfx/winelio-app\nGraph label: source_backed_multi_signal_graph\nNodes: 16\nEdges: 24\nNode types: {\"cooccurrence_profile\": 1, \"github_repo_summary\": 1, \"helicopter_repo_view\": 4, \"repo\": 1, \"source_artifact\": 8, \"source_bundle\": 1}\nEdge types: {\"artifact_needs_claim_verification\": 4, \"artifact_supports_design_schema_api\": 1, \"artifact_supports_verification\": 3, \"repo_has_cooccurrence_profile\": 1, \"repo_has_github_evidence_summary\": 1, \"repo_has_graphs_helicopter_view\": 2, \"repo_has_schemas_helicopter_view\": 2, \"repo_has_source_artifact\": 8, \"repo_has_source_bundle\": 1, \"source_bundle_uses_cooccurrence_profile\": 1}\nArtifact families: {\n[truncated by importer]", "source": "foundry_mined_dataset", "repo_url": "https://github.com/stephmadfx/winelio-app", "source_id": "comment-chain-pattern-assumption_checks-e1f2430001457d98", "synthetic": false, "gold_label": "", "graph_label": "source_backed_multi_signal_graph", "source_path": "/data/distillate/foundry_data/comment_chain_patterns/assumption_checks/shard-0.jsonl", "bundle_label": "", "priority_band": "", "priority_score": 0, "repo_full_name": "stephmadfx/winelio-app", "source_dataset": "comment_chain_patterns/assumption_checks", "training_usage": "weak_supervision"}}}, {"ruleId": "foundry_test_ci_gap", "level": "error", "message": {"text": "Foundry mined test ci gap after feedback: stephmadfx/winelio-app"}, "properties": {"repobilityId": 420210, "scanner": "foundry_dataset", "fingerprint": "126d2bb98711c51bbdd66c6f865948c1a9e0b09199574b4422f46eb3e9b73176", "category": "testing", "severity": "high", "confidence": 0.78, "triageState": "open", "verdict": "confirmed", "isResolved": false, "reason": "Imported from mined Foundry/Fable5 evidence with real GitHub/source provenance. Review source_id before acting.", "evidence": {"meta": {"kind": "graph_query_record", "title": "Feedback exposes missing tests or CI", "intent": "Hard negatives for feedback/fix chains without adequate guardrails.", "labels": {"bug_fix": 1, "test_or_ci": 1, "test_ci_gap": 1, "partial blueprint fit": 2, "mostly follows blueprint": 1, "claimed_resolved_unverified": 3, "issue_or_pull_request_thread": 1, "blueprint_human_gap_alignment": 2, "blueprint_human_gap_disagreement": 1, "human_reported_issue_then_fix_attempt": 1, "thread_has_human_issue_and_fix_context": 2}, "source": "graph_query_export", "motif_id": "test_ci_gap_after_feedback", "outcomes": {"claimed_resolved_unverified": 6}, "polarity": "bad", "query_id": "test_ci_gap_after_feedback", "severity": "high", "ci_labels": {}, "synthetic": false, "edge_count": 27, "edge_types": {"repo_has_thread": 1, "comment_has_chain": 1, "thread_has_comment": 1, "thread_touches_file": 1, "alignment_uses_comment": 3, "alignment_uses_finding": 3, "chain_has_link_quality": 6, "comment_aligns_finding": 3, "thread_has_fix_outcome": 1, "thread_has_issue_chain": 1, "issue_chain_touches_file": 1, "thread_has_comment_chain": 1, "comment_chain_links_commit": 1, "comment_chain_touches_file": 1, "issue_chain_has_fix_outcome": 1, "issue_chain_has_comment_chain": 1}, "node_count": 20, "node_types": {"repo": 1, "commit": 1, "thread": 1, "comment": 1, "pr_file": 1, "alignment": 3, "fix_outcome": 1, "issue_chain": 1, "link_quality": 6, "comment_chain": 1, "blueprint_finding": 3}, "query_type": "motif_query", "thread_key": "stephmadfx/winelio-app#2", "issue_number": "2", "quality_tiers": {"assumption_check": 3, "weak_supervision": 3}, "repo_full_name": "stephmadfx/winelio-app", "training_usage": "hard_negative", "source_motif_id": "graph-pattern-motif-thread-c1812d13c3d69d3d", "graph_gold_label": "weak_supervision_needs_review", "changed_file_labels": {"test_or_ci": 4}}, "text": "Graph query export: Feedback exposes missing tests or CI\nQuery id: test_ci_gap_after_feedback\nQuery type: motif_query\nIntent: Hard negatives for feedback/fix chains without adequate guardrails.\nMotif: test_ci_gap_after_feedback\nTraining usage: hard_negative\nGraph gold label: weak_supervision_needs_review\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nEvidence:\nGraph motif: Feedback or fix context exposes missing test/CI guardrails\nMotif id: test_ci_gap_after_feedback\nPolarity: bad\nTraining usage: hard_negative\nSeverity: high\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#2\nGraph gold label: weak_supervision_needs_review\nThread graph evidence:\nGitHub issue/PR evidence subgraph\nThread: stephmadfx/winelio-app#2\nRepo: stephmadfx/winelio-app\nIssue/PR number: 2\nGraph consistency label: weak_supervision_needs_review\nNodes: 20\nEdges: 27\nNode types: {'link_quality': 6, 'alignment': 3, 'blueprint_finding': 3, 'thread': 1, 'repo': 1, 'comment': 1, 'pr_file': 1, 'comment_chain': 1, 'commit': 1, 'issue_chain': 1, 'fix_outcome': 1}\nEdge types: {'chain_has_link_quality': 6, 'alignment_uses_comment': 3, 'alignment_uses_finding': 3, 'comment_aligns_finding': 3, 'repo_has_thread': 1, 'thread_has_comment': 1, 'thread_touches_file': 1, 'thread_has_comment_chain': 1, 'comment_has_chain': 1, 'comment_chain_links_commit': 1, 'comment_chain_touches_file': 1, 'thread_has_issue_chain': 1, 'issue_chain_has_comment_chain': 1, 'issue_chain_touches_file': 1, 'thread_has_fix_outcome': 1, 'issue_chain_has_fix_outcome': 1}\nLabels: {'claimed_resolved_unverified': 3, 'thread_has_human_issue_and_fix_context': 2, 'blueprint_human_gap_alignment': 2, 'partial blueprint fit': 2, 'issue_or_pull_request_thread': 1, 'test_ci_gap': 1, 'test_or_ci': 1, 'human_reported_issue_then_fix_attempt': 1, 'bug_fix': 1, 'blueprint_human_gap_disagreement': 1, 'mostly follows blueprint': 1}\nOutcomes: {'claimed_resolved_unverified': 6}\nQuality tiers: {'weak_supervision': 3, 'assumption_check': 3}\nCI labels: {}\nCurriculum targets:\n- Turn human feedback into regression tests and CI gates.\n- Penalize fixes that do not add or exercise verification for affected workflows.\nAssumption checks:\n- Did the fix add tests for the exact complaint?\n- Does CI run those tests, or is verification only implied?", "source": "foundry_mined_dataset", "repo_url": "https://github.com/stephmadfx/winelio-app", "source_id": "graph-query-motif_query-1878503f9fa786f4", "synthetic": false, "gold_label": "", "graph_label": "", "source_path": "/data/distillate/foundry_data/graph_queries/test_ci_gap_after_feedback/shard-0.jsonl", "bundle_label": "", "priority_band": "", "priority_score": 0, "repo_full_name": "stephmadfx/winelio-app", "source_dataset": "graph_queries/test_ci_gap_after_feedback", "training_usage": "hard_negative"}}}, {"ruleId": "foundry_test_ci_gap", "level": "error", "message": {"text": "Foundry mined test ci gap after feedback: stephmadfx/winelio-app"}, "properties": {"repobilityId": 420209, "scanner": "foundry_dataset", "fingerprint": "a5c0acee15079e1b1fa3085f4315de5126ba2d96b2b1c37dc8e82cf61afa9f8e", "category": "testing", "severity": "high", "confidence": 0.78, "triageState": "open", "verdict": "confirmed", "isResolved": false, "reason": "Imported from mined Foundry/Fable5 evidence with real GitHub/source provenance. Review source_id before acting.", "evidence": {"meta": {"kind": "graph_query_record", "title": "Feedback exposes missing tests or CI", "intent": "Hard negatives for feedback/fix chains without adequate guardrails.", "labels": {"bug_fix": 4, "test_ci_gap": 1, "partial blueprint fit": 2, "verification_or_tests": 1, "mostly follows blueprint": 1, "issue_or_pull_request_thread": 1, "blueprint_human_gap_alignment": 2, "blueprint_human_gap_disagreement": 1, "thread_has_human_issue_and_fix_context": 2, "claimed_resolved_with_verification_signal": 3, "human_reported_issue_then_verified_fix_attempt": 1}, "source": "graph_query_export", "motif_id": "test_ci_gap_after_feedback", "outcomes": {"claimed_resolved_with_verification_signal": 6}, "polarity": "bad", "query_id": "test_ci_gap_after_feedback", "severity": "high", "ci_labels": {}, "synthetic": false, "edge_count": 28, "edge_types": {"repo_has_thread": 1, "comment_has_chain": 1, "thread_has_comment": 1, "alignment_uses_comment": 3, "alignment_uses_finding": 3, "chain_has_link_quality": 6, "comment_aligns_finding": 3, "thread_has_fix_outcome": 1, "thread_has_issue_chain": 1, "thread_has_comment_chain": 1, "comment_chain_links_commit": 5, "issue_chain_has_fix_outcome": 1, "issue_chain_has_comment_chain": 1}, "node_count": 23, "node_types": {"repo": 1, "commit": 5, "thread": 1, "comment": 1, "alignment": 3, "fix_outcome": 1, "issue_chain": 1, "link_quality": 6, "comment_chain": 1, "blueprint_finding": 3}, "query_type": "motif_query", "thread_key": "stephmadfx/winelio-app#1", "issue_number": "1", "quality_tiers": {"assumption_check": 3, "weak_supervision": 3}, "repo_full_name": "stephmadfx/winelio-app", "training_usage": "hard_negative", "source_motif_id": "graph-pattern-motif-thread-c35ddcbe1e1aeeec", "graph_gold_label": "supported_by_verification_signal", "changed_file_labels": {}}, "text": "Graph query export: Feedback exposes missing tests or CI\nQuery id: test_ci_gap_after_feedback\nQuery type: motif_query\nIntent: Hard negatives for feedback/fix chains without adequate guardrails.\nMotif: test_ci_gap_after_feedback\nTraining usage: hard_negative\nGraph gold label: supported_by_verification_signal\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#1\nEvidence:\nGraph motif: Feedback or fix context exposes missing test/CI guardrails\nMotif id: test_ci_gap_after_feedback\nPolarity: bad\nTraining usage: hard_negative\nSeverity: high\nRepo: stephmadfx/winelio-app\nThread: stephmadfx/winelio-app#1\nGraph gold label: supported_by_verification_signal\nThread graph evidence:\nGitHub issue/PR evidence subgraph\nThread: stephmadfx/winelio-app#1\nRepo: stephmadfx/winelio-app\nIssue/PR number: 1\nGraph consistency label: supported_by_verification_signal\nNodes: 23\nEdges: 28\nNode types: {'link_quality': 6, 'commit': 5, 'alignment': 3, 'blueprint_finding': 3, 'thread': 1, 'repo': 1, 'comment': 1, 'comment_chain': 1, 'issue_chain': 1, 'fix_outcome': 1}\nEdge types: {'chain_has_link_quality': 6, 'comment_chain_links_commit': 5, 'alignment_uses_comment': 3, 'alignment_uses_finding': 3, 'comment_aligns_finding': 3, 'repo_has_thread': 1, 'thread_has_comment': 1, 'thread_has_comment_chain': 1, 'comment_has_chain': 1, 'thread_has_issue_chain': 1, 'issue_chain_has_comment_chain': 1, 'thread_has_fix_outcome': 1, 'issue_chain_has_fix_outcome': 1}\nLabels: {'bug_fix': 4, 'claimed_resolved_with_verification_signal': 3, 'thread_has_human_issue_and_fix_context': 2, 'blueprint_human_gap_alignment': 2, 'partial blueprint fit': 2, 'issue_or_pull_request_thread': 1, 'test_ci_gap': 1, 'human_reported_issue_then_verified_fix_attempt': 1, 'verification_or_tests': 1, 'blueprint_human_gap_disagreement': 1, 'mostly follows blueprint': 1}\nOutcomes: {'claimed_resolved_with_verification_signal': 6}\nQuality tiers: {'weak_supervision': 3, 'assumption_check': 3}\nCI labels: {}\nCurriculum targets:\n- Turn human feedback into regression tests and CI gates.\n- Penalize fixes that do not add or exercise verification for affected workflows.\nAssumption checks:\n- Did the fix add tests for the exact complaint?\n- Does CI run those tests, or is verification only implied?", "source": "foundry_mined_dataset", "repo_url": "https://github.com/stephmadfx/winelio-app", "source_id": "graph-query-motif_query-4eabde60bc4a06e5", "synthetic": false, "gold_label": "", "graph_label": "", "source_path": "/data/distillate/foundry_data/graph_queries/test_ci_gap_after_feedback/shard-0.jsonl", "bundle_label": "", "priority_band": "", "priority_score": 0, "repo_full_name": "stephmadfx/winelio-app", "source_dataset": "graph_queries/test_ci_gap_after_feedback", "training_usage": "hard_negative"}}}, {"ruleId": "scanner-bead75b0f9233e05", "level": "none", "message": {"text": "No API endpoints detected"}, "properties": {"repobilityId": "0f8bb852027c38f8", "scanner": "scanner-primary", "fingerprint": "bead75b0f9233e05", "layer": "api", "severity": "info", "confidence": 1.0, "tags": ["coverage"]}}, {"ruleId": "scanner-35296945768b36b1", "level": "note", "message": {"text": "Stray `console.log` in TS/JS \u2014 scripts/backfill-aliases.ts:34"}, "properties": {"repobilityId": "5f25294dd8e03c03", "scanner": "scanner-primary", "fingerprint": "35296945768b36b1", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.console-leak"]}}, {"ruleId": "scanner-5818ab701c52ba47", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/network-tree.tsx:307"}, "properties": {"repobilityId": "9d84241589c9e1a4", "scanner": "scanner-primary", "fingerprint": "5818ab701c52ba47", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-09e3e4c1d363c8b6", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/sidebar.tsx:113"}, "properties": {"repobilityId": "b6d9ddc60e182673", "scanner": "scanner-primary", "fingerprint": "09e3e4c1d363c8b6", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-66ab2d7ed064fc13", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/mobile-header.tsx:193"}, "properties": {"repobilityId": "50cc1edb0dea52b8", "scanner": "scanner-primary", "fingerprint": "66ab2d7ed064fc13", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-6903050badd15d9d", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/referral-buttons.tsx:297"}, "properties": {"repobilityId": "aeea68229a8a8f5e", "scanner": "scanner-primary", "fingerprint": "6903050badd15d9d", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-59632fc10be90214", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/activity-feed.tsx:339"}, "properties": {"repobilityId": "a28154a651399e7f", "scanner": "scanner-primary", "fingerprint": "59632fc10be90214", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-2a81f744addc7115", "level": "note", "message": {"text": "Icon-only button without accessible name \u2014 src/components/DemoSeedBanner.tsx:52"}, "properties": {"repobilityId": "0a5eb43a67728187", "scanner": "scanner-primary", "fingerprint": "2a81f744addc7115", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.button.no-label"]}}, {"ruleId": "scanner-6dd79222e356d281", "level": "note", "message": {"text": "Icon-only button without accessible name \u2014 src/components/network-graph.tsx:373"}, "properties": {"repobilityId": "dc2d8c3f219b3c01", "scanner": "scanner-primary", "fingerprint": "6dd79222e356d281", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.button.no-label"]}}, {"ruleId": "scanner-65570d4f2f05faa9", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/network-graph.tsx:523"}, "properties": {"repobilityId": "425b2e9d3cf2d28f", "scanner": "scanner-primary", "fingerprint": "65570d4f2f05faa9", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-0a48e75d45cd7fc6", "level": "warning", "message": {"text": "`dangerouslySetInnerHTML` used in a React component \u2014 src/components/ui/chart.tsx:95"}, "properties": {"repobilityId": "b8c68f17a4018107", "scanner": "scanner-primary", "fingerprint": "0a48e75d45cd7fc6", "layer": "frontend", "severity": "medium", "confidence": 1.0, "tags": ["frontend-quality", "fq.dangerous-html"]}}, {"ruleId": "scanner-3bc229fe2573b354", "level": "note", "message": {"text": "Icon-only button without accessible name \u2014 src/components/admin/EmailPreviewDialog.tsx:59"}, "properties": {"repobilityId": "0123176178004666", "scanner": "scanner-primary", "fingerprint": "3bc229fe2573b354", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.button.no-label"]}}, {"ruleId": "scanner-50bab95a58dc1fea", "level": "note", "message": {"text": "React Flow <MiniMap> without dark background \u2014 src/components/admin/NetworkTree.tsx:780"}, "properties": {"repobilityId": "9a84b5789f2db9c4", "scanner": "scanner-primary", "fingerprint": "50bab95a58dc1fea", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.minimap.no-bg"]}}, {"ruleId": "scanner-116e6d62d10be77e", "level": "note", "message": {"text": "React Flow <Controls> without dark theming \u2014 src/components/admin/NetworkTree.tsx:779"}, "properties": {"repobilityId": "983e2095f54efde7", "scanner": "scanner-primary", "fingerprint": "116e6d62d10be77e", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.controls.no-bg"]}}, {"ruleId": "scanner-921ed6b1bcf7b072", "level": "note", "message": {"text": "Icon-only button without accessible name \u2014 src/components/admin/NetworkTree.tsx:271"}, "properties": {"repobilityId": "9585d94cd2936b52", "scanner": "scanner-primary", "fingerprint": "921ed6b1bcf7b072", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.button.no-label"]}}, {"ruleId": "scanner-b4b51fe68c6d74f5", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/AdminLayoutShell.tsx:118"}, "properties": {"repobilityId": "00f5565ef67b1443", "scanner": "scanner-primary", "fingerprint": "b4b51fe68c6d74f5", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-7f3890a40f608867", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/AnnotationPanel.tsx:74"}, "properties": {"repobilityId": "6ad888b3622d3941", "scanner": "scanner-primary", "fingerprint": "7f3890a40f608867", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-dd440b67e1512526", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/BugTrackerBoard.tsx:376"}, "properties": {"repobilityId": "6b4df06ece3764f7", "scanner": "scanner-primary", "fingerprint": "dd440b67e1512526", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-2126861a4cc28a0d", "level": "note", "message": {"text": "Icon-only button without accessible name \u2014 src/components/admin/ProfessionnelsTable.tsx:191"}, "properties": {"repobilityId": "fe1b8b352ed870c4", "scanner": "scanner-primary", "fingerprint": "2126861a4cc28a0d", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.button.no-label"]}}, {"ruleId": "scanner-d8fc0ffa888f1aa1", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/ProfessionnelsTable.tsx:254"}, "properties": {"repobilityId": "6d2af5adb13ab8a2", "scanner": "scanner-primary", "fingerprint": "d8fc0ffa888f1aa1", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-6c236c9cd3cd040f", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/newsletters/NewsletterPreviewDialog.tsx:32"}, "properties": {"repobilityId": "4009392446dc2e12", "scanner": "scanner-primary", "fingerprint": "6c236c9cd3cd040f", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-c8d7c8838de691a3", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/components/admin/newsletters/NewsletterEditor.tsx:1033"}, "properties": {"repobilityId": "35f2cca33994bb44", "scanner": "scanner-primary", "fingerprint": "c8d7c8838de691a3", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-d393813b163d03e7", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/utilisateurs/page.tsx:204"}, "properties": {"repobilityId": "043156265545329c", "scanner": "scanner-primary", "fingerprint": "d393813b163d03e7", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-427102a75d433ed7", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/utilisateurs/[id]/page.tsx:154"}, "properties": {"repobilityId": "91a5b240962ff8cd", "scanner": "scanner-primary", "fingerprint": "427102a75d433ed7", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-0a4fac9df170449b", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/recommandations/page.tsx:127"}, "properties": {"repobilityId": "ba1ddd7596913756", "scanner": "scanner-primary", "fingerprint": "0a4fac9df170449b", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-dfe1c2b4a1a86628", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/reseau/AdminNetworkContent.tsx:169"}, "properties": {"repobilityId": "b09b635c43d49629", "scanner": "scanner-primary", "fingerprint": "dfe1c2b4a1a86628", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-6e1904901b72dc0e", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/newsletters/page.tsx:53"}, "properties": {"repobilityId": "e7679c0804b77924", "scanner": "scanner-primary", "fingerprint": "6e1904901b72dc0e", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-f66f50e7fc1956ed", "level": "note", "message": {"text": "Icon-only button without accessible name \u2014 src/app/gestion-reseau/retraits/page.tsx:127"}, "properties": {"repobilityId": "a8b83ff7fe118610", "scanner": "scanner-primary", "fingerprint": "f66f50e7fc1956ed", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.button.no-label"]}}, {"ruleId": "scanner-877b171bcd483cc6", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/gestion-reseau/retraits/page.tsx:77"}, "properties": {"repobilityId": "9670155fd0c372a3", "scanner": "scanner-primary", "fingerprint": "877b171bcd483cc6", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-af5dabf162f04670", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/page.tsx:341"}, "properties": {"repobilityId": "213e4372b1f099a0", "scanner": "scanner-primary", "fingerprint": "af5dabf162f04670", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-b474ecf182750061", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/new/StepContact.tsx:123"}, "properties": {"repobilityId": "cc258c77fbeb20c4", "scanner": "scanner-primary", "fingerprint": "b474ecf182750061", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-b9122a9c44f5cbce", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/recommendations/[id]/page.tsx:294"}, "properties": {"repobilityId": "b139bcb07a493624", "scanner": "scanner-primary", "fingerprint": "b9122a9c44f5cbce", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-f772d96ba83369d3", "level": "none", "message": {"text": "`truncate` class without `title=` for hover reveal \u2014 src/app/(protected)/network/page.tsx:147"}, "properties": {"repobilityId": "b7f7227444364db7", "scanner": "scanner-primary", "fingerprint": "f772d96ba83369d3", "layer": "frontend", "severity": "info", "confidence": 1.0, "tags": ["frontend-quality", "fq.truncate.no-title"]}}, {"ruleId": "scanner-a90108750906049f", "level": "note", "message": {"text": "Stray `console.log` in TS/JS \u2014 src/app/(protected)/test-recommendation/page.tsx:27"}, "properties": {"repobilityId": "82c199d0cf069651", "scanner": "scanner-primary", "fingerprint": "a90108750906049f", "layer": "frontend", "severity": "low", "confidence": 1.0, "tags": ["frontend-quality", "fq.console-leak"]}}, {"ruleId": "scanner-c7e254d4ccddc63c", "level": "warning", "message": {"text": "Privileged port 195 in use"}, "properties": {"repobilityId": "3a4a58b5c45bd831", "scanner": "scanner-primary", "fingerprint": "c7e254d4ccddc63c", "layer": "network", "severity": "medium", "confidence": 1.0, "tags": ["security", "ports"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": ".github/workflows/deploy-dev2.yml"}, "region": {"startLine": 1}}}]}, {"ruleId": "scanner-f2c6d165af64636e", "level": "note", "message": {"text": "Docker base image is tag-pinned but not digest-pinned: node:22.22.2-alpine"}, "properties": {"repobilityId": "0ec548cf6b38b46e", "scanner": "scanner-primary", "fingerprint": "f2c6d165af64636e", "layer": "hardware", "severity": "low", "confidence": 1.0, "tags": ["supply-chain", "docker", "pinned-dependencies"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": "Dockerfile"}, "region": {"startLine": 1}}}]}, {"ruleId": "scanner-aa5acaa49eb8315b", "level": "note", "message": {"text": "Containers defined but no K8s/orchestration manifest found"}, "properties": {"repobilityId": "b230ea9b68736081", "scanner": "scanner-primary", "fingerprint": "aa5acaa49eb8315b", "layer": "hardware", "severity": "low", "confidence": 1.0, "tags": ["coverage", "deployment"]}}, {"ruleId": "scanner-a22d2ac060c1bbb9", "level": "error", "message": {"text": "Possible secret in tmp-test-login.cjs"}, "properties": {"repobilityId": "3d9f8100a8594116", "scanner": "scanner-primary", "fingerprint": "a22d2ac060c1bbb9", "layer": "security", "severity": "critical", "confidence": 1.0, "tags": ["secrets"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": "tmp-test-login.cjs"}, "region": {"startLine": 4}}}]}, {"ruleId": "scanner-f36756e4816e3f59", "level": "warning", "message": {"text": "Insecure pattern 'dangerous_innerhtml' in src/components/ui/chart.tsx:95"}, "properties": {"repobilityId": "33f10636e53b4298", "scanner": "scanner-primary", "fingerprint": "f36756e4816e3f59", "layer": "security", "severity": "medium", "confidence": 1.0, "tags": ["owasp", "dangerous_innerhtml"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": "src/components/ui/chart.tsx"}, "region": {"startLine": 95}}}]}, {"ruleId": "scanner-43362c89c1299779", "level": "warning", "message": {"text": "Insecure pattern 'node_child_process' in src/lib/generate-signed-pdf.ts:2"}, "properties": {"repobilityId": "a4b9ed079cf3ed42", "scanner": "scanner-primary", "fingerprint": "43362c89c1299779", "layer": "security", "severity": "medium", "confidence": 1.0, "tags": ["owasp", "node_child_process"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": "src/lib/generate-signed-pdf.ts"}, "region": {"startLine": 2}}}]}, {"ruleId": "scanner-84a3022c0c33da03", "level": "warning", "message": {"text": "Insecure pattern 'node_child_process' in video/scripts/generate-audio.mjs:10"}, "properties": {"repobilityId": "bcb74bb44a1662e6", "scanner": "scanner-primary", "fingerprint": "84a3022c0c33da03", "layer": "security", "severity": "medium", "confidence": 1.0, "tags": ["owasp", "node_child_process"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": "video/scripts/generate-audio.mjs"}, "region": {"startLine": 10}}}]}, {"ruleId": "scanner-f7fa3da12bd977cb", "level": "warning", "message": {"text": "Insecure pattern 'node_child_process' in video/editor/server.mjs:5"}, "properties": {"repobilityId": "a1ee2575393da2e7", "scanner": "scanner-primary", "fingerprint": "f7fa3da12bd977cb", "layer": "security", "severity": "medium", "confidence": 1.0, "tags": ["owasp", "node_child_process"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": "video/editor/server.mjs"}, "region": {"startLine": 5}}}]}, {"ruleId": "scanner-67ef737a6c5314f1", "level": "warning", "message": {"text": "Insecure pattern 'cors_wildcard' in video/editor/server.mjs:49"}, "properties": {"repobilityId": "d6be6c26620bb16c", "scanner": "scanner-primary", "fingerprint": "67ef737a6c5314f1", "layer": "security", "severity": "medium", "confidence": 1.0, "tags": ["owasp", "cors_wildcard"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": "video/editor/server.mjs"}, "region": {"startLine": 49}}}]}, {"ruleId": "scanner-908d126fb67d173a", "level": "warning", "message": {"text": "Insecure pattern 'direct_innerhtml_assignment' in video/editor/index.html:365"}, "properties": {"repobilityId": "ce8ee66cab3dc827", "scanner": "scanner-primary", "fingerprint": "908d126fb67d173a", "layer": "security", "severity": "medium", "confidence": 1.0, "tags": ["owasp", "direct_innerhtml_assignment"]}, "locations": [{"physicalLocation": {"artifactLocation": {"uri": "video/editor/index.html"}, "region": {"startLine": 365}}}]}, {"ruleId": "scanner-81656bbb1e8a5439", "level": "note", "message": {"text": "Very large file: src/components/admin/newsletters/NewsletterEditor.tsx (1071 lines)"}, "properties": {"repobilityId": "f49fa7567e3e8a97", "scanner": "scanner-primary", "fingerprint": "81656bbb1e8a5439", "layer": "quality", "severity": "low", "confidence": 1.0, "tags": ["complexity"]}}, {"ruleId": "scanner-6893a6c8b0861585", "level": "warning", "message": {"text": "Very low test-to-source ratio"}, "properties": {"repobilityId": "54a7de3f06314bf0", "scanner": "scanner-primary", "fingerprint": "6893a6c8b0861585", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["tests", "coverage"]}}, {"ruleId": "scanner-141b30a41e03817b", "level": "note", "message": {"text": "No license file detected"}, "properties": {"repobilityId": "01dc6c2be308fadd", "scanner": "scanner-primary", "fingerprint": "141b30a41e03817b", "layer": "quality", "severity": "low", "confidence": 1.0, "tags": ["license", "repo-hardening", "generated-repo-pattern"]}}, {"ruleId": "scanner-01f96f71d9907a8c", "level": "note", "message": {"text": "README lacks setup or run instructions"}, "properties": {"repobilityId": "e793bae4481a1f97", "scanner": "scanner-primary", "fingerprint": "01f96f71d9907a8c", "layer": "quality", "severity": "low", "confidence": 1.0, "tags": ["docs", "readme", "repo-hardening", "generated-repo-pattern"]}}, {"ruleId": "scanner-3ab5d313dda8e5f9", "level": "note", "message": {"text": "Debug logging residue appears in source files"}, "properties": {"repobilityId": "7874351221bd9967", "scanner": "scanner-primary", "fingerprint": "3ab5d313dda8e5f9", "layer": "quality", "severity": "low", "confidence": 1.0, "tags": ["debug", "cleanup", "repo-hardening", "generated-repo-pattern"]}}, {"ruleId": "scanner-72b2a6250083a784", "level": "warning", "message": {"text": "Placeholder or mock-heavy implementation detected"}, "properties": {"repobilityId": "93cd666c452b0c83", "scanner": "scanner-primary", "fingerprint": "72b2a6250083a784", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["placeholder", "mock-data", "incomplete", "generated-repo-pattern"]}}, {"ruleId": "scanner-9d79c4077342a7d0", "level": "warning", "message": {"text": "Runtime service client appears to use placeholder configuration"}, "properties": {"repobilityId": "a79fdeeed54eb201", "scanner": "scanner-primary", "fingerprint": "9d79c4077342a7d0", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["placeholder", "runtime-config", "service-client", "generated-repo-pattern"]}}, {"ruleId": "scanner-2d0c7b7ab8f8aacf", "level": "warning", "message": {"text": "Critical user flow still appears backed by mock or placeholder data"}, "properties": {"repobilityId": "c02d48ff83a967c8", "scanner": "scanner-primary", "fingerprint": "2d0c7b7ab8f8aacf", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["placeholder", "mock-data", "critical-flow", "generated-repo-pattern"]}}, {"ruleId": "scanner-11825279136b53a3", "level": "warning", "message": {"text": "CI is configured but no tests are detected"}, "properties": {"repobilityId": "6f8d47ee878d3bd6", "scanner": "scanner-primary", "fingerprint": "11825279136b53a3", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["tests", "ci", "config-theater", "repo-hardening", "generated-repo-pattern"]}}, {"ruleId": "scanner-b9088664ace7f748", "level": "warning", "message": {"text": "Composite production-readiness gap"}, "properties": {"repobilityId": "c250e44b447b1b45", "scanner": "scanner-primary", "fingerprint": "b9088664ace7f748", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["production-readiness", "repo-hardening", "generated-repo-pattern"]}}, {"ruleId": "scanner-749d4bc1bd66df5f", "level": "warning", "message": {"text": "Agent instructions exist but release-hardening basics are missing"}, "properties": {"repobilityId": "ac974ecc4ac6f774", "scanner": "scanner-primary", "fingerprint": "749d4bc1bd66df5f", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["agent-instructions", "repo-hardening", "generated-repo-pattern"]}}, {"ruleId": "scanner-ea8f3013f588db25", "level": "note", "message": {"text": "Shallow git history limits provenance confidence"}, "properties": {"repobilityId": "280f75da68017413", "scanner": "scanner-primary", "fingerprint": "ea8f3013f588db25", "layer": "quality", "severity": "low", "confidence": 1.0, "tags": ["provenance", "git-history", "generated-repo-pattern"]}}, {"ruleId": "scanner-8424db9c75e04ba4", "level": "none", "message": {"text": "Very short observed git history"}, "properties": {"repobilityId": "c3b00ee35500b862", "scanner": "scanner-primary", "fingerprint": "8424db9c75e04ba4", "layer": "quality", "severity": "info", "confidence": 1.0, "tags": ["provenance", "git-history", "generated-repo-pattern"]}}, {"ruleId": "scanner-e725d2ab884fbd49", "level": "note", "message": {"text": "Multiple root agent instruction files without precedence"}, "properties": {"repobilityId": "1953db6c89508d22", "scanner": "scanner-primary", "fingerprint": "e725d2ab884fbd49", "layer": "quality", "severity": "low", "confidence": 1.0, "tags": ["agent-instructions", "governance"]}}, {"ruleId": "scanner-b2cd03a11bb175c0", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 scripts/scrape-google-places.mjs:122"}, "properties": {"repobilityId": "a305f9f38f45bb9d", "scanner": "scanner-primary", "fingerprint": "b2cd03a11bb175c0", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-0f8a471b0ccff6a6", "level": "none", "message": {"text": "Commented-code block (7 lines) in scripts/seed-sandrine.mjs:84"}, "properties": {"repobilityId": "f5ac652ea5e5f51f", "scanner": "scanner-primary", "fingerprint": "0f8a471b0ccff6a6", "layer": "quality", "severity": "info", "confidence": 1.0, "tags": ["integrity", "commented-code", "dead-code"]}}, {"ruleId": "scanner-3a35b3c89e35ba2c", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/save-payment-method-dialog.tsx:42"}, "properties": {"repobilityId": "d6587980baaa5d36", "scanner": "scanner-primary", "fingerprint": "3a35b3c89e35ba2c", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-05e8ecfe2530369e", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/network-graph.tsx:278"}, "properties": {"repobilityId": "721b886462d821a3", "scanner": "scanner-primary", "fingerprint": "05e8ecfe2530369e", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-fde945aa3463ddfc", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/sign-out-button.tsx:16"}, "properties": {"repobilityId": "785eed1a720c5361", "scanner": "scanner-primary", "fingerprint": "fde945aa3463ddfc", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-1d6c7d5123e608cf", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/admin/newsletters/NewsletterEditor.tsx:253"}, "properties": {"repobilityId": "f1b0e16036adb208", "scanner": "scanner-primary", "fingerprint": "1d6c7d5123e608cf", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-f0442795e9a96c20", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/components/bug-report/ReportFormDialog.tsx:109"}, "properties": {"repobilityId": "c0507e273b3a2896", "scanner": "scanner-primary", "fingerprint": "f0442795e9a96c20", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-1d357525847f3cb6", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/auth/login/page.tsx:111"}, "properties": {"repobilityId": "9b4f854048568d44", "scanner": "scanner-primary", "fingerprint": "1d357525847f3cb6", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-157682329a54c05a", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/api/auth/verify-code/route.ts:194"}, "properties": {"repobilityId": "319dc4dfac840ba8", "scanner": "scanner-primary", "fingerprint": "157682329a54c05a", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-afa18034f9cbce1e", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/settings/page.tsx:117"}, "properties": {"repobilityId": "4ed4dd7efdc51622", "scanner": "scanner-primary", "fingerprint": "afa18034f9cbce1e", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-e6734f90ac73cee5", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/recommendations/page.tsx:123"}, "properties": {"repobilityId": "7d6c5d44cd1072ee", "scanner": "scanner-primary", "fingerprint": "e6734f90ac73cee5", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-84eb1447c70a9f49", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/app/(protected)/recommendations/[id]/page.tsx:118"}, "properties": {"repobilityId": "6afc7a7c73357a39", "scanner": "scanner-primary", "fingerprint": "84eb1447c70a9f49", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-07622773aeed9056", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 src/lib/siren.ts:42"}, "properties": {"repobilityId": "867bc3e7b2e94371", "scanner": "scanner-primary", "fingerprint": "07622773aeed9056", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}, {"ruleId": "scanner-c35938cd7cf1222b", "level": "warning", "message": {"text": "`fetch()` without try/.catch or AbortSignal \u2014 video/scripts/generate-audio.mjs:83"}, "properties": {"repobilityId": "4893cbe306ed749e", "scanner": "scanner-primary", "fingerprint": "c35938cd7cf1222b", "layer": "quality", "severity": "medium", "confidence": 1.0, "tags": ["integrity", "fragile-runtime", "robustness"]}}]}]}