* Parse and extract from the source code
()
| 567 | * Parse and extract from the source code |
| 568 | */ |
| 569 | extract(): ExtractionResult { |
| 570 | const startTime = Date.now(); |
| 571 | |
| 572 | if (!isLanguageSupported(this.language)) { |
| 573 | return { |
| 574 | nodes: [], |
| 575 | edges: [], |
| 576 | unresolvedReferences: [], |
| 577 | errors: [ |
| 578 | { |
| 579 | message: `Unsupported language: ${this.language}`, |
| 580 | filePath: this.filePath, |
| 581 | severity: 'error', |
| 582 | code: 'unsupported_language', |
| 583 | }, |
| 584 | ], |
| 585 | durationMs: Date.now() - startTime, |
| 586 | }; |
| 587 | } |
| 588 | |
| 589 | const parser = getParser(this.language); |
| 590 | if (!parser) { |
| 591 | return { |
| 592 | nodes: [], |
| 593 | edges: [], |
| 594 | unresolvedReferences: [], |
| 595 | errors: [ |
| 596 | { |
| 597 | message: `Failed to get parser for language: ${this.language}`, |
| 598 | filePath: this.filePath, |
| 599 | severity: 'error', |
| 600 | code: 'parser_error', |
| 601 | }, |
| 602 | ], |
| 603 | durationMs: Date.now() - startTime, |
| 604 | }; |
| 605 | } |
| 606 | |
| 607 | try { |
| 608 | // Optional pre-parse source transform (offset-preserving) to work around |
| 609 | // grammar gaps — e.g. C# blanks conditional-compilation directive lines |
| 610 | // the grammar mis-parses inside enum bodies (#237). We reassign |
| 611 | // this.source so downstream getNodeText reads the same bytes the parser |
| 612 | // saw (identical outside the blanked directive lines). Skipped when the |
| 613 | // kernel route point already applied it (sourceIsPreParsed). |
| 614 | if (this.extractor?.preParse && !this.sourceIsPreParsed) { |
| 615 | this.source = this.extractor.preParse(this.source, this.filePath); |
| 616 | } |
| 617 | this.tree = parser.parse(this.source) ?? null; |
| 618 | if (!this.tree) { |
| 619 | throw new Error('Parser returned null tree'); |
| 620 | } |
| 621 | |
| 622 | // Create file node representing the source file |
| 623 | const fileNode: Node = { |
| 624 | id: `file:${this.filePath}`, |
| 625 | kind: 'file', |
| 626 | name: path.basename(this.filePath), |
no test coverage detected