@volar/typescript 2.2.0-alpha.0 → 2.2.0-alpha.10

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.
@@ -1,25 +1,23 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.searchExternalFiles = exports.decorateLanguageServiceHost = void 0;
4
- const language_core_1 = require("@volar/language-core");
5
4
  const resolveModuleName_1 = require("../resolveModuleName");
6
- function decorateLanguageServiceHost(language, languageServiceHost, ts) {
7
- let extraProjectVersion = 0;
8
- const exts = language.plugins
5
+ function decorateLanguageServiceHost(ts, language, languageServiceHost) {
6
+ const extensions = language.plugins
9
7
  .map(plugin => plugin.typescript?.extraFileExtensions.map(ext => '.' + ext.extension) ?? [])
10
8
  .flat();
11
9
  const scripts = new Map();
10
+ const crashFileNames = new Set();
12
11
  const readDirectory = languageServiceHost.readDirectory?.bind(languageServiceHost);
13
12
  const resolveModuleNameLiterals = languageServiceHost.resolveModuleNameLiterals?.bind(languageServiceHost);
14
13
  const resolveModuleNames = languageServiceHost.resolveModuleNames?.bind(languageServiceHost);
15
- const getProjectVersion = languageServiceHost.getProjectVersion?.bind(languageServiceHost);
16
14
  const getScriptSnapshot = languageServiceHost.getScriptSnapshot.bind(languageServiceHost);
17
15
  const getScriptKind = languageServiceHost.getScriptKind?.bind(languageServiceHost);
18
16
  // path completion
19
17
  if (readDirectory) {
20
18
  languageServiceHost.readDirectory = (path, extensions, exclude, include, depth) => {
21
19
  if (extensions) {
22
- for (const ext of exts) {
20
+ for (const ext of extensions) {
23
21
  if (!extensions.includes(ext)) {
24
22
  extensions = [...extensions, ...ext];
25
23
  }
@@ -28,91 +26,88 @@ function decorateLanguageServiceHost(language, languageServiceHost, ts) {
28
26
  return readDirectory(path, extensions, exclude, include, depth);
29
27
  };
30
28
  }
31
- if (language.plugins.some(language => language.typescript?.extraFileExtensions.length)) {
29
+ if (extensions.length) {
32
30
  const resolveModuleName = (0, resolveModuleName_1.createResolveModuleName)(ts, languageServiceHost, language.plugins, fileName => language.scripts.get(fileName));
31
+ const getCanonicalFileName = languageServiceHost.useCaseSensitiveFileNames?.()
32
+ ? (fileName) => fileName
33
+ : (fileName) => fileName.toLowerCase();
34
+ const moduleResolutionCache = ts.createModuleResolutionCache(languageServiceHost.getCurrentDirectory(), getCanonicalFileName, languageServiceHost.getCompilationSettings());
33
35
  if (resolveModuleNameLiterals) {
34
36
  languageServiceHost.resolveModuleNameLiterals = (moduleLiterals, containingFile, redirectedReference, options, ...rest) => {
35
- if (moduleLiterals.every(name => !exts.some(ext => name.text.endsWith(ext)))) {
37
+ if (moduleLiterals.every(name => !extensions.some(ext => name.text.endsWith(ext)))) {
36
38
  return resolveModuleNameLiterals(moduleLiterals, containingFile, redirectedReference, options, ...rest);
37
39
  }
38
40
  return moduleLiterals.map(moduleLiteral => {
39
- return resolveModuleName(moduleLiteral.text, containingFile, options, undefined, redirectedReference);
41
+ return resolveModuleName(moduleLiteral.text, containingFile, options, moduleResolutionCache, redirectedReference);
40
42
  });
41
43
  };
42
44
  }
43
45
  if (resolveModuleNames) {
44
46
  languageServiceHost.resolveModuleNames = (moduleNames, containingFile, reusedNames, redirectedReference, options, containingSourceFile) => {
45
- if (moduleNames.every(name => !exts.some(ext => name.endsWith(ext)))) {
47
+ if (moduleNames.every(name => !extensions.some(ext => name.endsWith(ext)))) {
46
48
  return resolveModuleNames(moduleNames, containingFile, reusedNames, redirectedReference, options, containingSourceFile);
47
49
  }
48
50
  return moduleNames.map(moduleName => {
49
- return resolveModuleName(moduleName, containingFile, options, undefined, redirectedReference).resolvedModule;
51
+ return resolveModuleName(moduleName, containingFile, options, moduleResolutionCache, redirectedReference).resolvedModule;
50
52
  });
51
53
  };
52
54
  }
53
55
  }
54
- if (getProjectVersion) {
55
- languageServiceHost.getProjectVersion = () => {
56
- return getProjectVersion() + ':' + extraProjectVersion;
57
- };
58
- }
59
56
  languageServiceHost.getScriptSnapshot = fileName => {
60
- if (exts.some(ext => fileName.endsWith(ext))) {
61
- updateScript(fileName);
62
- return scripts.get(fileName)?.snapshot;
57
+ const virtualScript = updateVirtualScript(fileName);
58
+ if (virtualScript) {
59
+ return virtualScript.snapshot;
63
60
  }
64
61
  return getScriptSnapshot(fileName);
65
62
  };
66
63
  if (getScriptKind) {
67
64
  languageServiceHost.getScriptKind = fileName => {
68
- if (exts.some(ext => fileName.endsWith(ext))) {
69
- updateScript(fileName);
70
- const script = scripts.get(fileName);
71
- if (script) {
72
- return script.kind;
73
- }
74
- return ts.ScriptKind.Deferred;
65
+ const virtualScript = updateVirtualScript(fileName);
66
+ if (virtualScript) {
67
+ return virtualScript.kind;
75
68
  }
76
69
  return getScriptKind(fileName);
77
70
  };
78
71
  }
79
- function updateScript(fileName) {
80
- const version = languageServiceHost.getScriptVersion(fileName);
81
- if (version !== scripts.get(fileName)?.version) {
82
- let extension = '.ts';
83
- let snapshotSnapshot;
84
- let scriptKind = ts.ScriptKind.TS;
85
- const snapshot = getScriptSnapshot(fileName);
86
- if (snapshot) {
87
- extraProjectVersion++;
88
- const sourceScript = language.scripts.set(fileName, (0, language_core_1.resolveCommonLanguageId)(fileName), snapshot);
89
- if (sourceScript.generated) {
90
- const text = snapshot.getText(0, snapshot.getLength());
91
- let patchedText = text.split('\n').map(line => ' '.repeat(line.length)).join('\n');
92
- const serviceScript = sourceScript.generated.languagePlugin.typescript?.getServiceScript(sourceScript.generated.root);
93
- if (serviceScript) {
94
- extension = serviceScript.extension;
95
- scriptKind = serviceScript.scriptKind;
96
- patchedText += serviceScript.code.snapshot.getText(0, serviceScript.code.snapshot.getLength());
97
- }
98
- snapshotSnapshot = ts.ScriptSnapshot.fromString(patchedText);
99
- if (sourceScript.generated.languagePlugin.typescript?.getExtraServiceScripts) {
100
- console.warn('getExtraScripts() is not available in this use case.');
101
- }
72
+ function updateVirtualScript(fileName) {
73
+ if (crashFileNames.has(fileName)) {
74
+ return;
75
+ }
76
+ let version;
77
+ try {
78
+ version = languageServiceHost.getScriptVersion(fileName);
79
+ }
80
+ catch {
81
+ // fix https://github.com/vuejs/language-tools/issues/4278
82
+ crashFileNames.add(fileName);
83
+ }
84
+ if (version === undefined) {
85
+ // somehow getScriptVersion returns undefined
86
+ return;
87
+ }
88
+ let script = scripts.get(fileName);
89
+ if (!script || script[0] !== version) {
90
+ script = [version];
91
+ const sourceScript = language.scripts.get(fileName);
92
+ if (sourceScript?.generated) {
93
+ const serviceScript = sourceScript.generated.languagePlugin.typescript?.getServiceScript(sourceScript.generated.root);
94
+ if (serviceScript) {
95
+ const sourceContents = sourceScript.snapshot.getText(0, sourceScript.snapshot.getLength());
96
+ let virtualContents = sourceContents.split('\n').map(line => ' '.repeat(line.length)).join('\n');
97
+ virtualContents += serviceScript.code.snapshot.getText(0, serviceScript.code.snapshot.getLength());
98
+ script[1] = {
99
+ extension: serviceScript.extension,
100
+ kind: serviceScript.scriptKind,
101
+ snapshot: ts.ScriptSnapshot.fromString(virtualContents),
102
+ };
103
+ }
104
+ if (sourceScript.generated.languagePlugin.typescript?.getExtraServiceScripts) {
105
+ console.warn('getExtraServiceScripts() is not available in TS plugin.');
102
106
  }
103
107
  }
104
- else if (language.scripts.get(fileName)) {
105
- extraProjectVersion++;
106
- language.scripts.delete(fileName);
107
- }
108
- scripts.set(fileName, {
109
- version,
110
- extension,
111
- snapshot: snapshotSnapshot,
112
- kind: scriptKind,
113
- });
108
+ scripts.set(fileName, script);
114
109
  }
115
- return scripts.get(fileName);
110
+ return script[1];
116
111
  }
117
112
  }
118
113
  exports.decorateLanguageServiceHost = decorateLanguageServiceHost;
@@ -9,6 +9,7 @@ function decorateProgram(language, program) {
9
9
  const getSyntacticDiagnostics = program.getSyntacticDiagnostics;
10
10
  const getSemanticDiagnostics = program.getSemanticDiagnostics;
11
11
  const getGlobalDiagnostics = program.getGlobalDiagnostics;
12
+ const getSourceFileByPath = program.getSourceFileByPath;
12
13
  // for tsc --noEmit --watch
13
14
  // @ts-ignore
14
15
  const getBindAndCheckDiagnostics = program.getBindAndCheckDiagnostics;
@@ -17,31 +18,39 @@ function decorateProgram(language, program) {
17
18
  return {
18
19
  ...result,
19
20
  diagnostics: result.diagnostics
20
- .map(d => (0, transform_1.transformDiagnostic)(language, d))
21
+ .map(d => (0, transform_1.transformDiagnostic)(language, d, true))
21
22
  .filter(utils_1.notEmpty),
22
23
  };
23
24
  };
24
25
  program.getSyntacticDiagnostics = (sourceFile, cancellationToken) => {
25
26
  return getSyntacticDiagnostics(sourceFile, cancellationToken)
26
- .map(d => (0, transform_1.transformDiagnostic)(language, d))
27
+ .map(d => (0, transform_1.transformDiagnostic)(language, d, true))
27
28
  .filter(utils_1.notEmpty);
28
29
  };
29
30
  program.getSemanticDiagnostics = (sourceFile, cancellationToken) => {
30
31
  return getSemanticDiagnostics(sourceFile, cancellationToken)
31
- .map(d => (0, transform_1.transformDiagnostic)(language, d))
32
+ .map(d => (0, transform_1.transformDiagnostic)(language, d, true))
32
33
  .filter(utils_1.notEmpty);
33
34
  };
34
35
  program.getGlobalDiagnostics = cancellationToken => {
35
36
  return getGlobalDiagnostics(cancellationToken)
36
- .map(d => (0, transform_1.transformDiagnostic)(language, d))
37
+ .map(d => (0, transform_1.transformDiagnostic)(language, d, true))
37
38
  .filter(utils_1.notEmpty);
38
39
  };
39
40
  // @ts-ignore
40
41
  program.getBindAndCheckDiagnostics = (sourceFile, cancellationToken) => {
41
42
  return getBindAndCheckDiagnostics(sourceFile, cancellationToken)
42
- .map(d => (0, transform_1.transformDiagnostic)(language, d))
43
+ .map(d => (0, transform_1.transformDiagnostic)(language, d, true))
43
44
  .filter(utils_1.notEmpty);
44
45
  };
46
+ // fix https://github.com/vuejs/language-tools/issues/4099 with `incremental`
47
+ program.getSourceFileByPath = path => {
48
+ const sourceFile = getSourceFileByPath(path);
49
+ if (sourceFile) {
50
+ (0, transform_1.fillSourceFileText)(language, sourceFile);
51
+ }
52
+ return sourceFile;
53
+ };
45
54
  }
46
55
  exports.decorateProgram = decorateProgram;
47
56
  //# sourceMappingURL=decorateProgram.js.map
@@ -1,3 +1,2 @@
1
1
  import type * as ts from 'typescript';
2
- export declare function dedupeReferencedSymbols<T extends ts.ReferencedSymbol>(items: T[]): T[];
3
2
  export declare function dedupeDocumentSpans<T extends ts.DocumentSpan>(items: T[]): T[];
@@ -1,14 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.dedupeDocumentSpans = exports.dedupeReferencedSymbols = void 0;
4
- function dedupeReferencedSymbols(items) {
5
- return dedupe(items, item => [
6
- item.definition.fileName,
7
- item.definition.textSpan.start,
8
- item.definition.textSpan.length,
9
- ].join(':'));
10
- }
11
- exports.dedupeReferencedSymbols = dedupeReferencedSymbols;
3
+ exports.dedupeDocumentSpans = void 0;
12
4
  function dedupeDocumentSpans(items) {
13
5
  return dedupe(items, item => [
14
6
  item.fileName,
@@ -1,3 +1,3 @@
1
- import type * as ts from 'typescript';
2
1
  import { LanguagePlugin } from '@volar/language-core';
3
- export declare function proxyCreateProgram(ts: typeof import('typescript'), original: typeof ts['createProgram'], extensions: string[], getLanguagePlugins: (ts: typeof import('typescript'), options: ts.CreateProgramOptions) => LanguagePlugin[]): typeof import("typescript").createProgram;
2
+ import type * as ts from 'typescript';
3
+ export declare function proxyCreateProgram(ts: typeof import('typescript'), original: typeof ts['createProgram'], getLanguagePlugins: (ts: typeof import('typescript'), options: ts.CreateProgramOptions) => LanguagePlugin[], getLanguageId: (fileName: string) => string): typeof import("typescript").createProgram;
@@ -1,117 +1,161 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.proxyCreateProgram = void 0;
4
- const decorateProgram_1 = require("./decorateProgram");
5
4
  const language_core_1 = require("@volar/language-core");
6
- function proxyCreateProgram(ts, original, extensions, getLanguagePlugins) {
5
+ const resolveModuleName_1 = require("../resolveModuleName");
6
+ const decorateProgram_1 = require("./decorateProgram");
7
+ const arrayEqual = (a, b) => {
8
+ if (a.length !== b.length) {
9
+ return false;
10
+ }
11
+ for (let i = 0; i < a.length; i++) {
12
+ if (a[i] !== b[i]) {
13
+ return false;
14
+ }
15
+ }
16
+ return true;
17
+ };
18
+ const objectEqual = (a, b) => {
19
+ const keysA = Object.keys(a);
20
+ const keysB = Object.keys(b);
21
+ if (keysA.length !== keysB.length) {
22
+ return false;
23
+ }
24
+ for (const key of keysA) {
25
+ if (a[key] !== b[key]) {
26
+ return false;
27
+ }
28
+ }
29
+ return true;
30
+ };
31
+ function proxyCreateProgram(ts, original, getLanguagePlugins, getLanguageId) {
32
+ const sourceFileSnapshots = new Map();
33
+ const parsedSourceFiles = new WeakMap();
34
+ let lastOptions;
35
+ let languagePlugins;
36
+ let language;
37
+ let moduleResolutionCache;
7
38
  return new Proxy(original, {
8
39
  apply: (target, thisArg, args) => {
9
40
  const options = args[0];
10
41
  assert(!!options.host, '!!options.host');
11
- const sourceFileToSnapshotMap = new WeakMap();
12
- const language = (0, language_core_1.createLanguage)(getLanguagePlugins(ts, options), ts.sys.useCaseSensitiveFileNames, fileName => {
13
- let snapshot;
14
- assert(originalSourceFiles.has(fileName), `originalSourceFiles.has(${fileName})`);
15
- const sourceFile = originalSourceFiles.get(fileName);
16
- if (sourceFile) {
17
- snapshot = sourceFileToSnapshotMap.get(sourceFile);
18
- if (!snapshot) {
19
- snapshot = {
20
- getChangeRange() {
21
- return undefined;
22
- },
23
- getLength() {
24
- return sourceFile.text.length;
25
- },
26
- getText(start, end) {
27
- return sourceFile.text.substring(start, end);
28
- },
29
- };
30
- sourceFileToSnapshotMap.set(sourceFile, snapshot);
31
- }
32
- }
33
- if (snapshot) {
34
- language.scripts.set(fileName, (0, language_core_1.resolveCommonLanguageId)(fileName), snapshot);
35
- }
36
- else {
37
- language.scripts.delete(fileName);
38
- }
39
- });
40
- const originalSourceFiles = new Map();
41
- const parsedSourceFiles = new WeakMap();
42
- const arbitraryExtensions = extensions.map(ext => `.d${ext}.ts`);
43
- const originalHost = options.host;
44
- const moduleResolutionHost = {
45
- ...originalHost,
46
- fileExists(fileName) {
47
- for (let i = 0; i < arbitraryExtensions.length; i++) {
48
- if (fileName.endsWith(arbitraryExtensions[i])) {
49
- return originalHost.fileExists(fileName.slice(0, -arbitraryExtensions[i].length) + extensions[i]);
42
+ if (!lastOptions
43
+ || !languagePlugins
44
+ || !language
45
+ || !arrayEqual(options.rootNames, lastOptions.rootNames)
46
+ || !objectEqual(options.options, lastOptions.options)) {
47
+ moduleResolutionCache = ts.createModuleResolutionCache(options.host.getCurrentDirectory(), options.host.getCanonicalFileName, options.options);
48
+ lastOptions = options;
49
+ languagePlugins = getLanguagePlugins(ts, options);
50
+ language = (0, language_core_1.createLanguage)(languagePlugins, ts.sys.useCaseSensitiveFileNames, fileName => {
51
+ if (!sourceFileSnapshots.has(fileName)) {
52
+ const sourceFileText = originalHost.readFile(fileName);
53
+ if (sourceFileText !== undefined) {
54
+ sourceFileSnapshots.set(fileName, [undefined, {
55
+ getChangeRange() {
56
+ return undefined;
57
+ },
58
+ getLength() {
59
+ return sourceFileText.length;
60
+ },
61
+ getText(start, end) {
62
+ return sourceFileText.substring(start, end);
63
+ },
64
+ }]);
65
+ }
66
+ else {
67
+ sourceFileSnapshots.set(fileName, [undefined, undefined]);
50
68
  }
51
69
  }
52
- return originalHost.fileExists(fileName);
53
- },
54
- };
70
+ const snapshot = sourceFileSnapshots.get(fileName)?.[1];
71
+ if (snapshot) {
72
+ language.scripts.set(fileName, getLanguageId(fileName), snapshot);
73
+ }
74
+ else {
75
+ language.scripts.delete(fileName);
76
+ }
77
+ });
78
+ }
79
+ const originalHost = options.host;
80
+ const extensions = languagePlugins
81
+ .map(plugin => plugin.typescript?.extraFileExtensions.map(({ extension }) => `.${extension}`) ?? [])
82
+ .flat();
55
83
  options.host = { ...originalHost };
56
- options.options.allowArbitraryExtensions = true;
57
84
  options.host.getSourceFile = (fileName, languageVersionOrOptions, onError, shouldCreateNewSourceFile) => {
58
85
  const originalSourceFile = originalHost.getSourceFile(fileName, languageVersionOrOptions, onError, shouldCreateNewSourceFile);
59
- originalSourceFiles.set(fileName, originalSourceFile);
60
- if (originalSourceFile && extensions.some(ext => fileName.endsWith(ext))) {
61
- let sourceFile2 = parsedSourceFiles.get(originalSourceFile);
62
- if (!sourceFile2) {
63
- const sourceScript = language.scripts.get(fileName);
64
- assert(!!sourceScript, '!!sourceScript');
65
- let patchedText = originalSourceFile.text.split('\n').map(line => ' '.repeat(line.length)).join('\n');
66
- let scriptKind = ts.ScriptKind.TS;
67
- if (sourceScript.generated?.languagePlugin.typescript) {
68
- const { getServiceScript: getScript, getExtraServiceScripts: getExtraScripts } = sourceScript.generated.languagePlugin.typescript;
69
- const serviceScript = getScript(sourceScript.generated.root);
70
- if (serviceScript) {
71
- scriptKind = serviceScript.scriptKind;
72
- patchedText += serviceScript.code.snapshot.getText(0, serviceScript.code.snapshot.getLength());
73
- }
74
- if (getExtraScripts) {
75
- console.warn('getExtraScripts() is not available in this use case.');
76
- }
86
+ if (!sourceFileSnapshots.has(fileName)
87
+ || sourceFileSnapshots.get(fileName)?.[0] !== originalSourceFile) {
88
+ if (originalSourceFile) {
89
+ sourceFileSnapshots.set(fileName, [originalSourceFile, {
90
+ getChangeRange() {
91
+ return undefined;
92
+ },
93
+ getLength() {
94
+ return originalSourceFile.text.length;
95
+ },
96
+ getText(start, end) {
97
+ return originalSourceFile.text.substring(start, end);
98
+ },
99
+ }]);
100
+ }
101
+ else {
102
+ sourceFileSnapshots.set(fileName, [undefined, undefined]);
103
+ }
104
+ }
105
+ if (!originalSourceFile) {
106
+ return;
107
+ }
108
+ if (!parsedSourceFiles.has(originalSourceFile)) {
109
+ const sourceScript = language.scripts.get(fileName);
110
+ assert(!!sourceScript, '!!sourceScript');
111
+ parsedSourceFiles.set(originalSourceFile, originalSourceFile);
112
+ if (sourceScript.generated?.languagePlugin.typescript) {
113
+ const { getServiceScript, getExtraServiceScripts } = sourceScript.generated.languagePlugin.typescript;
114
+ const serviceScript = getServiceScript(sourceScript.generated.root);
115
+ if (serviceScript) {
116
+ let patchedText = originalSourceFile.text.split('\n').map(line => ' '.repeat(line.length)).join('\n');
117
+ let scriptKind = ts.ScriptKind.TS;
118
+ scriptKind = serviceScript.scriptKind;
119
+ patchedText += serviceScript.code.snapshot.getText(0, serviceScript.code.snapshot.getLength());
120
+ const parsedSourceFile = ts.createSourceFile(fileName, patchedText, languageVersionOrOptions, undefined, scriptKind);
121
+ // @ts-expect-error
122
+ parsedSourceFile.version = originalSourceFile.version;
123
+ parsedSourceFiles.set(originalSourceFile, parsedSourceFile);
124
+ }
125
+ if (getExtraServiceScripts) {
126
+ console.warn('getExtraServiceScripts() is not available in this use case.');
77
127
  }
78
- sourceFile2 = ts.createSourceFile(fileName, patchedText, 99, true, scriptKind);
79
- // @ts-expect-error
80
- sourceFile2.version = originalSourceFile.version;
81
- parsedSourceFiles.set(originalSourceFile, sourceFile2);
82
128
  }
83
- return sourceFile2;
84
129
  }
85
- return originalSourceFile;
86
- };
87
- options.host.resolveModuleNameLiterals = (moduleNames, containingFile, redirectedReference, options) => {
88
- return moduleNames.map(name => {
89
- return resolveModuleName(name.text, containingFile, options, redirectedReference);
90
- });
130
+ return parsedSourceFiles.get(originalSourceFile);
91
131
  };
92
- options.host.resolveModuleNames = (moduleNames, containingFile, _reusedNames, redirectedReference, options) => {
93
- return moduleNames.map(name => {
94
- return resolveModuleName(name, containingFile, options, redirectedReference).resolvedModule;
95
- });
96
- };
97
- const program = Reflect.apply(target, thisArg, [options]);
132
+ if (extensions.length) {
133
+ options.options.allowArbitraryExtensions = true;
134
+ const resolveModuleName = (0, resolveModuleName_1.createResolveModuleName)(ts, originalHost, language.plugins, fileName => language.scripts.get(fileName));
135
+ const resolveModuleNameLiterals = originalHost.resolveModuleNameLiterals;
136
+ const resolveModuleNames = originalHost.resolveModuleNames;
137
+ options.host.resolveModuleNameLiterals = (moduleLiterals, containingFile, redirectedReference, compilerOptions, ...rest) => {
138
+ if (resolveModuleNameLiterals && moduleLiterals.every(name => !extensions.some(ext => name.text.endsWith(ext)))) {
139
+ return resolveModuleNameLiterals(moduleLiterals, containingFile, redirectedReference, compilerOptions, ...rest);
140
+ }
141
+ return moduleLiterals.map(moduleLiteral => {
142
+ return resolveModuleName(moduleLiteral.text, containingFile, compilerOptions, moduleResolutionCache, redirectedReference);
143
+ });
144
+ };
145
+ options.host.resolveModuleNames = (moduleNames, containingFile, reusedNames, redirectedReference, compilerOptions, containingSourceFile) => {
146
+ if (resolveModuleNames && moduleNames.every(name => !extensions.some(ext => name.endsWith(ext)))) {
147
+ return resolveModuleNames(moduleNames, containingFile, reusedNames, redirectedReference, compilerOptions, containingSourceFile);
148
+ }
149
+ return moduleNames.map(moduleName => {
150
+ return resolveModuleName(moduleName, containingFile, compilerOptions, moduleResolutionCache, redirectedReference).resolvedModule;
151
+ });
152
+ };
153
+ }
154
+ const program = Reflect.apply(target, thisArg, args);
98
155
  (0, decorateProgram_1.decorateProgram)(language, program);
99
156
  // TODO: #128
100
- program.__volar__ = { files: language };
157
+ program.__volar__ = { language };
101
158
  return program;
102
- function resolveModuleName(name, containingFile, options, redirectedReference) {
103
- const resolved = ts.resolveModuleName(name, containingFile, options, moduleResolutionHost, originalHost.getModuleResolutionCache?.(), redirectedReference);
104
- if (resolved.resolvedModule) {
105
- for (let i = 0; i < arbitraryExtensions.length; i++) {
106
- if (resolved.resolvedModule.resolvedFileName.endsWith(arbitraryExtensions[i])) {
107
- const sourceFileName = resolved.resolvedModule.resolvedFileName.slice(0, -arbitraryExtensions[i].length) + extensions[i];
108
- resolved.resolvedModule.resolvedFileName = sourceFileName;
109
- resolved.resolvedModule.extension = extensions[i];
110
- }
111
- }
112
- }
113
- return resolved;
114
- }
115
159
  },
116
160
  });
117
161
  }
@@ -1,10 +1,15 @@
1
- import { Language, CodeInformation } from '@volar/language-core';
1
+ import { Language, CodeInformation, SourceMap, SourceScript } from '@volar/language-core';
2
2
  import type * as ts from 'typescript';
3
- export declare function transformCallHierarchyItem(files: Language, item: ts.CallHierarchyItem, filter: (data: CodeInformation) => boolean): ts.CallHierarchyItem;
4
- export declare function transformDiagnostic<T extends ts.Diagnostic>(files: Language, diagnostic: T): T | undefined;
5
- export declare function transformFileTextChanges(files: Language, changes: ts.FileTextChanges, filter: (data: CodeInformation) => boolean): ts.FileTextChanges | undefined;
6
- export declare function transformDocumentSpan<T extends ts.DocumentSpan>(files: Language, documentSpan: T, filter: (data: CodeInformation) => boolean, shouldFallback?: boolean): T | undefined;
7
- export declare function transformSpan(files: Language, fileName: string | undefined, textSpan: ts.TextSpan | undefined, filter: (data: CodeInformation) => boolean): {
3
+ export declare function transformCallHierarchyItem(language: Language, item: ts.CallHierarchyItem, filter: (data: CodeInformation) => boolean): ts.CallHierarchyItem;
4
+ export declare function transformDiagnostic<T extends ts.Diagnostic>(language: Language, diagnostic: T, isTsc: boolean): T | undefined;
5
+ export declare function fillSourceFileText(language: Language, sourceFile: ts.SourceFile): void;
6
+ export declare function transformFileTextChanges(language: Language, changes: ts.FileTextChanges, filter: (data: CodeInformation) => boolean): ts.FileTextChanges | undefined;
7
+ export declare function transformDocumentSpan<T extends ts.DocumentSpan>(language: Language, documentSpan: T, filter: (data: CodeInformation) => boolean, shouldFallback?: boolean): T | undefined;
8
+ export declare function transformSpan(language: Language, fileName: string | undefined, textSpan: ts.TextSpan | undefined, filter: (data: CodeInformation) => boolean): {
8
9
  fileName: string;
9
10
  textSpan: ts.TextSpan;
10
11
  } | undefined;
12
+ export declare function transformTextChange(sourceScript: SourceScript, map: SourceMap<CodeInformation>, textChange: ts.TextChange, filter: (data: CodeInformation) => boolean): ts.TextChange | undefined;
13
+ export declare function transformTextSpan(sourceScript: SourceScript, map: SourceMap<CodeInformation>, textSpan: ts.TextSpan, filter: (data: CodeInformation) => boolean): ts.TextSpan | undefined;
14
+ export declare function toSourceOffset(sourceScript: SourceScript, map: SourceMap, position: number, filter: (data: CodeInformation) => boolean): number | undefined;
15
+ export declare function toGeneratedOffset(sourceScript: SourceScript, map: SourceMap, position: number, filter: (data: CodeInformation) => boolean): number | undefined;