Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions extensions/vscode/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -240,6 +240,10 @@ function patchTypeScriptExtension() {
configNamespace: 'typescript',
languages: config.server.includeLanguages,
},
{
name: 'vue-reactivity-analysis-plugin-pack',
enableForWorkspaceTypeScriptVersions: true,
},
];

fs.readFileSync = (...args: any[]) => {
Expand Down
6 changes: 3 additions & 3 deletions extensions/vscode/lib/reactivityVisualization.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import type { getReactiveReferences } from '@vue/typescript-plugin/lib/requests/getReactiveReferences';
import type { Analyzer } from 'laplacenoma';
import type * as ts from 'typescript';
import * as vscode from 'vscode';
import { config } from './config';
Expand Down Expand Up @@ -85,11 +85,11 @@ export function activate(
try {
const result = await vscode.commands.executeCommand<
{
body?: ReturnType<typeof getReactiveReferences>;
body?: ReturnType<Analyzer['analyze']> | undefined;
} | undefined
>(
'typescript.tsserverRequest',
'_vue:getReactiveReferences',
'_vue:getReactivityAnalysis',
[
document.uri.fsPath.replace(/\\/g, '/'),
document.offsetAt(editor.selection.active),
Expand Down
3 changes: 3 additions & 0 deletions extensions/vscode/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -461,11 +461,14 @@
"@types/node": "^22.10.4",
"@types/semver": "^7.5.3",
"@types/vscode": "1.88.0",
"@volar/typescript": "2.4.23",
"@volar/vscode": "2.4.23",
"@vscode/vsce": "^3.2.1",
"@vue/compiler-sfc": "^3.5.0",
"@vue/language-core": "3.0.8",
"@vue/language-server": "3.0.8",
"@vue/typescript-plugin": "3.0.8",
"laplacenoma": "^0.0.3",
"reactive-vscode": "^0.2.9",
"rolldown": "1.0.0-beta.8",
"semver": "^7.5.4",
Expand Down
Original file line number Diff line number Diff line change
@@ -1,38 +1,72 @@
import { createProxyLanguageService, decorateLanguageServiceHost } from '@volar/typescript';
import type { Language, SourceScript } from '@vue/language-core';
import type { Language } from '@vue/language-core';
import { createAnalyzer } from 'laplacenoma';
import * as rulesVue from 'laplacenoma/rules/vue';
// @ts-expect-error
import rulesVue from 'laplacenoma/rules/vue';
import type * as ts from 'typescript';

const analyzer = createAnalyzer({
rules: rulesVue,
});

let currentVersion = -1;
let currentFileName = '';
let currentSnapshot: ts.IScriptSnapshot | undefined;
let languageService: ts.LanguageService | undefined;

export function getReactiveReferences(
const analyzer = createAnalyzer({ rules: rulesVue });
const plugin: ts.server.PluginModuleFactory = ({ typescript: ts }) => {
return {
create(info) {
if (info.session && !(info.session as any).handlers.has('_vue:getReactivityAnalysis')) {
info.session.addProtocolHandler('_vue:getReactivityAnalysis', request => {
const [fileName, position]: [string, number] = request.arguments;
return {
response: getReactivityAnalysis(ts, info.session!, fileName, position),
responseRequired: true,
};
});
}

return info.languageService;
},
};
};

export = plugin;

function getReactivityAnalysis(
ts: typeof import('typescript'),
language: Language<string>,
sourceScript: SourceScript<string>,
session: ts.server.Session,
fileName: string,
position: number,
leadingOffset: number = 0,
) {
const { project } = session['getFileAndProject']({
file: fileName,
projectFileName: undefined,
}) as {
file: ts.server.NormalizedPath;
project: ts.server.Project;
};

const language: Language<string> | undefined = project['program']?.__vue__?.language;
if (!language) {
return;
}

const sourceScript = language.scripts.get(fileName);
if (!sourceScript) {
return;
}

if (currentSnapshot !== sourceScript.snapshot || currentFileName !== sourceScript.id) {
currentSnapshot = sourceScript.snapshot;
currentFileName = sourceScript.id;
currentVersion++;
}
if (!languageService) {
const compilerOptions: ts.CompilerOptions = { allowJs: true, allowNonTsExtensions: true };
const languageServiceHost: ts.LanguageServiceHost = {
getProjectVersion: () => currentVersion.toString(),
getScriptVersion: () => currentVersion.toString(),
getScriptFileNames: () => [currentFileName],
getScriptSnapshot: fileName => fileName === currentFileName ? currentSnapshot : undefined,
getCompilationSettings: () => compilerOptions,
getCompilationSettings: () => ({ allowJs: true, allowNonTsExtensions: true }),
getCurrentDirectory: () => '',
getDefaultLibFileName: () => '',
readFile: () => undefined,
Expand All @@ -49,6 +83,7 @@ export function getReactiveReferences(
sourceScript.generated.root,
);
const map = serviceScript ? language.maps.get(serviceScript.code, sourceScript) : undefined;
const leadingOffset = sourceScript.generated ? sourceScript.snapshot.getLength() : 0;
const toSourceRange = map
? (pos: number, end: number) => {
for (const [mappedStart, mappedEnd] of map.toSourceRange(pos - leadingOffset, end - leadingOffset, false)) {
Expand Down
7 changes: 7 additions & 0 deletions extensions/vscode/rolldown.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ const resolve = (...paths: string[]) => path.resolve(__dirname, ...paths);
const config: RolldownOptions = {
input: {
'extension': './index.ts',
'reactivity-analysis': './reactivityAnalysis/plugin.ts',
},
output: {
format: 'cjs',
Expand All @@ -33,6 +34,12 @@ const config: RolldownOptions = {
`module.exports = require('../../dist/typescript-plugin.js');`,
);

fs.mkdirSync(resolve('./node_modules/vue-reactivity-analysis-plugin-pack'), { recursive: true });
fs.writeFileSync(
resolve('./node_modules/vue-reactivity-analysis-plugin-pack/index.js'),
`module.exports = require('../../dist/reactivity-analysis.js');`,
);

if (isDev) {
fs.mkdirSync(resolve('./dist'), { recursive: true });
fs.writeFileSync(
Expand Down
2 changes: 1 addition & 1 deletion extensions/vscode/tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,5 @@
"module": "CommonJS",
"moduleResolution": "Node"
},
"include": ["*", "lib/**/*"]
"include": ["*", "lib/**/*", "reactivityAnalysis/**/*"]
}
3 changes: 0 additions & 3 deletions packages/language-server/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -122,9 +122,6 @@ connection.onInitialize(params => {
getImportPathForFile(...args) {
return sendTsServerRequest('_vue:getImportPathForFile', args);
},
getReactiveReferences(...args) {
return sendTsServerRequest('_vue:getReactiveReferences', args);
},
isRefAtPosition(...args) {
return sendTsServerRequest('_vue:isRefAtPosition', args);
},
Expand Down
18 changes: 1 addition & 17 deletions packages/typescript-plugin/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ import { getComponentSlots } from './lib/requests/getComponentSlots';
import { getElementAttrs } from './lib/requests/getElementAttrs';
import { getElementNames } from './lib/requests/getElementNames';
import { getImportPathForFile } from './lib/requests/getImportPathForFile';
import { getReactiveReferences } from './lib/requests/getReactiveReferences';
import { isRefAtPosition } from './lib/requests/isRefAtPosition';

const windowsPathReg = /\\/g;
Expand Down Expand Up @@ -187,20 +186,6 @@ export = createLanguageServicePlugin(
const { languageService } = getLanguageService(fileName);
return createResponse(getElementNames(ts, languageService.getProgram()!, fileName));
});
session.addProtocolHandler('_vue:getReactiveReferences', request => {
const [fileName, position]: Parameters<Requests['getReactiveReferences']> = request.arguments;
const { language } = getLanguageService(fileName);
const sourceScript = language.scripts.get(fileName)!;
return createResponse(
getReactiveReferences(
ts,
language,
sourceScript,
position,
sourceScript.generated ? sourceScript.snapshot.getLength() : 0,
),
);
});

projectService.logger.info('Vue specific commands are successfully added.');

Expand Down Expand Up @@ -229,8 +214,7 @@ export = createLanguageServicePlugin(
}

function getLanguageService(fileName: string) {
// @ts-expect-error
const { project } = session.getFileAndProject({
const { project } = session['getFileAndProject']({
file: fileName,
projectFileName: undefined,
}) as {
Expand Down
4 changes: 0 additions & 4 deletions packages/typescript-plugin/lib/requests/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,10 +40,6 @@ export interface Requests {
getElementNames(
fileName: string,
): Response<ReturnType<typeof import('./getElementNames.js')['getElementNames']>>;
getReactiveReferences(
fileName: string,
position: number,
): Response<ReturnType<typeof import('./getReactiveReferences.js')['getReactiveReferences']>>;
getDocumentHighlights(
fileName: string,
position: number,
Expand Down
1 change: 0 additions & 1 deletion packages/typescript-plugin/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@
"@volar/typescript": "2.4.23",
"@vue/language-core": "3.0.8",
"@vue/shared": "^3.5.0",
"laplacenoma": "^0.0.3",
"path-browserify": "^1.0.1"
},
"devDependencies": {
Expand Down
12 changes: 9 additions & 3 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading