UNPKG

wireit

Version:

Upgrade your npm scripts to make them smarter and more efficient

135 lines 4.76 kB
/** * @license * Copyright 2022 Google LLC * SPDX-License-Identifier: Apache-2.0 */ // This is where the bulk of the work of the extension happens. This file // runs in its own process, and communicates with the main process via // node IPC. // jsonc-parser often uses 'any' when they mean 'unknown'. We might want to // declare our own types for them, but for now, we'll just quiet down eslint. import { createConnection, TextDocuments, ProposedFeatures, TextDocumentSyncKind, CodeActionKind, } from 'vscode-languageserver/node'; import * as url from 'url'; import { TextDocument } from 'vscode-languageserver-textdocument'; import { inspect } from 'util'; import { IdeAnalyzer } from './ide.js'; const ideAnalyzer = new IdeAnalyzer(); const connection = createConnection(ProposedFeatures.all); connection.onInitialize((init) => { const workspacePaths = []; for (const folder of init.workspaceFolders ?? []) { workspacePaths.push(url.fileURLToPath(folder.uri)); } ideAnalyzer.setWorkspaceRoots(workspacePaths); const result = { capabilities: { textDocumentSync: TextDocumentSyncKind.Incremental, // If we add any new features, we'll generally need to declare them // here. codeActionProvider: { codeActionKinds: [ CodeActionKind.QuickFix, CodeActionKind.RefactorExtract, ], }, definitionProvider: true, referencesProvider: true, completionProvider: { // We don't have more information later, so don't bother asking. resolveProvider: false, completionItem: {}, triggerCharacters: ['"', ':', '/'], }, }, }; return result; }); function log(...values) { for (const value of values) { let message; if (typeof value === 'string') { message = value; } else { message = inspect(value, { depth: 4 }); } connection.console.log(message); } } // So that we can just console.log and console.error as usual. console.log = log; console.error = log; const documents = new TextDocuments(TextDocument); let requestIdCounter = 0; const getAndSendDiagnostics = async () => { requestIdCounter++; const requestId = requestIdCounter; const diagnosticsByFile = await ideAnalyzer.getDiagnostics(); if (requestId !== requestIdCounter) { return; // another request has been made since this one } for (const path of ideAnalyzer.openFiles) { const diagnostics = diagnosticsByFile.get(path) ?? []; void connection.sendDiagnostics({ uri: url.pathToFileURL(path).toString(), diagnostics: [...diagnostics], }); } }; const updateOpenFile = (document) => { if (document.languageId !== 'json') { return; } const path = url.fileURLToPath(document.uri); if (!path.endsWith('package.json')) { return; } const contents = document.getText(); ideAnalyzer.setOpenFileContents(path, contents); void getAndSendDiagnostics(); }; documents.onDidOpen((event) => { updateOpenFile(event.document); }); documents.onDidChangeContent((change) => { updateOpenFile(change.document); }); documents.onDidClose((change) => { const path = url.fileURLToPath(change.document.uri); ideAnalyzer.closeFile(path); void getAndSendDiagnostics(); // Clear diagnostics for closed file. void connection.sendDiagnostics({ uri: change.document.uri, diagnostics: [], }); }); connection.onCodeAction(async (params) => { const document = documents.get(params.textDocument.uri); if (document === undefined) { return []; } const path = url.fileURLToPath(document.uri); const actions = await ideAnalyzer.getCodeActions(path, params.range); return actions; }); connection.onDefinition(async (params) => { const path = url.fileURLToPath(params.textDocument.uri); const position = params.position; return ideAnalyzer.getDefinition(path, position); }); connection.onReferences(async (params) => { // TODO: handle params.context.includeDeclaration const path = url.fileURLToPath(params.textDocument.uri); const position = params.position; return ideAnalyzer.findAllReferences(path, position); }); connection.onCompletion(async (params) => { const path = url.fileURLToPath(params.textDocument.uri); const position = params.position; return ideAnalyzer.getCompletions(path, position); }); // Actually start listening documents.listen(connection); connection.listen(); //# sourceMappingURL=language-server.js.map