Skip to content

Commit 0d50bf9

Browse files
committed
feat added support for getErrors, getErrorsForProject, getSemanticDiagnosticsSync
1 parent 8e590a1 commit 0d50bf9

File tree

5 files changed

+175
-12
lines changed

5 files changed

+175
-12
lines changed

src/exp.js

Lines changed: 18 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -21,29 +21,38 @@ for (let file of FILES) {
2121
console.log('findSourceDefinitionResp', JSON.stringify(findSourceDefinitionResp));
2222

2323
const completionInfoResp = await tsServer.getCompletionInfo(file.filepath, file.getCompletionInfo.line, file.getCompletionInfo.offset);
24-
console.assert('completionInfoResp', JSON.stringify(completionInfoResp));
24+
console.log('completionInfoResp', JSON.stringify(completionInfoResp));
2525

2626
const getCompletionDetailsResp = await tsServer.getCompletionDetails(file.filepath, file.getCompletionDetails.line, file.getCompletionDetails.offset, completionInfoResp.body.entries[0].name);
27-
console.assert('getCompletionDetailsResp', JSON.stringify(getCompletionDetailsResp));
27+
console.log('getCompletionDetailsResp', JSON.stringify(getCompletionDetailsResp));
2828

2929
const getCompileOnSaveResp = await tsServer.getCompileOnSaveAffectedFileList(file.filepath);
30-
console.assert('getCompileOnSaveResp', JSON.stringify(getCompileOnSaveResp));
30+
console.log('getCompileOnSaveResp', JSON.stringify(getCompileOnSaveResp));
3131

3232
const compileOnSaveEmitFileResp = await tsServer.compileOnSaveEmitFile(file.filepath);
33-
console.assert('compileOnSaveEmitFileResp', JSON.stringify(compileOnSaveEmitFileResp));
33+
console.log('compileOnSaveEmitFileResp', JSON.stringify(compileOnSaveEmitFileResp));
3434

3535
const getDefinitionAndBoundSpanResp = await tsServer.getDefinitionAndBoundSpan(file.filepath, file.getDefinitionAndBoundSpan.line, file.getDefinitionAndBoundSpan.offset);
36-
console.assert('getDefinitionAndBoundSpanResp', JSON.stringify(getDefinitionAndBoundSpanResp));
36+
console.log('getDefinitionAndBoundSpanResp', JSON.stringify(getDefinitionAndBoundSpanResp));
3737

3838
const getImplementationsResp = await tsServer.getImplementations(file.filepath, file.getImplementations.line, file.getImplementations.offset);
39-
console.assert('getImplementationsResp', JSON.stringify(getImplementationsResp));
39+
console.log('getImplementationsResp', JSON.stringify(getImplementationsResp));
4040

4141
const formatResp = await tsServer.format(file.filepath, file.format.line, file.format.offset, file.format.endLine, file.format.endOffset);
42-
console.assert('formatResp', JSON.stringify(formatResp));
42+
console.log('formatResp', JSON.stringify(formatResp));
4343

4444
const formatOnKeyResp = await tsServer.formatOnKey(file.filepath, file.formatOnKey.line, file.formatOnKey.offset, file.formatOnKey.key);
45-
console.assert('formatOnKeyResp', JSON.stringify(formatOnKeyResp));
45+
console.log('formatOnKeyResp', JSON.stringify(formatOnKeyResp));
4646

47+
for (const sample of file.getErrors.files) {
48+
await tsServer.openFile(sample);
49+
}
50+
//await tsServer.getErrors(file.getErrors.files, file.getErrors.delay);
4751

52+
//await tsServer.getErrorsForProject(file.getErrorsForProject.filePath, file.getErrorsForProject.delay);
53+
54+
// await tsServer.openFile(file.getSemanticDiagnosticsSync.filePath);
55+
const getSemanticDiagnosticsSyncResp = await tsServer.getSemanticDiagnosticsSync(file.getSemanticDiagnosticsSync.filePath, true);
56+
console.log('getSemanticDiagnosticsSyncResp', JSON.stringify(getSemanticDiagnosticsSyncResp));
4857
}
49-
tsServer.exitServer();
58+
//tsServer.exitServer();

src/test/sample/nonCompleteInit.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
let x = 10

src/test/sample/sematic.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
// sample.ts
2+
function greet(name: string) {
3+
console.log('Hello, ' + name);
4+
}
5+
6+
greet(42); // Intentionally passing a number to cause a semantic error.

src/utils/server.js

