@code-rag/core 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +19 -0
- package/dist/auth/audit-log.d.ts +35 -0
- package/dist/auth/audit-log.js +110 -0
- package/dist/auth/audit-log.js.map +1 -0
- package/dist/auth/audit-log.test.d.ts +1 -0
- package/dist/auth/audit-log.test.js +261 -0
- package/dist/auth/audit-log.test.js.map +1 -0
- package/dist/auth/index.d.ts +6 -0
- package/dist/auth/index.js +5 -0
- package/dist/auth/index.js.map +1 -0
- package/dist/auth/oidc-provider.d.ts +49 -0
- package/dist/auth/oidc-provider.js +358 -0
- package/dist/auth/oidc-provider.js.map +1 -0
- package/dist/auth/oidc-provider.test.d.ts +1 -0
- package/dist/auth/oidc-provider.test.js +520 -0
- package/dist/auth/oidc-provider.test.js.map +1 -0
- package/dist/auth/rbac.d.ts +29 -0
- package/dist/auth/rbac.js +75 -0
- package/dist/auth/rbac.js.map +1 -0
- package/dist/auth/rbac.test.d.ts +1 -0
- package/dist/auth/rbac.test.js +224 -0
- package/dist/auth/rbac.test.js.map +1 -0
- package/dist/auth/saml-provider.d.ts +51 -0
- package/dist/auth/saml-provider.js +355 -0
- package/dist/auth/saml-provider.js.map +1 -0
- package/dist/auth/saml-provider.test.d.ts +1 -0
- package/dist/auth/saml-provider.test.js +422 -0
- package/dist/auth/saml-provider.test.js.map +1 -0
- package/dist/auth/types.d.ts +81 -0
- package/dist/auth/types.js +11 -0
- package/dist/auth/types.js.map +1 -0
- package/dist/auth/types.test.d.ts +1 -0
- package/dist/auth/types.test.js +147 -0
- package/dist/auth/types.test.js.map +1 -0
- package/dist/backlog/ab-reference-scanner.d.ts +10 -0
- package/dist/backlog/ab-reference-scanner.js +22 -0
- package/dist/backlog/ab-reference-scanner.js.map +1 -0
- package/dist/backlog/ab-reference-scanner.test.d.ts +1 -0
- package/dist/backlog/ab-reference-scanner.test.js +83 -0
- package/dist/backlog/ab-reference-scanner.test.js.map +1 -0
- package/dist/backlog/azure-devops-provider.d.ts +59 -0
- package/dist/backlog/azure-devops-provider.js +283 -0
- package/dist/backlog/azure-devops-provider.js.map +1 -0
- package/dist/backlog/backlog-provider.d.ts +13 -0
- package/dist/backlog/backlog-provider.js +6 -0
- package/dist/backlog/backlog-provider.js.map +1 -0
- package/dist/backlog/backlog-provider.test.d.ts +1 -0
- package/dist/backlog/backlog-provider.test.js +426 -0
- package/dist/backlog/backlog-provider.test.js.map +1 -0
- package/dist/backlog/clickup-provider.d.ts +55 -0
- package/dist/backlog/clickup-provider.js +301 -0
- package/dist/backlog/clickup-provider.js.map +1 -0
- package/dist/backlog/clickup-provider.test.d.ts +1 -0
- package/dist/backlog/clickup-provider.test.js +426 -0
- package/dist/backlog/clickup-provider.test.js.map +1 -0
- package/dist/backlog/clickup-reference-scanner.d.ts +10 -0
- package/dist/backlog/clickup-reference-scanner.js +32 -0
- package/dist/backlog/clickup-reference-scanner.js.map +1 -0
- package/dist/backlog/clickup-reference-scanner.test.d.ts +1 -0
- package/dist/backlog/clickup-reference-scanner.test.js +92 -0
- package/dist/backlog/clickup-reference-scanner.test.js.map +1 -0
- package/dist/backlog/code-linker.d.ts +63 -0
- package/dist/backlog/code-linker.js +90 -0
- package/dist/backlog/code-linker.js.map +1 -0
- package/dist/backlog/code-linker.test.d.ts +1 -0
- package/dist/backlog/code-linker.test.js +325 -0
- package/dist/backlog/code-linker.test.js.map +1 -0
- package/dist/backlog/index.d.ts +14 -0
- package/dist/backlog/index.js +8 -0
- package/dist/backlog/index.js.map +1 -0
- package/dist/backlog/jira-provider.d.ts +60 -0
- package/dist/backlog/jira-provider.js +272 -0
- package/dist/backlog/jira-provider.js.map +1 -0
- package/dist/backlog/jira-provider.test.d.ts +1 -0
- package/dist/backlog/jira-provider.test.js +449 -0
- package/dist/backlog/jira-provider.test.js.map +1 -0
- package/dist/backlog/jira-reference-scanner.d.ts +11 -0
- package/dist/backlog/jira-reference-scanner.js +26 -0
- package/dist/backlog/jira-reference-scanner.js.map +1 -0
- package/dist/backlog/jira-reference-scanner.test.d.ts +1 -0
- package/dist/backlog/jira-reference-scanner.test.js +127 -0
- package/dist/backlog/jira-reference-scanner.test.js.map +1 -0
- package/dist/backlog/types.d.ts +22 -0
- package/dist/backlog/types.js +1 -0
- package/dist/backlog/types.js.map +1 -0
- package/dist/chunker/ast-chunker.d.ts +45 -0
- package/dist/chunker/ast-chunker.js +292 -0
- package/dist/chunker/ast-chunker.js.map +1 -0
- package/dist/chunker/ast-chunker.test.d.ts +1 -0
- package/dist/chunker/ast-chunker.test.js +391 -0
- package/dist/chunker/ast-chunker.test.js.map +1 -0
- package/dist/chunker/chunker.d.ts +8 -0
- package/dist/chunker/chunker.js +1 -0
- package/dist/chunker/chunker.js.map +1 -0
- package/dist/chunker/index.d.ts +3 -0
- package/dist/chunker/index.js +2 -0
- package/dist/chunker/index.js.map +1 -0
- package/dist/config/config-parser.d.ts +15 -0
- package/dist/config/config-parser.js +283 -0
- package/dist/config/config-parser.js.map +1 -0
- package/dist/config/config-parser.test.d.ts +1 -0
- package/dist/config/config-parser.test.js +699 -0
- package/dist/config/config-parser.test.js.map +1 -0
- package/dist/docs/confluence-provider.d.ts +121 -0
- package/dist/docs/confluence-provider.js +459 -0
- package/dist/docs/confluence-provider.js.map +1 -0
- package/dist/docs/confluence-provider.test.d.ts +1 -0
- package/dist/docs/confluence-provider.test.js +765 -0
- package/dist/docs/confluence-provider.test.js.map +1 -0
- package/dist/docs/index.d.ts +4 -0
- package/dist/docs/index.js +2 -0
- package/dist/docs/index.js.map +1 -0
- package/dist/docs/sharepoint-provider.d.ts +150 -0
- package/dist/docs/sharepoint-provider.js +637 -0
- package/dist/docs/sharepoint-provider.js.map +1 -0
- package/dist/docs/sharepoint-provider.test.d.ts +1 -0
- package/dist/docs/sharepoint-provider.test.js +873 -0
- package/dist/docs/sharepoint-provider.test.js.map +1 -0
- package/dist/embedding/bm25-index.d.ts +12 -0
- package/dist/embedding/bm25-index.js +89 -0
- package/dist/embedding/bm25-index.js.map +1 -0
- package/dist/embedding/bm25-index.test.d.ts +1 -0
- package/dist/embedding/bm25-index.test.js +289 -0
- package/dist/embedding/bm25-index.test.js.map +1 -0
- package/dist/embedding/hybrid-search.d.ts +13 -0
- package/dist/embedding/hybrid-search.js +124 -0
- package/dist/embedding/hybrid-search.js.map +1 -0
- package/dist/embedding/hybrid-search.test.d.ts +1 -0
- package/dist/embedding/hybrid-search.test.js +266 -0
- package/dist/embedding/hybrid-search.test.js.map +1 -0
- package/dist/embedding/index.d.ts +11 -0
- package/dist/embedding/index.js +7 -0
- package/dist/embedding/index.js.map +1 -0
- package/dist/embedding/lancedb-store.d.ts +21 -0
- package/dist/embedding/lancedb-store.js +172 -0
- package/dist/embedding/lancedb-store.js.map +1 -0
- package/dist/embedding/lancedb-store.test.d.ts +1 -0
- package/dist/embedding/lancedb-store.test.js +268 -0
- package/dist/embedding/lancedb-store.test.js.map +1 -0
- package/dist/embedding/model-lifecycle-manager.d.ts +83 -0
- package/dist/embedding/model-lifecycle-manager.js +419 -0
- package/dist/embedding/model-lifecycle-manager.js.map +1 -0
- package/dist/embedding/model-lifecycle-manager.test.d.ts +1 -0
- package/dist/embedding/model-lifecycle-manager.test.js +642 -0
- package/dist/embedding/model-lifecycle-manager.test.js.map +1 -0
- package/dist/embedding/ollama-embedding-provider.d.ts +16 -0
- package/dist/embedding/ollama-embedding-provider.js +74 -0
- package/dist/embedding/ollama-embedding-provider.js.map +1 -0
- package/dist/embedding/ollama-embedding-provider.test.d.ts +1 -0
- package/dist/embedding/ollama-embedding-provider.test.js +198 -0
- package/dist/embedding/ollama-embedding-provider.test.js.map +1 -0
- package/dist/embedding/openai-compatible-embedding-provider.d.ts +19 -0
- package/dist/embedding/openai-compatible-embedding-provider.js +108 -0
- package/dist/embedding/openai-compatible-embedding-provider.js.map +1 -0
- package/dist/embedding/openai-compatible-embedding-provider.test.d.ts +1 -0
- package/dist/embedding/openai-compatible-embedding-provider.test.js +456 -0
- package/dist/embedding/openai-compatible-embedding-provider.test.js.map +1 -0
- package/dist/embedding/qdrant-store.d.ts +28 -0
- package/dist/embedding/qdrant-store.js +174 -0
- package/dist/embedding/qdrant-store.js.map +1 -0
- package/dist/embedding/qdrant-store.test.d.ts +1 -0
- package/dist/embedding/qdrant-store.test.js +359 -0
- package/dist/embedding/qdrant-store.test.js.map +1 -0
- package/dist/enrichment/index.d.ts +4 -0
- package/dist/enrichment/index.js +2 -0
- package/dist/enrichment/index.js.map +1 -0
- package/dist/enrichment/nl-enricher.d.ts +16 -0
- package/dist/enrichment/nl-enricher.js +47 -0
- package/dist/enrichment/nl-enricher.js.map +1 -0
- package/dist/enrichment/nl-enricher.test.d.ts +1 -0
- package/dist/enrichment/nl-enricher.test.js +154 -0
- package/dist/enrichment/nl-enricher.test.js.map +1 -0
- package/dist/enrichment/ollama-client.d.ts +18 -0
- package/dist/enrichment/ollama-client.js +55 -0
- package/dist/enrichment/ollama-client.js.map +1 -0
- package/dist/enrichment/ollama-client.test.d.ts +1 -0
- package/dist/enrichment/ollama-client.test.js +129 -0
- package/dist/enrichment/ollama-client.test.js.map +1 -0
- package/dist/git/git-client.d.ts +22 -0
- package/dist/git/git-client.js +6 -0
- package/dist/git/git-client.js.map +1 -0
- package/dist/git/git-client.test.d.ts +1 -0
- package/dist/git/git-client.test.js +200 -0
- package/dist/git/git-client.test.js.map +1 -0
- package/dist/git/ignore-filter.d.ts +2 -0
- package/dist/git/ignore-filter.js +31 -0
- package/dist/git/ignore-filter.js.map +1 -0
- package/dist/git/ignore-filter.test.d.ts +1 -0
- package/dist/git/ignore-filter.test.js +87 -0
- package/dist/git/ignore-filter.test.js.map +1 -0
- package/dist/git/index.d.ts +4 -0
- package/dist/git/index.js +3 -0
- package/dist/git/index.js.map +1 -0
- package/dist/git/simple-git-client.d.ts +12 -0
- package/dist/git/simple-git-client.js +138 -0
- package/dist/git/simple-git-client.js.map +1 -0
- package/dist/graph/cross-repo-resolver.d.ts +50 -0
- package/dist/graph/cross-repo-resolver.js +315 -0
- package/dist/graph/cross-repo-resolver.js.map +1 -0
- package/dist/graph/cross-repo-resolver.test.d.ts +1 -0
- package/dist/graph/cross-repo-resolver.test.js +548 -0
- package/dist/graph/cross-repo-resolver.test.js.map +1 -0
- package/dist/graph/dependency-graph.d.ts +44 -0
- package/dist/graph/dependency-graph.js +108 -0
- package/dist/graph/dependency-graph.js.map +1 -0
- package/dist/graph/dependency-graph.test.d.ts +1 -0
- package/dist/graph/dependency-graph.test.js +276 -0
- package/dist/graph/dependency-graph.test.js.map +1 -0
- package/dist/graph/graph-builder.d.ts +11 -0
- package/dist/graph/graph-builder.js +113 -0
- package/dist/graph/graph-builder.js.map +1 -0
- package/dist/graph/graph-builder.test.d.ts +1 -0
- package/dist/graph/graph-builder.test.js +178 -0
- package/dist/graph/graph-builder.test.js.map +1 -0
- package/dist/graph/import-resolver.d.ts +11 -0
- package/dist/graph/import-resolver.js +199 -0
- package/dist/graph/import-resolver.js.map +1 -0
- package/dist/graph/import-resolver.test.d.ts +1 -0
- package/dist/graph/import-resolver.test.js +282 -0
- package/dist/graph/import-resolver.test.js.map +1 -0
- package/dist/graph/index.d.ts +7 -0
- package/dist/graph/index.js +4 -0
- package/dist/graph/index.js.map +1 -0
- package/dist/index.d.ts +31 -0
- package/dist/index.js +15 -0
- package/dist/index.js.map +1 -0
- package/dist/indexer/file-scanner.d.ts +34 -0
- package/dist/indexer/file-scanner.js +69 -0
- package/dist/indexer/file-scanner.js.map +1 -0
- package/dist/indexer/file-scanner.test.d.ts +1 -0
- package/dist/indexer/file-scanner.test.js +110 -0
- package/dist/indexer/file-scanner.test.js.map +1 -0
- package/dist/indexer/file-watcher.d.ts +79 -0
- package/dist/indexer/file-watcher.js +148 -0
- package/dist/indexer/incremental-indexer.d.ts +67 -0
- package/dist/indexer/incremental-indexer.js +142 -0
- package/dist/indexer/incremental-indexer.js.map +1 -0
- package/dist/indexer/incremental-indexer.test.d.ts +1 -0
- package/dist/indexer/incremental-indexer.test.js +266 -0
- package/dist/indexer/incremental-indexer.test.js.map +1 -0
- package/dist/indexer/index-check.d.ts +22 -0
- package/dist/indexer/index-check.js +74 -0
- package/dist/indexer/index-check.js.map +1 -0
- package/dist/indexer/index-check.test.d.ts +1 -0
- package/dist/indexer/index-check.test.js +100 -0
- package/dist/indexer/index-check.test.js.map +1 -0
- package/dist/indexer/index-state.d.ts +61 -0
- package/dist/indexer/index-state.js +82 -0
- package/dist/indexer/index-state.js.map +1 -0
- package/dist/indexer/index-state.test.d.ts +1 -0
- package/dist/indexer/index-state.test.js +140 -0
- package/dist/indexer/index-state.test.js.map +1 -0
- package/dist/indexer/index.d.ts +12 -0
- package/dist/indexer/index.js +6 -0
- package/dist/indexer/index.js.map +1 -0
- package/dist/indexer/multi-repo-indexer.d.ts +63 -0
- package/dist/indexer/multi-repo-indexer.js +144 -0
- package/dist/indexer/multi-repo-indexer.js.map +1 -0
- package/dist/indexer/multi-repo-indexer.test.d.ts +1 -0
- package/dist/indexer/multi-repo-indexer.test.js +238 -0
- package/dist/indexer/multi-repo-indexer.test.js.map +1 -0
- package/dist/parser/index.d.ts +4 -0
- package/dist/parser/index.js +3 -0
- package/dist/parser/index.js.map +1 -0
- package/dist/parser/language-registry.d.ts +46 -0
- package/dist/parser/language-registry.js +219 -0
- package/dist/parser/language-registry.js.map +1 -0
- package/dist/parser/language-registry.test.d.ts +1 -0
- package/dist/parser/language-registry.test.js +225 -0
- package/dist/parser/language-registry.test.js.map +1 -0
- package/dist/parser/markdown-parser.d.ts +124 -0
- package/dist/parser/markdown-parser.js +487 -0
- package/dist/parser/markdown-parser.js.map +1 -0
- package/dist/parser/markdown-parser.test.d.ts +1 -0
- package/dist/parser/markdown-parser.test.js +600 -0
- package/dist/parser/markdown-parser.test.js.map +1 -0
- package/dist/parser/tree-sitter-parser.d.ts +32 -0
- package/dist/parser/tree-sitter-parser.js +146 -0
- package/dist/parser/tree-sitter-parser.js.map +1 -0
- package/dist/retrieval/context-expander.d.ts +51 -0
- package/dist/retrieval/context-expander.js +218 -0
- package/dist/retrieval/context-expander.js.map +1 -0
- package/dist/retrieval/context-expander.test.d.ts +1 -0
- package/dist/retrieval/context-expander.test.js +339 -0
- package/dist/retrieval/context-expander.test.js.map +1 -0
- package/dist/retrieval/cross-encoder-reranker.d.ts +16 -0
- package/dist/retrieval/cross-encoder-reranker.js +90 -0
- package/dist/retrieval/cross-encoder-reranker.js.map +1 -0
- package/dist/retrieval/cross-encoder-reranker.test.d.ts +1 -0
- package/dist/retrieval/cross-encoder-reranker.test.js +305 -0
- package/dist/retrieval/cross-encoder-reranker.test.js.map +1 -0
- package/dist/retrieval/index.d.ts +8 -0
- package/dist/retrieval/index.js +4 -0
- package/dist/retrieval/index.js.map +1 -0
- package/dist/retrieval/query-analyzer.d.ts +29 -0
- package/dist/retrieval/query-analyzer.js +238 -0
- package/dist/retrieval/query-analyzer.js.map +1 -0
- package/dist/retrieval/query-analyzer.test.d.ts +1 -0
- package/dist/retrieval/query-analyzer.test.js +236 -0
- package/dist/retrieval/query-analyzer.test.js.map +1 -0
- package/dist/retrieval/token-budget.d.ts +51 -0
- package/dist/retrieval/token-budget.js +141 -0
- package/dist/retrieval/token-budget.js.map +1 -0
- package/dist/retrieval/token-budget.test.d.ts +1 -0
- package/dist/retrieval/token-budget.test.js +404 -0
- package/dist/retrieval/token-budget.test.js.map +1 -0
- package/dist/storage/azure-blob-provider.d.ts +19 -0
- package/dist/storage/azure-blob-provider.js +199 -0
- package/dist/storage/azure-blob-provider.js.map +1 -0
- package/dist/storage/azure-blob-provider.test.d.ts +1 -0
- package/dist/storage/azure-blob-provider.test.js +250 -0
- package/dist/storage/azure-blob-provider.test.js.map +1 -0
- package/dist/storage/gcs-provider.d.ts +22 -0
- package/dist/storage/gcs-provider.js +241 -0
- package/dist/storage/gcs-provider.js.map +1 -0
- package/dist/storage/gcs-provider.test.d.ts +1 -0
- package/dist/storage/gcs-provider.test.js +299 -0
- package/dist/storage/gcs-provider.test.js.map +1 -0
- package/dist/storage/index.d.ts +5 -0
- package/dist/storage/index.js +4 -0
- package/dist/storage/index.js.map +1 -0
- package/dist/storage/s3-provider.d.ts +21 -0
- package/dist/storage/s3-provider.js +220 -0
- package/dist/storage/s3-provider.js.map +1 -0
- package/dist/storage/s3-provider.test.d.ts +1 -0
- package/dist/storage/s3-provider.test.js +329 -0
- package/dist/storage/s3-provider.test.js.map +1 -0
- package/dist/storage/types.d.ts +65 -0
- package/dist/storage/types.js +12 -0
- package/dist/storage/types.js.map +1 -0
- package/dist/types/chunk.d.ts +32 -0
- package/dist/types/chunk.js +1 -0
- package/dist/types/chunk.js.map +1 -0
- package/dist/types/config.d.ts +71 -0
- package/dist/types/config.js +1 -0
- package/dist/types/config.js.map +1 -0
- package/dist/types/index.d.ts +5 -0
- package/dist/types/index.js +1 -0
- package/dist/types/index.js.map +1 -0
- package/dist/types/provider.d.ts +54 -0
- package/dist/types/provider.js +36 -0
- package/dist/types/provider.js.map +1 -0
- package/dist/types/search.d.ts +27 -0
- package/dist/types/search.js +1 -0
- package/dist/types/search.js.map +1 -0
- package/package.json +70 -0
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import { type Result } from 'neverthrow';
|
|
2
|
+
import { BacklogError } from './backlog-provider.js';
|
|
3
|
+
import type { BacklogProvider } from './backlog-provider.js';
|
|
4
|
+
import type { BacklogItem } from './types.js';
|
|
5
|
+
import type { Chunk } from '../types/chunk.js';
|
|
6
|
+
/**
|
|
7
|
+
* Bidirectional mapping between backlog items and code chunks.
|
|
8
|
+
*
|
|
9
|
+
* - `itemToChunks`: Maps a backlog item ID to the set of chunk IDs that reference it.
|
|
10
|
+
* - `chunkToItems`: Maps a chunk ID to the set of backlog item IDs it references.
|
|
11
|
+
*/
|
|
12
|
+
export interface BacklogCodeMap {
|
|
13
|
+
itemToChunks: Map<string, Set<string>>;
|
|
14
|
+
chunkToItems: Map<string, Set<string>>;
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Coverage report showing which backlog items have linked code and which do not.
|
|
18
|
+
*/
|
|
19
|
+
export interface CoverageReport {
|
|
20
|
+
/** Backlog items that have at least one linked code chunk. */
|
|
21
|
+
linkedItems: BacklogItem[];
|
|
22
|
+
/** Backlog items that have no linked code chunks. */
|
|
23
|
+
unlinkedItems: BacklogItem[];
|
|
24
|
+
/** Total number of backlog items evaluated. */
|
|
25
|
+
totalItems: number;
|
|
26
|
+
/** Number of items with at least one linked chunk. */
|
|
27
|
+
linkedCount: number;
|
|
28
|
+
/** Number of items with no linked chunks. */
|
|
29
|
+
unlinkedCount: number;
|
|
30
|
+
/** Coverage percentage (0-100). */
|
|
31
|
+
coveragePercent: number;
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* Links code chunks to backlog items by scanning chunk content for AB# references
|
|
35
|
+
* and creating bidirectional mappings.
|
|
36
|
+
*
|
|
37
|
+
* Uses `scanForABReferences` to detect `AB#<number>` patterns in chunk content
|
|
38
|
+
* and resolves them against a BacklogProvider to build a BacklogCodeMap.
|
|
39
|
+
*/
|
|
40
|
+
export declare class CodeLinker {
|
|
41
|
+
/**
|
|
42
|
+
* Scans an array of chunks for AB# references and builds a bidirectional
|
|
43
|
+
* mapping between backlog item IDs and chunk IDs.
|
|
44
|
+
*
|
|
45
|
+
* For each chunk, the content is scanned for AB# patterns. Each detected
|
|
46
|
+
* reference is resolved against the provider to confirm the item exists.
|
|
47
|
+
* Only valid (existing) backlog items are included in the map.
|
|
48
|
+
*
|
|
49
|
+
* @param chunks - Code chunks to scan for backlog references
|
|
50
|
+
* @param provider - BacklogProvider used to validate item existence
|
|
51
|
+
* @returns A Result containing the BacklogCodeMap or a BacklogError
|
|
52
|
+
*/
|
|
53
|
+
linkChunksToBacklog(chunks: Chunk[], provider: BacklogProvider): Promise<Result<BacklogCodeMap, BacklogError>>;
|
|
54
|
+
/**
|
|
55
|
+
* Generates a coverage report showing which backlog items have linked code
|
|
56
|
+
* chunks and which do not.
|
|
57
|
+
*
|
|
58
|
+
* @param map - The BacklogCodeMap produced by `linkChunksToBacklog`
|
|
59
|
+
* @param allItems - The full list of backlog items to evaluate
|
|
60
|
+
* @returns A CoverageReport with linked/unlinked items and statistics
|
|
61
|
+
*/
|
|
62
|
+
getCoverageReport(map: BacklogCodeMap, allItems: BacklogItem[]): CoverageReport;
|
|
63
|
+
}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import { ok, err } from 'neverthrow';
|
|
2
|
+
import { BacklogError } from './backlog-provider.js';
|
|
3
|
+
import { scanForABReferences } from './ab-reference-scanner.js';
|
|
4
|
+
/**
|
|
5
|
+
* Links code chunks to backlog items by scanning chunk content for AB# references
|
|
6
|
+
* and creating bidirectional mappings.
|
|
7
|
+
*
|
|
8
|
+
* Uses `scanForABReferences` to detect `AB#<number>` patterns in chunk content
|
|
9
|
+
* and resolves them against a BacklogProvider to build a BacklogCodeMap.
|
|
10
|
+
*/
|
|
11
|
+
export class CodeLinker {
|
|
12
|
+
/**
|
|
13
|
+
* Scans an array of chunks for AB# references and builds a bidirectional
|
|
14
|
+
* mapping between backlog item IDs and chunk IDs.
|
|
15
|
+
*
|
|
16
|
+
* For each chunk, the content is scanned for AB# patterns. Each detected
|
|
17
|
+
* reference is resolved against the provider to confirm the item exists.
|
|
18
|
+
* Only valid (existing) backlog items are included in the map.
|
|
19
|
+
*
|
|
20
|
+
* @param chunks - Code chunks to scan for backlog references
|
|
21
|
+
* @param provider - BacklogProvider used to validate item existence
|
|
22
|
+
* @returns A Result containing the BacklogCodeMap or a BacklogError
|
|
23
|
+
*/
|
|
24
|
+
async linkChunksToBacklog(chunks, provider) {
|
|
25
|
+
const itemToChunks = new Map();
|
|
26
|
+
const chunkToItems = new Map();
|
|
27
|
+
try {
|
|
28
|
+
for (const chunk of chunks) {
|
|
29
|
+
const refIds = scanForABReferences(chunk.content);
|
|
30
|
+
for (const refId of refIds) {
|
|
31
|
+
// Validate that the backlog item actually exists
|
|
32
|
+
const itemResult = await provider.getItem(refId);
|
|
33
|
+
if (itemResult.isErr()) {
|
|
34
|
+
// Item doesn't exist in backlog — skip this reference
|
|
35
|
+
continue;
|
|
36
|
+
}
|
|
37
|
+
const itemId = itemResult.value.id;
|
|
38
|
+
// Add to itemToChunks
|
|
39
|
+
if (!itemToChunks.has(itemId)) {
|
|
40
|
+
itemToChunks.set(itemId, new Set());
|
|
41
|
+
}
|
|
42
|
+
itemToChunks.get(itemId).add(chunk.id);
|
|
43
|
+
// Add to chunkToItems
|
|
44
|
+
if (!chunkToItems.has(chunk.id)) {
|
|
45
|
+
chunkToItems.set(chunk.id, new Set());
|
|
46
|
+
}
|
|
47
|
+
chunkToItems.get(chunk.id).add(itemId);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
return ok({ itemToChunks, chunkToItems });
|
|
51
|
+
}
|
|
52
|
+
catch (error) {
|
|
53
|
+
const message = error instanceof Error ? error.message : 'Unknown error';
|
|
54
|
+
return err(new BacklogError(`Failed to link chunks to backlog: ${message}`));
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* Generates a coverage report showing which backlog items have linked code
|
|
59
|
+
* chunks and which do not.
|
|
60
|
+
*
|
|
61
|
+
* @param map - The BacklogCodeMap produced by `linkChunksToBacklog`
|
|
62
|
+
* @param allItems - The full list of backlog items to evaluate
|
|
63
|
+
* @returns A CoverageReport with linked/unlinked items and statistics
|
|
64
|
+
*/
|
|
65
|
+
getCoverageReport(map, allItems) {
|
|
66
|
+
const linkedItems = [];
|
|
67
|
+
const unlinkedItems = [];
|
|
68
|
+
for (const item of allItems) {
|
|
69
|
+
const chunks = map.itemToChunks.get(item.id);
|
|
70
|
+
if (chunks && chunks.size > 0) {
|
|
71
|
+
linkedItems.push(item);
|
|
72
|
+
}
|
|
73
|
+
else {
|
|
74
|
+
unlinkedItems.push(item);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
const totalItems = allItems.length;
|
|
78
|
+
const linkedCount = linkedItems.length;
|
|
79
|
+
const unlinkedCount = unlinkedItems.length;
|
|
80
|
+
const coveragePercent = totalItems > 0 ? Math.round((linkedCount / totalItems) * 100) : 0;
|
|
81
|
+
return {
|
|
82
|
+
linkedItems,
|
|
83
|
+
unlinkedItems,
|
|
84
|
+
totalItems,
|
|
85
|
+
linkedCount,
|
|
86
|
+
unlinkedCount,
|
|
87
|
+
coveragePercent,
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"code-linker.js","sourceRoot":"","sources":["../../src/backlog/code-linker.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,325 @@
|
|
|
1
|
+
import { describe, it, expect, vi } from 'vitest';
|
|
2
|
+
import { ok, err } from 'neverthrow';
|
|
3
|
+
import { CodeLinker } from './code-linker.js';
|
|
4
|
+
import { BacklogError } from './backlog-provider.js';
|
|
5
|
+
// --- Helpers ---
|
|
6
|
+
function createMockChunk(overrides) {
|
|
7
|
+
return {
|
|
8
|
+
id: 'chunk-1',
|
|
9
|
+
content: '// some code',
|
|
10
|
+
nlSummary: 'A code chunk',
|
|
11
|
+
filePath: 'src/example.ts',
|
|
12
|
+
startLine: 1,
|
|
13
|
+
endLine: 10,
|
|
14
|
+
language: 'typescript',
|
|
15
|
+
metadata: {
|
|
16
|
+
chunkType: 'function',
|
|
17
|
+
name: 'example',
|
|
18
|
+
declarations: [],
|
|
19
|
+
imports: [],
|
|
20
|
+
exports: [],
|
|
21
|
+
},
|
|
22
|
+
...overrides,
|
|
23
|
+
};
|
|
24
|
+
}
|
|
25
|
+
function createMockItem(overrides) {
|
|
26
|
+
return {
|
|
27
|
+
id: '123',
|
|
28
|
+
externalId: 'AB#123',
|
|
29
|
+
title: 'Fix login bug',
|
|
30
|
+
description: 'Users cannot log in when using SSO',
|
|
31
|
+
type: 'bug',
|
|
32
|
+
state: 'Active',
|
|
33
|
+
assignedTo: 'dev@example.com',
|
|
34
|
+
tags: ['auth'],
|
|
35
|
+
linkedCodePaths: [],
|
|
36
|
+
url: 'https://devops.example.com/workitem/123',
|
|
37
|
+
metadata: {},
|
|
38
|
+
...overrides,
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
function createMockProvider(items) {
|
|
42
|
+
return {
|
|
43
|
+
name: 'mock-provider',
|
|
44
|
+
initialize: vi.fn().mockResolvedValue(ok(undefined)),
|
|
45
|
+
getItems: vi.fn().mockResolvedValue(ok(items)),
|
|
46
|
+
getItem: vi.fn().mockImplementation(async (id) => {
|
|
47
|
+
const item = items.find((i) => i.id === id);
|
|
48
|
+
if (!item) {
|
|
49
|
+
return err(new BacklogError(`Item not found: ${id}`));
|
|
50
|
+
}
|
|
51
|
+
return ok(item);
|
|
52
|
+
}),
|
|
53
|
+
searchItems: vi.fn().mockResolvedValue(ok(items)),
|
|
54
|
+
getLinkedCode: vi.fn().mockResolvedValue(ok([])),
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
// --- CodeLinker tests ---
|
|
58
|
+
describe('CodeLinker', () => {
|
|
59
|
+
describe('linkChunksToBacklog', () => {
|
|
60
|
+
it('should link a chunk containing a single AB# reference', async () => {
|
|
61
|
+
const item = createMockItem({ id: '42', externalId: 'AB#42' });
|
|
62
|
+
const chunk = createMockChunk({
|
|
63
|
+
id: 'chunk-a',
|
|
64
|
+
content: '// Fixes AB#42\nfunction login() { return true; }',
|
|
65
|
+
});
|
|
66
|
+
const provider = createMockProvider([item]);
|
|
67
|
+
const linker = new CodeLinker();
|
|
68
|
+
const result = await linker.linkChunksToBacklog([chunk], provider);
|
|
69
|
+
expect(result.isOk()).toBe(true);
|
|
70
|
+
if (result.isOk()) {
|
|
71
|
+
const map = result.value;
|
|
72
|
+
expect(map.itemToChunks.get('42')).toEqual(new Set(['chunk-a']));
|
|
73
|
+
expect(map.chunkToItems.get('chunk-a')).toEqual(new Set(['42']));
|
|
74
|
+
}
|
|
75
|
+
});
|
|
76
|
+
it('should link a chunk with multiple AB# references', async () => {
|
|
77
|
+
const item1 = createMockItem({ id: '10', externalId: 'AB#10' });
|
|
78
|
+
const item2 = createMockItem({ id: '20', externalId: 'AB#20' });
|
|
79
|
+
const chunk = createMockChunk({
|
|
80
|
+
id: 'chunk-multi',
|
|
81
|
+
content: '// Implements AB#10 and AB#20\nexport class Auth {}',
|
|
82
|
+
});
|
|
83
|
+
const provider = createMockProvider([item1, item2]);
|
|
84
|
+
const linker = new CodeLinker();
|
|
85
|
+
const result = await linker.linkChunksToBacklog([chunk], provider);
|
|
86
|
+
expect(result.isOk()).toBe(true);
|
|
87
|
+
if (result.isOk()) {
|
|
88
|
+
const map = result.value;
|
|
89
|
+
expect(map.itemToChunks.get('10')).toEqual(new Set(['chunk-multi']));
|
|
90
|
+
expect(map.itemToChunks.get('20')).toEqual(new Set(['chunk-multi']));
|
|
91
|
+
expect(map.chunkToItems.get('chunk-multi')).toEqual(new Set(['10', '20']));
|
|
92
|
+
}
|
|
93
|
+
});
|
|
94
|
+
it('should link multiple chunks to the same backlog item', async () => {
|
|
95
|
+
const item = createMockItem({ id: '99', externalId: 'AB#99' });
|
|
96
|
+
const chunk1 = createMockChunk({
|
|
97
|
+
id: 'chunk-1',
|
|
98
|
+
content: '// AB#99 implementation part 1',
|
|
99
|
+
});
|
|
100
|
+
const chunk2 = createMockChunk({
|
|
101
|
+
id: 'chunk-2',
|
|
102
|
+
content: '// AB#99 implementation part 2',
|
|
103
|
+
});
|
|
104
|
+
const provider = createMockProvider([item]);
|
|
105
|
+
const linker = new CodeLinker();
|
|
106
|
+
const result = await linker.linkChunksToBacklog([chunk1, chunk2], provider);
|
|
107
|
+
expect(result.isOk()).toBe(true);
|
|
108
|
+
if (result.isOk()) {
|
|
109
|
+
const map = result.value;
|
|
110
|
+
expect(map.itemToChunks.get('99')).toEqual(new Set(['chunk-1', 'chunk-2']));
|
|
111
|
+
expect(map.chunkToItems.get('chunk-1')).toEqual(new Set(['99']));
|
|
112
|
+
expect(map.chunkToItems.get('chunk-2')).toEqual(new Set(['99']));
|
|
113
|
+
}
|
|
114
|
+
});
|
|
115
|
+
it('should return empty maps when chunks have no references', async () => {
|
|
116
|
+
const chunk = createMockChunk({
|
|
117
|
+
id: 'chunk-plain',
|
|
118
|
+
content: 'function add(a: number, b: number) { return a + b; }',
|
|
119
|
+
});
|
|
120
|
+
const provider = createMockProvider([]);
|
|
121
|
+
const linker = new CodeLinker();
|
|
122
|
+
const result = await linker.linkChunksToBacklog([chunk], provider);
|
|
123
|
+
expect(result.isOk()).toBe(true);
|
|
124
|
+
if (result.isOk()) {
|
|
125
|
+
const map = result.value;
|
|
126
|
+
expect(map.itemToChunks.size).toBe(0);
|
|
127
|
+
expect(map.chunkToItems.size).toBe(0);
|
|
128
|
+
}
|
|
129
|
+
});
|
|
130
|
+
it('should return empty maps when chunks array is empty', async () => {
|
|
131
|
+
const provider = createMockProvider([]);
|
|
132
|
+
const linker = new CodeLinker();
|
|
133
|
+
const result = await linker.linkChunksToBacklog([], provider);
|
|
134
|
+
expect(result.isOk()).toBe(true);
|
|
135
|
+
if (result.isOk()) {
|
|
136
|
+
const map = result.value;
|
|
137
|
+
expect(map.itemToChunks.size).toBe(0);
|
|
138
|
+
expect(map.chunkToItems.size).toBe(0);
|
|
139
|
+
}
|
|
140
|
+
});
|
|
141
|
+
it('should skip references to non-existent backlog items', async () => {
|
|
142
|
+
const item = createMockItem({ id: '100', externalId: 'AB#100' });
|
|
143
|
+
const chunk = createMockChunk({
|
|
144
|
+
id: 'chunk-mixed',
|
|
145
|
+
content: '// AB#100 exists, AB#999 does not',
|
|
146
|
+
});
|
|
147
|
+
const provider = createMockProvider([item]);
|
|
148
|
+
const linker = new CodeLinker();
|
|
149
|
+
const result = await linker.linkChunksToBacklog([chunk], provider);
|
|
150
|
+
expect(result.isOk()).toBe(true);
|
|
151
|
+
if (result.isOk()) {
|
|
152
|
+
const map = result.value;
|
|
153
|
+
// Only item 100 should be linked
|
|
154
|
+
expect(map.itemToChunks.has('100')).toBe(true);
|
|
155
|
+
expect(map.itemToChunks.has('999')).toBe(false);
|
|
156
|
+
expect(map.chunkToItems.get('chunk-mixed')).toEqual(new Set(['100']));
|
|
157
|
+
}
|
|
158
|
+
});
|
|
159
|
+
it('should deduplicate repeated references in same chunk', async () => {
|
|
160
|
+
const item = createMockItem({ id: '55', externalId: 'AB#55' });
|
|
161
|
+
const chunk = createMockChunk({
|
|
162
|
+
id: 'chunk-dup',
|
|
163
|
+
content: '// AB#55 first mention\n// AB#55 second mention',
|
|
164
|
+
});
|
|
165
|
+
const provider = createMockProvider([item]);
|
|
166
|
+
const linker = new CodeLinker();
|
|
167
|
+
const result = await linker.linkChunksToBacklog([chunk], provider);
|
|
168
|
+
expect(result.isOk()).toBe(true);
|
|
169
|
+
if (result.isOk()) {
|
|
170
|
+
const map = result.value;
|
|
171
|
+
// Should only have one entry, not duplicated
|
|
172
|
+
expect(map.itemToChunks.get('55')).toEqual(new Set(['chunk-dup']));
|
|
173
|
+
expect(map.chunkToItems.get('chunk-dup')).toEqual(new Set(['55']));
|
|
174
|
+
}
|
|
175
|
+
});
|
|
176
|
+
it('should handle references in code comments', async () => {
|
|
177
|
+
const item = createMockItem({ id: '200', externalId: 'AB#200' });
|
|
178
|
+
const chunk = createMockChunk({
|
|
179
|
+
id: 'chunk-comment',
|
|
180
|
+
content: `
|
|
181
|
+
/*
|
|
182
|
+
* Implements AB#200 — user authentication flow
|
|
183
|
+
*/
|
|
184
|
+
export class AuthService {
|
|
185
|
+
login() { return true; }
|
|
186
|
+
}
|
|
187
|
+
`,
|
|
188
|
+
});
|
|
189
|
+
const provider = createMockProvider([item]);
|
|
190
|
+
const linker = new CodeLinker();
|
|
191
|
+
const result = await linker.linkChunksToBacklog([chunk], provider);
|
|
192
|
+
expect(result.isOk()).toBe(true);
|
|
193
|
+
if (result.isOk()) {
|
|
194
|
+
const map = result.value;
|
|
195
|
+
expect(map.itemToChunks.get('200')).toEqual(new Set(['chunk-comment']));
|
|
196
|
+
}
|
|
197
|
+
});
|
|
198
|
+
it('should validate items against the provider', async () => {
|
|
199
|
+
const item = createMockItem({ id: '7', externalId: 'AB#7' });
|
|
200
|
+
const chunk = createMockChunk({
|
|
201
|
+
id: 'chunk-val',
|
|
202
|
+
content: '// AB#7 fix',
|
|
203
|
+
});
|
|
204
|
+
const provider = createMockProvider([item]);
|
|
205
|
+
const linker = new CodeLinker();
|
|
206
|
+
await linker.linkChunksToBacklog([chunk], provider);
|
|
207
|
+
expect(provider.getItem).toHaveBeenCalledWith('7');
|
|
208
|
+
});
|
|
209
|
+
});
|
|
210
|
+
describe('getCoverageReport', () => {
|
|
211
|
+
it('should report all items as linked when all have chunks', () => {
|
|
212
|
+
const items = [
|
|
213
|
+
createMockItem({ id: '1', title: 'Story 1' }),
|
|
214
|
+
createMockItem({ id: '2', title: 'Story 2' }),
|
|
215
|
+
];
|
|
216
|
+
const map = {
|
|
217
|
+
itemToChunks: new Map([
|
|
218
|
+
['1', new Set(['chunk-a'])],
|
|
219
|
+
['2', new Set(['chunk-b'])],
|
|
220
|
+
]),
|
|
221
|
+
chunkToItems: new Map([
|
|
222
|
+
['chunk-a', new Set(['1'])],
|
|
223
|
+
['chunk-b', new Set(['2'])],
|
|
224
|
+
]),
|
|
225
|
+
};
|
|
226
|
+
const linker = new CodeLinker();
|
|
227
|
+
const report = linker.getCoverageReport(map, items);
|
|
228
|
+
expect(report.linkedItems).toHaveLength(2);
|
|
229
|
+
expect(report.unlinkedItems).toHaveLength(0);
|
|
230
|
+
expect(report.totalItems).toBe(2);
|
|
231
|
+
expect(report.linkedCount).toBe(2);
|
|
232
|
+
expect(report.unlinkedCount).toBe(0);
|
|
233
|
+
expect(report.coveragePercent).toBe(100);
|
|
234
|
+
});
|
|
235
|
+
it('should report all items as unlinked when none have chunks', () => {
|
|
236
|
+
const items = [
|
|
237
|
+
createMockItem({ id: '1', title: 'Story 1' }),
|
|
238
|
+
createMockItem({ id: '2', title: 'Story 2' }),
|
|
239
|
+
];
|
|
240
|
+
const map = {
|
|
241
|
+
itemToChunks: new Map(),
|
|
242
|
+
chunkToItems: new Map(),
|
|
243
|
+
};
|
|
244
|
+
const linker = new CodeLinker();
|
|
245
|
+
const report = linker.getCoverageReport(map, items);
|
|
246
|
+
expect(report.linkedItems).toHaveLength(0);
|
|
247
|
+
expect(report.unlinkedItems).toHaveLength(2);
|
|
248
|
+
expect(report.totalItems).toBe(2);
|
|
249
|
+
expect(report.linkedCount).toBe(0);
|
|
250
|
+
expect(report.unlinkedCount).toBe(2);
|
|
251
|
+
expect(report.coveragePercent).toBe(0);
|
|
252
|
+
});
|
|
253
|
+
it('should correctly split linked and unlinked items', () => {
|
|
254
|
+
const items = [
|
|
255
|
+
createMockItem({ id: '1', title: 'Linked Story' }),
|
|
256
|
+
createMockItem({ id: '2', title: 'Unlinked Story' }),
|
|
257
|
+
createMockItem({ id: '3', title: 'Another Linked Story' }),
|
|
258
|
+
];
|
|
259
|
+
const map = {
|
|
260
|
+
itemToChunks: new Map([
|
|
261
|
+
['1', new Set(['chunk-a'])],
|
|
262
|
+
['3', new Set(['chunk-b', 'chunk-c'])],
|
|
263
|
+
]),
|
|
264
|
+
chunkToItems: new Map([
|
|
265
|
+
['chunk-a', new Set(['1'])],
|
|
266
|
+
['chunk-b', new Set(['3'])],
|
|
267
|
+
['chunk-c', new Set(['3'])],
|
|
268
|
+
]),
|
|
269
|
+
};
|
|
270
|
+
const linker = new CodeLinker();
|
|
271
|
+
const report = linker.getCoverageReport(map, items);
|
|
272
|
+
expect(report.linkedItems).toHaveLength(2);
|
|
273
|
+
expect(report.unlinkedItems).toHaveLength(1);
|
|
274
|
+
expect(report.unlinkedItems[0].id).toBe('2');
|
|
275
|
+
expect(report.totalItems).toBe(3);
|
|
276
|
+
expect(report.linkedCount).toBe(2);
|
|
277
|
+
expect(report.unlinkedCount).toBe(1);
|
|
278
|
+
expect(report.coveragePercent).toBe(67);
|
|
279
|
+
});
|
|
280
|
+
it('should handle empty items array', () => {
|
|
281
|
+
const map = {
|
|
282
|
+
itemToChunks: new Map(),
|
|
283
|
+
chunkToItems: new Map(),
|
|
284
|
+
};
|
|
285
|
+
const linker = new CodeLinker();
|
|
286
|
+
const report = linker.getCoverageReport(map, []);
|
|
287
|
+
expect(report.linkedItems).toHaveLength(0);
|
|
288
|
+
expect(report.unlinkedItems).toHaveLength(0);
|
|
289
|
+
expect(report.totalItems).toBe(0);
|
|
290
|
+
expect(report.linkedCount).toBe(0);
|
|
291
|
+
expect(report.unlinkedCount).toBe(0);
|
|
292
|
+
expect(report.coveragePercent).toBe(0);
|
|
293
|
+
});
|
|
294
|
+
it('should handle items with empty chunk sets as unlinked', () => {
|
|
295
|
+
const items = [
|
|
296
|
+
createMockItem({ id: '1', title: 'Story with empty set' }),
|
|
297
|
+
];
|
|
298
|
+
const map = {
|
|
299
|
+
itemToChunks: new Map([['1', new Set()]]),
|
|
300
|
+
chunkToItems: new Map(),
|
|
301
|
+
};
|
|
302
|
+
const linker = new CodeLinker();
|
|
303
|
+
const report = linker.getCoverageReport(map, items);
|
|
304
|
+
expect(report.linkedItems).toHaveLength(0);
|
|
305
|
+
expect(report.unlinkedItems).toHaveLength(1);
|
|
306
|
+
expect(report.coveragePercent).toBe(0);
|
|
307
|
+
});
|
|
308
|
+
it('should calculate correct percentage with rounding', () => {
|
|
309
|
+
const items = [
|
|
310
|
+
createMockItem({ id: '1' }),
|
|
311
|
+
createMockItem({ id: '2' }),
|
|
312
|
+
createMockItem({ id: '3' }),
|
|
313
|
+
];
|
|
314
|
+
const map = {
|
|
315
|
+
itemToChunks: new Map([['1', new Set(['chunk-a'])]]),
|
|
316
|
+
chunkToItems: new Map([['chunk-a', new Set(['1'])]]),
|
|
317
|
+
};
|
|
318
|
+
const linker = new CodeLinker();
|
|
319
|
+
const report = linker.getCoverageReport(map, items);
|
|
320
|
+
// 1/3 = 33.33... -> rounds to 33
|
|
321
|
+
expect(report.coveragePercent).toBe(33);
|
|
322
|
+
});
|
|
323
|
+
});
|
|
324
|
+
});
|
|
325
|
+
//# sourceMappingURL=code-linker.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"code-linker.test.js","sourceRoot":"","sources":["../../src/backlog/code-linker.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,EAAE,EAAE,MAAM,QAAQ,CAAC;AAClD,OAAO,EAAE,EAAE,EAAE,GAAG,EAAE,MAAM,YAAY,CAAC;AACrC,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAE9C,OAAO,EAAE,YAAY,EAAE,MAAM,uBAAuB,CAAC;AAKrD,kBAAkB;AAElB,SAAS,eAAe,CAAC,SAA0B;IACjD,OAAO;QACL,EAAE,EAAE,SAAS;QACb,OAAO,EAAE,cAAc;QACvB,SAAS,EAAE,cAAc;QACzB,QAAQ,EAAE,gBAAgB;QAC1B,SAAS,EAAE,CAAC;QACZ,OAAO,EAAE,EAAE;QACX,QAAQ,EAAE,YAAY;QACtB,QAAQ,EAAE;YACR,SAAS,EAAE,UAAU;YACrB,IAAI,EAAE,SAAS;YACf,YAAY,EAAE,EAAE;YAChB,OAAO,EAAE,EAAE;YACX,OAAO,EAAE,EAAE;SACZ;QACD,GAAG,SAAS;KACb,CAAC;AACJ,CAAC;AAED,SAAS,cAAc,CAAC,SAAgC;IACtD,OAAO;QACL,EAAE,EAAE,KAAK;QACT,UAAU,EAAE,QAAQ;QACpB,KAAK,EAAE,eAAe;QACtB,WAAW,EAAE,oCAAoC;QACjD,IAAI,EAAE,KAAK;QACX,KAAK,EAAE,QAAQ;QACf,UAAU,EAAE,iBAAiB;QAC7B,IAAI,EAAE,CAAC,MAAM,CAAC;QACd,eAAe,EAAE,EAAE;QACnB,GAAG,EAAE,yCAAyC;QAC9C,QAAQ,EAAE,EAAE;QACZ,GAAG,SAAS;KACb,CAAC;AACJ,CAAC;AAED,SAAS,kBAAkB,CAAC,KAAoB;IAC9C,OAAO;QACL,IAAI,EAAE,eAAe;QACrB,UAAU,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,iBAAiB,CAAC,EAAE,CAAC,SAAS,CAAC,CAAC;QACpD,QAAQ,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,iBAAiB,CAAC,EAAE,CAAC,KAAK,CAAC,CAAC;QAC9C,OAAO,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,kBAAkB,CAAC,KAAK,EAAE,EAAU,EAAE,EAAE;YACvD,MAAM,IAAI,GAAG,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC;YAC5C,IAAI,CAAC,IAAI,EAAE,CAAC;gBACV,OAAO,GAAG,CAAC,IAAI,YAAY,CAAC,mBAAmB,EAAE,EAAE,CAAC,CAAC,CAAC;YACxD,CAAC;YACD,OAAO,EAAE,CAAC,IAAI,CAAC,CAAC;QAClB,CAAC,CAAC;QACF,WAAW,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,iBAAiB,CAAC,EAAE,CAAC,KAAK,CAAC,CAAC;QACjD,aAAa,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,iBAAiB,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC;KACjD,CAAC;AACJ,CAAC;AAED,2BAA2B;AAE3B,QAAQ,CAAC,YAAY,EAAE,GAAG,EAAE;IAC1B,QAAQ,CAAC,qBAAqB,EAAE,GAAG,EAAE;QACnC,EAAE,CAAC,uDAAuD,EAAE,KAAK,IAAI,EAAE;YACrE,MAAM,IAAI,GAAG,cAAc,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE,OAAO,EAAE,CAAC,CAAC;YAC/D,MAAM,KAAK,GAAG,eAAe,CAAC;gBAC5B,EAAE,EAAE,SAAS;gBACb,OAAO,EAAE,mDAAmD;aAC7D,CAAC,CAAC;YACH,MAAM,QAAQ,GAAG,kBAAkB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;YAC5C,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAAC,CAAC,KAAK,CAAC,EAAE,QAAQ,CAAC,CAAC;YAEnE,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,IAAI,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC;gBAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC;gBACzB,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC;gBACjE,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACnE,CAAC;QACH,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,kDAAkD,EAAE,KAAK,IAAI,EAAE;YAChE,MAAM,KAAK,GAAG,cAAc,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE,OAAO,EAAE,CAAC,CAAC;YAChE,MAAM,KAAK,GAAG,cAAc,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE,OAAO,EAAE,CAAC,CAAC;YAChE,MAAM,KAAK,GAAG,eAAe,CAAC;gBAC5B,EAAE,EAAE,aAAa;gBACjB,OAAO,EAAE,qDAAqD;aAC/D,CAAC,CAAC;YACH,MAAM,QAAQ,GAAG,kBAAkB,CAAC,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC,CAAC;YACpD,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAAC,CAAC,KAAK,CAAC,EAAE,QAAQ,CAAC,CAAC;YAEnE,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,IAAI,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC;gBAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC;gBACzB,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,aAAa,CAAC,CAAC,CAAC,CAAC;gBACrE,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,aAAa,CAAC,CAAC,CAAC,CAAC;gBACrE,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,aAAa,CAAC,CAAC,CAAC,OAAO,CACjD,IAAI,GAAG,CAAC,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC,CACtB,CAAC;YACJ,CAAC;QACH,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,sDAAsD,EAAE,KAAK,IAAI,EAAE;YACpE,MAAM,IAAI,GAAG,cAAc,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE,OAAO,EAAE,CAAC,CAAC;YAC/D,MAAM,MAAM,GAAG,eAAe,CAAC;gBAC7B,EAAE,EAAE,SAAS;gBACb,OAAO,EAAE,gCAAgC;aAC1C,CAAC,CAAC;YACH,MAAM,MAAM,GAAG,eAAe,CAAC;gBAC7B,EAAE,EAAE,SAAS;gBACb,OAAO,EAAE,gCAAgC;aAC1C,CAAC,CAAC;YACH,MAAM,QAAQ,GAAG,kBAAkB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;YAC5C,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAC7C,CAAC,MAAM,EAAE,MAAM,CAAC,EAChB,QAAQ,CACT,CAAC;YAEF,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,IAAI,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC;gBAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC;gBACzB,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,OAAO,CACxC,IAAI,GAAG,CAAC,CAAC,SAAS,EAAE,SAAS,CAAC,CAAC,CAChC,CAAC;gBACF,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;gBACjE,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACnE,CAAC;QACH,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,yDAAyD,EAAE,KAAK,IAAI,EAAE;YACvE,MAAM,KAAK,GAAG,eAAe,CAAC;gBAC5B,EAAE,EAAE,aAAa;gBACjB,OAAO,EAAE,sDAAsD;aAChE,CAAC,CAAC;YACH,MAAM,QAAQ,GAAG,kBAAkB,CAAC,EAAE,CAAC,CAAC;YACxC,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAAC,CAAC,KAAK,CAAC,EAAE,QAAQ,CAAC,CAAC;YAEnE,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,IAAI,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC;gBAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC;gBACzB,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;gBACtC,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACxC,CAAC;QACH,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,qDAAqD,EAAE,KAAK,IAAI,EAAE;YACnE,MAAM,QAAQ,GAAG,kBAAkB,CAAC,EAAE,CAAC,CAAC;YACxC,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAAC,EAAE,EAAE,QAAQ,CAAC,CAAC;YAE9D,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,IAAI,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC;gBAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC;gBACzB,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;gBACtC,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACxC,CAAC;QACH,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,sDAAsD,EAAE,KAAK,IAAI,EAAE;YACpE,MAAM,IAAI,GAAG,cAAc,CAAC,EAAE,EAAE,EAAE,KAAK,EAAE,UAAU,EAAE,QAAQ,EAAE,CAAC,CAAC;YACjE,MAAM,KAAK,GAAG,eAAe,CAAC;gBAC5B,EAAE,EAAE,aAAa;gBACjB,OAAO,EAAE,mCAAmC;aAC7C,CAAC,CAAC;YACH,MAAM,QAAQ,GAAG,kBAAkB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;YAC5C,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAAC,CAAC,KAAK,CAAC,EAAE,QAAQ,CAAC,CAAC;YAEnE,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,IAAI,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC;gBAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC;gBACzB,iCAAiC;gBACjC,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;gBAC/C,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;gBAChD,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,aAAa,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;YACxE,CAAC;QACH,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,sDAAsD,EAAE,KAAK,IAAI,EAAE;YACpE,MAAM,IAAI,GAAG,cAAc,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE,OAAO,EAAE,CAAC,CAAC;YAC/D,MAAM,KAAK,GAAG,eAAe,CAAC;gBAC5B,EAAE,EAAE,WAAW;gBACf,OAAO,EAAE,iDAAiD;aAC3D,CAAC,CAAC;YACH,MAAM,QAAQ,GAAG,kBAAkB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;YAC5C,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAAC,CAAC,KAAK,CAAC,EAAE,QAAQ,CAAC,CAAC;YAEnE,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,IAAI,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC;gBAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC;gBACzB,6CAA6C;gBAC7C,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,CAAC;gBACnE,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACrE,CAAC;QACH,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,2CAA2C,EAAE,KAAK,IAAI,EAAE;YACzD,MAAM,IAAI,GAAG,cAAc,CAAC,EAAE,EAAE,EAAE,KAAK,EAAE,UAAU,EAAE,QAAQ,EAAE,CAAC,CAAC;YACjE,MAAM,KAAK,GAAG,eAAe,CAAC;gBAC5B,EAAE,EAAE,eAAe;gBACnB,OAAO,EAAE;;;;;;;SAOR;aACF,CAAC,CAAC;YACH,MAAM,QAAQ,GAAG,kBAAkB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;YAC5C,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAAC,CAAC,KAAK,CAAC,EAAE,QAAQ,CAAC,CAAC;YAEnE,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,IAAI,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC;gBAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC;gBACzB,MAAM,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CACzC,IAAI,GAAG,CAAC,CAAC,eAAe,CAAC,CAAC,CAC3B,CAAC;YACJ,CAAC;QACH,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,4CAA4C,EAAE,KAAK,IAAI,EAAE;YAC1D,MAAM,IAAI,GAAG,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,UAAU,EAAE,MAAM,EAAE,CAAC,CAAC;YAC7D,MAAM,KAAK,GAAG,eAAe,CAAC;gBAC5B,EAAE,EAAE,WAAW;gBACf,OAAO,EAAE,aAAa;aACvB,CAAC,CAAC;YACH,MAAM,QAAQ,GAAG,kBAAkB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;YAC5C,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,CAAC,mBAAmB,CAAC,CAAC,KAAK,CAAC,EAAE,QAAQ,CAAC,CAAC;YAEpD,MAAM,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC,oBAAoB,CAAC,GAAG,CAAC,CAAC;QACrD,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,QAAQ,CAAC,mBAAmB,EAAE,GAAG,EAAE;QACjC,EAAE,CAAC,wDAAwD,EAAE,GAAG,EAAE;YAChE,MAAM,KAAK,GAAG;gBACZ,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC;gBAC7C,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC;aAC9C,CAAC;YACF,MAAM,GAAG,GAAmB;gBAC1B,YAAY,EAAE,IAAI,GAAG,CAAC;oBACpB,CAAC,GAAG,EAAE,IAAI,GAAG,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC;oBAC3B,CAAC,GAAG,EAAE,IAAI,GAAG,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC;iBAC5B,CAAC;gBACF,YAAY,EAAE,IAAI,GAAG,CAAC;oBACpB,CAAC,SAAS,EAAE,IAAI,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;oBAC3B,CAAC,SAAS,EAAE,IAAI,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;iBAC5B,CAAC;aACH,CAAC;YACF,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,CAAC,iBAAiB,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;YAEpD,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC3C,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC7C,MAAM,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClC,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACnC,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACrC,MAAM,CAAC,MAAM,CAAC,eAAe,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QAC3C,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,2DAA2D,EAAE,GAAG,EAAE;YACnE,MAAM,KAAK,GAAG;gBACZ,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC;gBAC7C,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC;aAC9C,CAAC;YACF,MAAM,GAAG,GAAmB;gBAC1B,YAAY,EAAE,IAAI,GAAG,EAAE;gBACvB,YAAY,EAAE,IAAI,GAAG,EAAE;aACxB,CAAC;YACF,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,CAAC,iBAAiB,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;YAEpD,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC3C,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC7C,MAAM,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClC,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACnC,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACrC,MAAM,CAAC,MAAM,CAAC,eAAe,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QACzC,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,kDAAkD,EAAE,GAAG,EAAE;YAC1D,MAAM,KAAK,GAAG;gBACZ,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,cAAc,EAAE,CAAC;gBAClD,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,gBAAgB,EAAE,CAAC;gBACpD,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,sBAAsB,EAAE,CAAC;aAC3D,CAAC;YACF,MAAM,GAAG,GAAmB;gBAC1B,YAAY,EAAE,IAAI,GAAG,CAAC;oBACpB,CAAC,GAAG,EAAE,IAAI,GAAG,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC;oBAC3B,CAAC,GAAG,EAAE,IAAI,GAAG,CAAC,CAAC,SAAS,EAAE,SAAS,CAAC,CAAC,CAAC;iBACvC,CAAC;gBACF,YAAY,EAAE,IAAI,GAAG,CAAC;oBACpB,CAAC,SAAS,EAAE,IAAI,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;oBAC3B,CAAC,SAAS,EAAE,IAAI,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;oBAC3B,CAAC,SAAS,EAAE,IAAI,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;iBAC5B,CAAC;aACH,CAAC;YACF,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,CAAC,iBAAiB,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;YAEpD,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC3C,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC7C,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,CAAE,CAAC,EAAE,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;YAC9C,MAAM,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClC,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACnC,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACrC,MAAM,CAAC,MAAM,CAAC,eAAe,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QAC1C,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,iCAAiC,EAAE,GAAG,EAAE;YACzC,MAAM,GAAG,GAAmB;gBAC1B,YAAY,EAAE,IAAI,GAAG,EAAE;gBACvB,YAAY,EAAE,IAAI,GAAG,EAAE;aACxB,CAAC;YACF,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,CAAC,iBAAiB,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC;YAEjD,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC3C,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC7C,MAAM,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClC,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACnC,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACrC,MAAM,CAAC,MAAM,CAAC,eAAe,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QACzC,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,uDAAuD,EAAE,GAAG,EAAE;YAC/D,MAAM,KAAK,GAAG;gBACZ,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,sBAAsB,EAAE,CAAC;aAC3D,CAAC;YACF,MAAM,GAAG,GAAmB;gBAC1B,YAAY,EAAE,IAAI,GAAG,CAAC,CAAC,CAAC,GAAG,EAAE,IAAI,GAAG,EAAE,CAAC,CAAC,CAAC;gBACzC,YAAY,EAAE,IAAI,GAAG,EAAE;aACxB,CAAC;YACF,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,CAAC,iBAAiB,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;YAEpD,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC3C,MAAM,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;YAC7C,MAAM,CAAC,MAAM,CAAC,eAAe,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QACzC,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,mDAAmD,EAAE,GAAG,EAAE;YAC3D,MAAM,KAAK,GAAG;gBACZ,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,CAAC;gBAC3B,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,CAAC;gBAC3B,cAAc,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,CAAC;aAC5B,CAAC;YACF,MAAM,GAAG,GAAmB;gBAC1B,YAAY,EAAE,IAAI,GAAG,CAAC,CAAC,CAAC,GAAG,EAAE,IAAI,GAAG,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC;gBACpD,YAAY,EAAE,IAAI,GAAG,CAAC,CAAC,CAAC,SAAS,EAAE,IAAI,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC;aACrD,CAAC;YACF,MAAM,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;YAEhC,MAAM,MAAM,GAAG,MAAM,CAAC,iBAAiB,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;YAEpD,iCAAiC;YACjC,MAAM,CAAC,MAAM,CAAC,eAAe,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QAC1C,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export type { BacklogItemType, BacklogItem, BacklogQuery } from './types.js';
|
|
2
|
+
export type { BacklogProvider } from './backlog-provider.js';
|
|
3
|
+
export { BacklogError } from './backlog-provider.js';
|
|
4
|
+
export { AzureDevOpsProvider } from './azure-devops-provider.js';
|
|
5
|
+
export type { AzureDevOpsConfig } from './azure-devops-provider.js';
|
|
6
|
+
export { scanForABReferences } from './ab-reference-scanner.js';
|
|
7
|
+
export { ClickUpProvider } from './clickup-provider.js';
|
|
8
|
+
export type { ClickUpConfig } from './clickup-provider.js';
|
|
9
|
+
export { scanForClickUpReferences } from './clickup-reference-scanner.js';
|
|
10
|
+
export { CodeLinker } from './code-linker.js';
|
|
11
|
+
export type { BacklogCodeMap, CoverageReport } from './code-linker.js';
|
|
12
|
+
export { JiraProvider } from './jira-provider.js';
|
|
13
|
+
export type { JiraConfig } from './jira-provider.js';
|
|
14
|
+
export { scanForJiraReferences } from './jira-reference-scanner.js';
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
export { BacklogError } from './backlog-provider.js';
|
|
2
|
+
export { AzureDevOpsProvider } from './azure-devops-provider.js';
|
|
3
|
+
export { scanForABReferences } from './ab-reference-scanner.js';
|
|
4
|
+
export { ClickUpProvider } from './clickup-provider.js';
|
|
5
|
+
export { scanForClickUpReferences } from './clickup-reference-scanner.js';
|
|
6
|
+
export { CodeLinker } from './code-linker.js';
|
|
7
|
+
export { JiraProvider } from './jira-provider.js';
|
|
8
|
+
export { scanForJiraReferences } from './jira-reference-scanner.js';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/backlog/index.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,YAAY,EAAE,MAAM,uBAAuB,CAAC;AACrD,OAAO,EAAE,mBAAmB,EAAE,MAAM,4BAA4B,CAAC;AAEjE,OAAO,EAAE,mBAAmB,EAAE,MAAM,2BAA2B,CAAC;AAChE,OAAO,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAExD,OAAO,EAAE,wBAAwB,EAAE,MAAM,gCAAgC,CAAC;AAC1E,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAE9C,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAElD,OAAO,EAAE,qBAAqB,EAAE,MAAM,6BAA6B,CAAC"}
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
import { type Result } from 'neverthrow';
|
|
2
|
+
import { BacklogError } from './backlog-provider.js';
|
|
3
|
+
import type { BacklogProvider } from './backlog-provider.js';
|
|
4
|
+
import type { BacklogItem, BacklogQuery } from './types.js';
|
|
5
|
+
/**
|
|
6
|
+
* Configuration for the Jira backlog provider.
|
|
7
|
+
*/
|
|
8
|
+
export interface JiraConfig {
|
|
9
|
+
host: string;
|
|
10
|
+
email: string;
|
|
11
|
+
apiToken: string;
|
|
12
|
+
project?: string;
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Jira backlog provider.
|
|
16
|
+
*
|
|
17
|
+
* Implements the BacklogProvider interface to index and query Jira
|
|
18
|
+
* issues (Epics, Stories, Tasks, Bugs, Sub-tasks) via the Jira REST API v3.
|
|
19
|
+
*/
|
|
20
|
+
export declare class JiraProvider implements BacklogProvider {
|
|
21
|
+
readonly name = "jira";
|
|
22
|
+
private config;
|
|
23
|
+
private baseUrl;
|
|
24
|
+
private authHeader;
|
|
25
|
+
/**
|
|
26
|
+
* Validates the config and tests the connection by fetching /rest/api/3/myself.
|
|
27
|
+
*/
|
|
28
|
+
initialize(config: Record<string, unknown>): Promise<Result<void, BacklogError>>;
|
|
29
|
+
/**
|
|
30
|
+
* Lists issues matching the given query using JQL search.
|
|
31
|
+
*/
|
|
32
|
+
getItems(query: BacklogQuery): Promise<Result<BacklogItem[], BacklogError>>;
|
|
33
|
+
/**
|
|
34
|
+
* Fetches a single issue by its key or ID.
|
|
35
|
+
*/
|
|
36
|
+
getItem(id: string): Promise<Result<BacklogItem, BacklogError>>;
|
|
37
|
+
/**
|
|
38
|
+
* Searches issues by summary and description using JQL.
|
|
39
|
+
*/
|
|
40
|
+
searchItems(text: string, limit?: number): Promise<Result<BacklogItem[], BacklogError>>;
|
|
41
|
+
/**
|
|
42
|
+
* Returns code references linked to the specified Jira issue
|
|
43
|
+
* (via issue links, development information, etc.).
|
|
44
|
+
*/
|
|
45
|
+
getLinkedCode(itemId: string): Promise<Result<string[], BacklogError>>;
|
|
46
|
+
private ensureInitialized;
|
|
47
|
+
/**
|
|
48
|
+
* Executes a JQL search query and returns the resulting issues mapped to BacklogItems.
|
|
49
|
+
*/
|
|
50
|
+
private executeJqlSearch;
|
|
51
|
+
/**
|
|
52
|
+
* Maps a raw Jira issue to a BacklogItem.
|
|
53
|
+
*/
|
|
54
|
+
private mapIssue;
|
|
55
|
+
/**
|
|
56
|
+
* Extracts code references from Jira issue links.
|
|
57
|
+
* Looks for issue links that may reference branches, commits, or pull requests.
|
|
58
|
+
*/
|
|
59
|
+
private extractCodeReferences;
|
|
60
|
+
}
|