Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit 5272ec6

Browse filesBrowse files
committed
Types Map WIP
1 parent 70e5c6b commit 5272ec6
Copy full SHA for 5272ec6

12 files changed

+642-40Lines changed: 642 additions & 40 deletions

File tree

Expand file treeCollapse file tree
Open diff view settings
Filter options
Expand file treeCollapse file tree
Open diff view settings
Collapse file

‎Gulpfile.ts‎

Copy file name to clipboardExpand all lines: Gulpfile.ts
+19-2Lines changed: 19 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -464,6 +464,7 @@ gulp.task(serverFile, /*help*/ false, [servicesFile, typingsInstallerJs, cancell
464464
.pipe(gulp.dest("src/server"));
465465
});
466466

467+
const typesMapJson = path.join(builtLocalDirectory, "typesMap.json");
467468
const tsserverLibraryFile = path.join(builtLocalDirectory, "tsserverlibrary.js");
468469
const tsserverLibraryDefinitionFile = path.join(builtLocalDirectory, "tsserverlibrary.d.ts");
469470

@@ -473,7 +474,7 @@ gulp.task(tsserverLibraryFile, /*help*/ false, [servicesFile], (done) => {
473474
.pipe(sourcemaps.init())
474475
.pipe(newer(tsserverLibraryFile))
475476
.pipe(serverLibraryProject());
476-
477+
477478
return merge2([
478479
js.pipe(prependCopyright())
479480
.pipe(sourcemaps.write("."))
@@ -486,7 +487,23 @@ gulp.task(tsserverLibraryFile, /*help*/ false, [servicesFile], (done) => {
486487
]);
487488
});
488489

489-
gulp.task("lssl", "Builds language service server library", [tsserverLibraryFile]);
490+
gulp.task(typesMapJson, /*help*/ false, [], (done) => {
491+
fs.readFile('src/server/typesMaps.json', 'utf-8', (err, data) => {
492+
if (err) {
493+
return done(err);
494+
}
495+
try {
496+
JSON.parse(data);
497+
} catch (e) {
498+
done(e);
499+
}
500+
fs.writeFile(typesMapJson, data, err => {
501+
done(err);
502+
});
503+
});
504+
});
505+
506+
gulp.task("lssl", "Builds language service server library", [tsserverLibraryFile, typesMapJson]);
490507
gulp.task("local", "Builds the full compiler and services", [builtLocalCompiler, servicesFile, serverFile, builtGeneratedDiagnosticMessagesJSON, tsserverLibraryFile]);
491508
gulp.task("tsc", "Builds only the compiler", [builtLocalCompiler]);
492509

Collapse file

‎Jakefile.js‎

Copy file name to clipboardExpand all lines: Jakefile.js
+14-2Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,8 @@ var watchGuardSources = filesFromConfig(path.join(serverDirectory, "watchGuard/t
8888
var serverSources = filesFromConfig(path.join(serverDirectory, "tsconfig.json"))
8989
var languageServiceLibrarySources = filesFromConfig(path.join(serverDirectory, "tsconfig.library.json"));
9090

91+
var typesMapOutputPath = path.join(builtLocalDirectory, 'typesMap.json');
92+
9193
var harnessCoreSources = [
9294
"harness.ts",
9395
"virtualFileSystem.ts",
@@ -422,6 +424,7 @@ var buildProtocolTs = path.join(scriptsDirectory, "buildProtocol.ts");
422424
var buildProtocolJs = path.join(scriptsDirectory, "buildProtocol.js");
423425
var buildProtocolDts = path.join(builtLocalDirectory, "protocol.d.ts");
424426
var typescriptServicesDts = path.join(builtLocalDirectory, "typescriptServices.d.ts");
427+
var typesMapJson = path.join(builtLocalDirectory, "typesMap.json");
425428

426429
file(buildProtocolTs);
427430

@@ -603,6 +606,16 @@ var serverFile = path.join(builtLocalDirectory, "tsserver.js");
603606
compileFile(serverFile, serverSources, [builtLocalDirectory, copyright, cancellationTokenFile, typingsInstallerFile, watchGuardFile].concat(serverSources).concat(servicesSources), /*prefixes*/ [copyright], /*useBuiltCompiler*/ true, { types: ["node"], preserveConstEnums: true, lib: "es6" });
604607
var tsserverLibraryFile = path.join(builtLocalDirectory, "tsserverlibrary.js");
605608
var tsserverLibraryDefinitionFile = path.join(builtLocalDirectory, "tsserverlibrary.d.ts");
609+
file(typesMapOutputPath, function() {
610+
var content = fs.readFileSync(path.join(serverDirectory, 'typesMap.json'));
611+
// Validate that it's valid JSON
612+
try {
613+
JSON.parse(content);
614+
} catch (e) {
615+
console.log("Parse error in typesMap.json: " + e);
616+
}
617+
fs.writeFileSync(typesMapOutputPath, content);
618+
});
606619
compileFile(
607620
tsserverLibraryFile,
608621
languageServiceLibrarySources,
@@ -625,7 +638,7 @@ compileFile(
625638

626639
// Local target to build the language service server library
627640
desc("Builds language service server library");
628-
task("lssl", [tsserverLibraryFile, tsserverLibraryDefinitionFile]);
641+
task("lssl", [tsserverLibraryFile, tsserverLibraryDefinitionFile, typesMapOutputPath]);
629642

630643
desc("Emit the start of the build fold");
631644
task("build-fold-start", [], function () {
@@ -654,7 +667,6 @@ task("release", function () {
654667
// Set the default task to "local"
655668
task("default", ["local"]);
656669

657-
658670
// Cleans the built directory
659671
desc("Cleans the compiler output, declare files, and tests");
660672
task("clean", function () {
Collapse file

‎src/harness/unittests/tsserverProjectSystem.ts‎

Copy file name to clipboardExpand all lines: src/harness/unittests/tsserverProjectSystem.ts
+21-12Lines changed: 21 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -18,14 +18,24 @@ namespace ts.projectSystem {
1818
})
1919
};
2020

21-
const customSafeList = {
22-
path: <Path>"/typeMapList.json",
23-
content: JSON.stringify({
24-
"quack": {
25-
"match": "/duckquack-(\\d+)\\.min\\.js",
26-
"types": ["duck-types"]
21+
const customTypesMap = {
22+
path: <Path>"/typesMap.json",
23+
content: `{
24+
"typesMap": {
25+
"jquery": {
26+
"match": "jquery(-(\\\\.?\\\\d+)+)?(\\\\.intellisense)?(\\\\.min)?\\\\.js$",
27+
"types": ["jquery"]
28+
},
29+
"quack": {
30+
"match": "/duckquack-(\\\\d+)\\\\.min\\\\.js",
31+
"types": ["duck-types"]
32+
}
2733
},
28-
})
34+
"simpleMap": {
35+
"Bacon": "baconjs",
36+
"bliss": "blissfuljs"
37+
}
38+
}`
2939
};
3040

3141
export interface PostExecAction {
@@ -59,7 +69,7 @@ namespace ts.projectSystem {
5969
installTypingHost: server.ServerHost,
6070
readonly typesRegistry = createMap<void>(),
6171
log?: TI.Log) {
62-
super(installTypingHost, globalTypingsCacheLocation, safeList.path, throttleLimit, log);
72+
super(installTypingHost, globalTypingsCacheLocation, safeList.path, customTypesMap.path, throttleLimit, log);
6373
}
6474

6575
protected postExecActions: PostExecAction[] = [];
@@ -218,7 +228,7 @@ namespace ts.projectSystem {
218228
constructor(host: server.ServerHost, logger: server.Logger, cancellationToken: HostCancellationToken, useSingleInferredProject: boolean,
219229
typingsInstaller: server.ITypingsInstaller, eventHandler: server.ProjectServiceEventHandler) {
220230
super({
221-
host, logger, cancellationToken, useSingleInferredProject, typingsInstaller, eventHandler
231+
host, logger, cancellationToken, useSingleInferredProject, typingsInstaller, eventHandler, typesMapLocation: customTypesMap.path
222232
});
223233
}
224234

@@ -1479,9 +1489,8 @@ namespace ts.projectSystem {
14791489
path: "/lib/duckquack-3.min.js",
14801490
content: "whoa do @@ not parse me ok thanks!!!"
14811491
};
1482-
const host = createServerHost([customSafeList, file1, office]);
1492+
const host = createServerHost([file1, office, customTypesMap]);
14831493
const projectService = createProjectService(host);
1484-
projectService.loadSafeList(customSafeList.path);
14851494
try {
14861495
projectService.openExternalProject({ projectFileName: "project", options: {}, rootFiles: toExternalFiles([file1.path, office.path]) });
14871496
const proj = projectService.externalProjects[0];
@@ -1491,7 +1500,7 @@ namespace ts.projectSystem {
14911500
projectService.resetSafeList();
14921501
}
14931502
});
1494-
1503+
14951504
it("ignores files excluded by the default type list", () => {
14961505
const file1 = {
14971506
path: "/a/b/f1.ts",
Collapse file

‎src/server/editorServices.ts‎

Copy file name to clipboardExpand all lines: src/server/editorServices.ts
+49-15Lines changed: 49 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,11 @@ namespace ts.server {
109109
"smart": IndentStyle.Smart
110110
});
111111

112+
export interface TypesMapFile {
113+
typesMap: SafeList;
114+
simpleMap: string[];
115+
}
116+
112117
/**
113118
* How to understand this block:
114119
* * The 'match' property is a regexp that matches a filename.
@@ -329,6 +334,7 @@ namespace ts.server {
329334
globalPlugins?: string[];
330335
pluginProbeLocations?: string[];
331336
allowLocalPluginLoads?: boolean;
337+
typesMapLocation?: string;
332338
}
333339

334340
export class ProjectService {
@@ -389,6 +395,7 @@ namespace ts.server {
389395
public readonly globalPlugins: ReadonlyArray<string>;
390396
public readonly pluginProbeLocations: ReadonlyArray<string>;
391397
public readonly allowLocalPluginLoads: boolean;
398+
public readonly typesMapLocation: string | undefined;
392399

393400
/** Tracks projects that we have already sent telemetry for. */
394401
private readonly seenProjects = createMap<true>();
@@ -404,13 +411,18 @@ namespace ts.server {
404411
this.globalPlugins = opts.globalPlugins || emptyArray;
405412
this.pluginProbeLocations = opts.pluginProbeLocations || emptyArray;
406413
this.allowLocalPluginLoads = !!opts.allowLocalPluginLoads;
414+
this.typesMapLocation = (opts.typesMapLocation === undefined) ? combinePaths(this.host.getExecutingFilePath(), '../typesMap.json') : opts.typesMapLocation;
407415

408416
Debug.assert(!!this.host.createHash, "'ServerHost.createHash' is required for ProjectService");
409417

410418
this.toCanonicalFileName = createGetCanonicalFileName(this.host.useCaseSensitiveFileNames);
411419
this.directoryWatchers = new DirectoryWatchers(this);
412420
this.throttledOperations = new ThrottledOperations(this.host);
413421

422+
if (opts.typesMapLocation) {
423+
this.loadTypesMap();
424+
}
425+
414426
this.typingsInstaller.attach(this);
415427

416428
this.typingsCache = new TypingsCache(this.typingsInstaller);
@@ -447,6 +459,25 @@ namespace ts.server {
447459
});
448460
}
449461

462+
private loadTypesMap() {
463+
if (!this.host.fileExists(this.typesMapLocation)) {
464+
this.logger.info(`Provided types map file "${this.typesMapLocation}" doesn't exist`);
465+
return;
466+
}
467+
try {
468+
const raw: TypesMapFile = JSON.parse(this.host.readFile(this.typesMapLocation));
469+
// Parse the regexps
470+
for (const k of Object.keys(raw.typesMap)) {
471+
raw.typesMap[k].match = new RegExp(raw.typesMap[k].match as {} as string, "i");
472+
}
473+
// raw is now fixed and ready
474+
this.safelist = raw.typesMap;
475+
} catch(e) {
476+
this.logger.info(`Error loading types map: ${e}`);
477+
this.safelist = defaultTypeSafeList;
478+
}
479+
}
480+
450481
updateTypingsForProject(response: SetTypings | InvalidateCachedTypings): void {
451482
const project = this.findProject(response.projectName);
452483
if (!project) {
@@ -1623,23 +1654,14 @@ namespace ts.server {
16231654
this.safelist = defaultTypeSafeList;
16241655
}
16251656

1626-
loadSafeList(fileName: string): void {
1627-
const raw: SafeList = JSON.parse(this.host.readFile(fileName, "utf-8"));
1628-
// Parse the regexps
1629-
for (const k of Object.keys(raw)) {
1630-
raw[k].match = new RegExp(raw[k].match as {} as string, "i");
1631-
}
1632-
// raw is now fixed and ready
1633-
this.safelist = raw;
1634-
}
1635-
1636-
applySafeList(proj: protocol.ExternalProject): void {
1657+
applySafeList(proj: protocol.ExternalProject): NormalizedPath[] {
16371658
const { rootFiles, typeAcquisition } = proj;
16381659
const types = (typeAcquisition && typeAcquisition.include) || [];
16391660

16401661
const excludeRules: string[] = [];
16411662

1642-
const normalizedNames = rootFiles.map(f => normalizeSlashes(f.fileName));
1663+
const normalizedNames = rootFiles.map(f => normalizeSlashes(f.fileName)) as NormalizedPath[];
1664+
const excludedFiles: NormalizedPath[] = [];
16431665

16441666
for (const name of Object.keys(this.safelist)) {
16451667
const rule = this.safelist[name];
@@ -1698,7 +1720,17 @@ namespace ts.server {
16981720
}
16991721

17001722
const excludeRegexes = excludeRules.map(e => new RegExp(e, "i"));
1701-
proj.rootFiles = proj.rootFiles.filter((_file, index) => !excludeRegexes.some(re => re.test(normalizedNames[index])));
1723+
const filesToKeep: ts.server.protocol.ExternalFile[] = [];
1724+
for(let i = 0; i < proj.rootFiles.length; i++) {
1725+
if (excludeRegexes.some(re => re.test(normalizedNames[i]))) {
1726+
excludedFiles.push(normalizedNames[i]);
1727+
}
1728+
else {
1729+
filesToKeep.push(proj.rootFiles[i]);
1730+
}
1731+
}
1732+
proj.rootFiles = filesToKeep;
1733+
return excludedFiles;
17021734
}
17031735

17041736
openExternalProject(proj: protocol.ExternalProject, suppressRefreshOfInferredProjects = false): void {
@@ -1709,7 +1741,7 @@ namespace ts.server {
17091741
proj.typeAcquisition = typeAcquisition;
17101742
}
17111743

1712-
this.applySafeList(proj);
1744+
const excludedFiles = this.applySafeList(proj);
17131745

17141746
let tsConfigFiles: NormalizedPath[];
17151747
const rootFiles: protocol.ExternalFile[] = [];
@@ -1733,6 +1765,7 @@ namespace ts.server {
17331765
const externalProject = this.findExternalProjectByProjectName(proj.projectFileName);
17341766
let exisingConfigFiles: string[];
17351767
if (externalProject) {
1768+
externalProject.excludedFiles = excludedFiles;
17361769
if (!tsConfigFiles) {
17371770
const compilerOptions = convertCompilerOptions(proj.options);
17381771
if (this.exceededTotalSizeLimitForNonTsFiles(proj.projectFileName, compilerOptions, proj.rootFiles, externalFilePropertyReader)) {
@@ -1802,7 +1835,8 @@ namespace ts.server {
18021835
else {
18031836
// no config files - remove the item from the collection
18041837
this.externalProjectToConfiguredProjectMap.delete(proj.projectFileName);
1805-
this.createAndAddExternalProject(proj.projectFileName, rootFiles, proj.options, proj.typeAcquisition);
1838+
const newProj = this.createAndAddExternalProject(proj.projectFileName, rootFiles, proj.options, proj.typeAcquisition);
1839+
newProj.excludedFiles = excludedFiles;
18061840
}
18071841
if (!suppressRefreshOfInferredProjects) {
18081842
this.refreshInferredProjects();
Collapse file

‎src/server/project.ts‎

Copy file name to clipboardExpand all lines: src/server/project.ts
+10Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -375,6 +375,10 @@ namespace ts.server {
375375
return this.getLanguageService().getEmitOutput(info.fileName, emitOnlyDtsFiles);
376376
}
377377

378+
getExcludedFiles(): ReadonlyArray<NormalizedPath> {
379+
return emptyArray;
380+
}
381+
378382
getFileNames(excludeFilesFromExternalLibraries?: boolean, excludeConfigFiles?: boolean) {
379383
if (!this.program) {
380384
return [];
@@ -1161,6 +1165,7 @@ namespace ts.server {
11611165
* These are created only if a host explicitly calls `openExternalProject`.
11621166
*/
11631167
export class ExternalProject extends Project {
1168+
excludedFiles: ReadonlyArray<NormalizedPath> = [];
11641169
private typeAcquisition: TypeAcquisition;
11651170
constructor(public externalProjectName: string,
11661171
projectService: ProjectService,
@@ -1170,6 +1175,11 @@ namespace ts.server {
11701175
public compileOnSaveEnabled: boolean,
11711176
private readonly projectFilePath?: string) {
11721177
super(externalProjectName, ProjectKind.External, projectService, documentRegistry, /*hasExplicitListOfFiles*/ true, languageServiceEnabled, compilerOptions, compileOnSaveEnabled);
1178+
1179+
}
1180+
1181+
getExcludedFiles() {
1182+
return this.excludedFiles;
11731183
}
11741184

11751185
getProjectRootPath() {
Collapse file

‎src/server/server.ts‎

Copy file name to clipboardExpand all lines: src/server/server.ts
+9-2Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ namespace ts.server {
1313
globalTypingsCacheLocation: string;
1414
logger: Logger;
1515
typingSafeListLocation: string;
16+
typesMapLocation: string | undefined;
1617
npmLocation: string | undefined;
1718
telemetryEnabled: boolean;
1819
globalPlugins: string[];
@@ -243,6 +244,7 @@ namespace ts.server {
243244
eventPort: number,
244245
readonly globalTypingsCacheLocation: string,
245246
readonly typingSafeListLocation: string,
247+
readonly typesMapLocation: string,
246248
private readonly npmLocation: string | undefined,
247249
private newLine: string) {
248250
this.throttledOperations = new ThrottledOperations(host);
@@ -288,6 +290,9 @@ namespace ts.server {
288290
if (this.typingSafeListLocation) {
289291
args.push(Arguments.TypingSafeListLocation, this.typingSafeListLocation);
290292
}
293+
if (this.typesMapLocation) {
294+
args.push(Arguments.TypesMapLocation, this.typesMapLocation);
295+
}
291296
if (this.npmLocation) {
292297
args.push(Arguments.NpmLocation, this.npmLocation);
293298
}
@@ -401,10 +406,10 @@ namespace ts.server {
401406

402407
class IOSession extends Session {
403408
constructor(options: IOSessionOptions) {
404-
const { host, installerEventPort, globalTypingsCacheLocation, typingSafeListLocation, npmLocation, canUseEvents } = options;
409+
const { host, installerEventPort, globalTypingsCacheLocation, typingSafeListLocation, typesMapLocation, npmLocation, canUseEvents } = options;
405410
const typingsInstaller = disableAutomaticTypingAcquisition
406411
? undefined
407-
: new NodeTypingsInstaller(telemetryEnabled, logger, host, installerEventPort, globalTypingsCacheLocation, typingSafeListLocation, npmLocation, host.newLine);
412+
: new NodeTypingsInstaller(telemetryEnabled, logger, host, installerEventPort, globalTypingsCacheLocation, typingSafeListLocation, typesMapLocation, npmLocation, host.newLine);
408413

409414
super({
410415
host,
@@ -758,6 +763,7 @@ namespace ts.server {
758763
}
759764

760765
const typingSafeListLocation = findArgument(Arguments.TypingSafeListLocation);
766+
const typesMapLocation = findArgument(Arguments.TypesMapLocation) || combinePaths(sys.getExecutingFilePath(), '../typesMap.json');
761767
const npmLocation = findArgument(Arguments.NpmLocation);
762768

763769
const globalPlugins = (findArgument("--globalPlugins") || "").split(",");
@@ -777,6 +783,7 @@ namespace ts.server {
777783
disableAutomaticTypingAcquisition,
778784
globalTypingsCacheLocation: getGlobalTypingsCacheLocation(),
779785
typingSafeListLocation,
786+
typesMapLocation,
780787
npmLocation,
781788
telemetryEnabled,
782789
logger,

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.