Lines changed: 132 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -126,8 +126,9 @@ function createTSServerInstance() {
126126
* @returns {Promise<Object>} A promise that resolves with the response from tsserver.
127127
*/
128128
function sendCommand(command, timeout = 5000) {
129-
if (command.command === "open") {
129+
if (command.command === "open" || command.command === "geterr" || command.command === "geterrForProject") {
130130
// For 'open' command, resolve immediately as no response is expected
131+
// geterr and geterrForProject returns result as events so resolve geterr and wait for response in events
131132
tsserverProcess.stdin.write(`${JSON.stringify(command)}\n`);
132133
return Promise.resolve();
133134
}
@@ -503,6 +504,133 @@ function createTSServerInstance() {
503504
return sendCommand(command);
504505
}
505506

507+
/**
508+
* Sends a 'geterr' request to the TypeScript Server. This command instructs the server to compute and
509+
* return errors (diagnostics) for the specified files. The diagnostics are not returned directly by this
510+
* function but are instead sent back by the server as separate events or messages. This function is useful
511+
* for asynchronously obtaining diagnostic information like errors and warnings from the server.
512+
*
513+
* @param {string[]} filePaths - An array of paths to the files for which to get errors. Each path should
514+
* be either absolute or relative to the TypeScript server's current working directory.
515+
* @param {number} delay - The delay in milliseconds to wait before the server processes the request.
516+
* This delay can be used to batch or throttle error requests, especially when dealing
517+
* with a large number of file changes or edits.
518+
*
519+
* @returns {Promise<void>} A promise that resolves when the command has been sent to the server. The resolution
520+
* of this promise indicates that the request was successfully dispatched, but it does not
521+
* imply that the errors have been received. The actual errors (diagnostics) will be sent
522+
* back by the server asynchronously as separate events or messages, which should be handled
523+
* separately in the client's message handling logic.
524+
*
525+
* Example usage:
526+
* ```
527+
* getErrors(['path/to/file1.ts', 'path/to/file2.ts'], 500).then(() => {
528+
* console.log('Error request sent. Waiting for diagnostics...');
529+
* });
530+
* ```
531+
* Note: The client should implement additional logic to listen for and handle the diagnostic events
532+
* or messages sent by the server in response to this request.
533+
*/
534+
function getErrors(filePaths, delay) {
535+
const command = {
536+
command: "geterr",
537+
arguments: {
538+
files: filePaths,
539+
delay: delay
540+
}
541+
};
542+
return sendCommand(command);
543+
}
544+
545+
/**
546+
* Sends a 'geterrForProject' request to the TypeScript Server. This command instructs the server to compute and
547+
* return errors (diagnostics) for all files in a specific project. The diagnostics are not returned directly by this
548+
* function but are instead sent back by the server as separate events or messages. This function is useful
549+
* for asynchronously obtaining a comprehensive diagnostic overview of an entire project.
550+
*
551+
* @param {string} filePath - The path to any file within the project. The server uses this file to identify
552+
* the project context. The path should be absolute or relative to the TypeScript
553+
* server's current working directory.
554+
* @param {number} delay - The delay in milliseconds before the server processes the request.
555+
* This delay can be used to batch or throttle diagnostic requests, especially useful
556+
* when dealing with large projects or numerous file changes.
557+
*
558+
* @returns {Promise<void>} A promise that resolves when the command has been sent to the server. The resolution
559+
* of this promise indicates that the request was successfully dispatched, but it does not
560+
* imply that the errors have been received. The actual errors (diagnostics) for the entire
561+
* project will be sent back by the server asynchronously as separate events or messages,
562+
* which should be handled separately in the client's message handling logic.
563+
*
564+
* Example usage:
565+
* ```
566+
* getErrorsForProject('path/to/anyFileInProject.ts', 500).then(() => {
567+
* console.log('Project error request sent. Waiting for diagnostics...');
568+
* });
569+
* ```
570+
* Note: The client should implement additional logic to listen for and handle the diagnostic events
571+
* or messages sent by the server in response to this request. These diagnostics will cover
572+
* the entire scope of the project associated with the provided file path.
573+
*/
574+
function getErrorsForProject(filePath, delay) {
575+
const command = {
576+
command: "geterrForProject",
577+
arguments: {
578+
file: filePath,
579+
delay: delay
580+
}
581+
};
582+
return sendCommand(command);
583+
}
584+
585+
/**
586+
* Sends a 'semanticDiagnosticsSync' request to the TypeScript Server. This command is used
587+
* to synchronously request semantic diagnostics (such as type errors) for a specific file.
588+
* It's useful when immediate and up-to-date semantic error information is needed for a file,
589+
* such as during file saves or build operations.
590+
*
591+
* @param {string} filePath - The path to the TypeScript file for which semantic diagnostics are requested.
592+
* The path should be absolute or relative to the TypeScript server's current
593+
* working directory.
594+
* @param {boolean} [includeLinePosition=false] - If set to true, the response will include detailed line
595+
* and character position information for each diagnostic.
596+
* This is useful for integrations that require precise
597+
* location data, such as IDEs or advanced text editors.
598+
*
599+
* @returns {Promise<Object>} A promise that resolves with the semantic diagnostics response from tsserver.
600+
* The response includes an array of diagnostic objects, each representing a
601+
* semantic error or warning found in the file. Each diagnostic object typically
602+
* contains the following information:
603+
* - `start`: The starting position of the error (line and character).
604+
* - `length`: The length of the error in characters.
605+
* - `text`: The error message text.
606+
* - `category`: The error category ('error', 'warning', or 'suggestion').
607+
* - `code`: The error code (useful for further reference or lookups).
608+
* If `includeLinePosition` is true, additional line and character position
609+
* information will be included in each diagnostic.
610+
*
611+
* Example usage:
612+
* ```
613+
* getSemanticDiagnosticsSync('path/to/file.ts', true).then(response => {
614+
* console.log('Semantic diagnostics with line positions:', response);
615+
* }).catch(error => {
616+
* console.error('Error getting semantic diagnostics:', error);
617+
* });
618+
* ```
619+
*
620+
* Note: This function performs a synchronous request, meaning it waits for the TypeScript server
621+
* to compute and return the diagnostics. The response is directly related to the current
622+
* state of the file at the time of the request.
623+
*/
624+
function getSemanticDiagnosticsSync(filePath, includeLinePosition = false) {
625+
const command = {
626+
command: "semanticDiagnosticsSync",
627+
arguments: {
628+
file: filePath,
629+
includeLinePosition: includeLinePosition
630+
}
631+
};
632+
return sendCommand(command);
633+
}
506634
/**
507635
* Terminates the TypeScript Server process.
508636
* Warning: Use this function with caution. Prefer using the exitServer function for a graceful shutdown.
@@ -535,6 +663,9 @@ function createTSServerInstance() {
535663
getImplementations,
536664
format,
537665
formatOnKey,
666+
getErrors,
667+
getErrorsForProject,
668+
getSemanticDiagnosticsSync,
538669
exitServer
539670
};
540671
}

src/utils/testconfig.js

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,13 @@ export const FILES = [{
99
getCompletionInfo: {line: 20, offset: 52},
1010
getCompletionDetails: {line: 20, offset: 52},
1111
format: {line: 9, offset: 0, endLine: 44, endOffset: 0},
12-
formatOnKey: {line: 44, offset: 154, key: ';'}
12+
formatOnKey: {line: 44, offset: 154, key: ';'},
13+
getErrors: {files: ['/home/charly/repo/tsIntelligence/src/test/sample/nonCompleteInit.js'], delay: 1000},
14+
getErrorsForProject: {
15+
filePath: '/home/charly/repo/tsIntelligence/src/exp.js',
16+
delay: 100
17+
},
18+
getSemanticDiagnosticsSync: {filePath: '/home/charly/repo/tsIntelligence/src/test/sample/semantic.js'}
1319

1420
}, {
1521
filepath: '/home/charly/repo/vscode/extensions/typescript-language-features/web/src/webServer.ts',
@@ -22,5 +28,15 @@ export const FILES = [{
2228
getCompletionInfo: {line: 40, offset: 40},
2329
getCompletionDetails: {line: 40, offset: 37},
2430
format: {line: 9, offset: 0, endLine: 44, endOffset: 0},
25-
formatOnKey: {line: 23, offset: 76, key: ';'}
31+
formatOnKey: {line: 23, offset: 76, key: ';'},
32+
getErrors: {
33+
files: ['/home/charly/repo/vscode/extensions/typescript-language-features/web/src/webServer.ts'],
34+
delay: 1000
35+
},
36+
getErrorsForProject: {
37+
filePath: '/home/charly/repo/vscode/extensions/typescript-language-features/web/src/webServer.ts',
38+
delay: 100
39+
},
40+
getSemanticDiagnosticsSync:
41+
{filePath: '/home/charly/repo/vscode/extensions/typescript-language-features/web/src/webServer.ts'}
2642
}];

0 commit comments

Comments
 (0)