@vue/language-service 2.0.7 → 2.0.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.
Files changed (31) hide show
  1. package/data/language-blocks/en.json +1 -1
  2. package/data/model-modifiers/ja.json +1 -1
  3. package/data/template/ja.json +1 -1
  4. package/index.d.ts +2 -2
  5. package/index.js +13 -5
  6. package/lib/ideFeatures/nameCasing.js +6 -6
  7. package/lib/plugins/css.d.ts +2 -2
  8. package/lib/plugins/vue-autoinsert-dotvalue.d.ts +5 -5
  9. package/lib/plugins/vue-autoinsert-dotvalue.js +24 -26
  10. package/lib/plugins/vue-autoinsert-parentheses.d.ts +2 -2
  11. package/lib/plugins/vue-autoinsert-parentheses.js +11 -5
  12. package/lib/plugins/vue-autoinsert-space.d.ts +2 -2
  13. package/lib/plugins/vue-autoinsert-space.js +5 -13
  14. package/lib/plugins/vue-codelens-references.d.ts +2 -2
  15. package/lib/plugins/vue-codelens-references.js +5 -3
  16. package/lib/plugins/vue-directive-comments.d.ts +2 -2
  17. package/lib/plugins/vue-document-drop.d.ts +2 -2
  18. package/lib/plugins/vue-document-drop.js +29 -11
  19. package/lib/plugins/vue-extract-file.d.ts +2 -2
  20. package/lib/plugins/vue-extract-file.js +14 -10
  21. package/lib/plugins/vue-sfc.d.ts +2 -2
  22. package/lib/plugins/vue-sfc.js +29 -28
  23. package/lib/plugins/vue-template.d.ts +2 -2
  24. package/lib/plugins/vue-template.js +28 -18
  25. package/lib/plugins/vue-toggle-v-bind-codeaction.d.ts +2 -2
  26. package/lib/plugins/vue-toggle-v-bind-codeaction.js +4 -2
  27. package/lib/plugins/vue-twoslash-queries.d.ts +2 -2
  28. package/lib/plugins/vue-twoslash-queries.js +6 -4
  29. package/lib/plugins/vue-visualize-hidden-callback-param.d.ts +2 -2
  30. package/lib/plugins/vue-visualize-hidden-callback-param.js +5 -3
  31. package/package.json +16 -16
@@ -556,7 +556,7 @@
556
556
  "valueSet": "v",
557
557
  "description": {
558
558
  "kind": "markdown",
559
- "value": "\nA `<style module>` tag is compiled as [CSS Modules](https://github.com/css-modules/css-modules) and exposes the resulting CSS classes to the component as an object under the key of `$style`:\n\n```vue\n<template>\n <p :class=\"$style.red\">This should be red</p>\n</template>\n\n<style module>\n.red {\n color: red;\n}\n</style>\n```\n\nThe resulting classes are hashed to avoid collision, achieving the same effect of scoping the CSS to the current component only.\n\nRefer to the [CSS Modules spec](https://github.com/css-modules/css-modules) for more details such as [global exceptions](https://github.com/css-modules/css-modules#exceptions) and [composition](https://github.com/css-modules/css-modules#composition).\n\n### Custom Inject Name \n\nYou can customize the property key of the injected classes object by giving the `module` attribute a value:\n\n```vue\n<template>\n <p :class=\"classes.red\">red</p>\n</template>\n\n<style module=\"classes\">\n.red {\n color: red;\n}\n</style>\n```\n\n### Usage with Composition API \n\nThe injected classes can be accessed in `setup()` and `<script setup>` via the `useCssModule` API. For `<style module>` blocks with custom injection names, `useCssModule` accepts the matching `module` attribute value as the first argument:\n\n```js\nimport { useCssModule } from 'vue'\n\n// inside setup() scope...\n// default, returns classes for <style module>\nuseCssModule()\n\n// named, returns classes for <style module=\"classes\">\nuseCssModule('classes')\n```\n"
559
+ "value": "\nA `<style module>` tag is compiled as [CSS Modules](https://github.com/css-modules/css-modules) and exposes the resulting CSS classes to the component as an object under the key of `$style`:\n\n```vue\n<template>\n <p :class=\"$style.red\">This should be red</p>\n</template>\n\n<style module>\n.red {\n color: red;\n}\n</style>\n```\n\nThe resulting classes are hashed to avoid collision, achieving the same effect of scoping the CSS to the current component only.\n\nRefer to the [CSS Modules spec](https://github.com/css-modules/css-modules) for more details such as [global exceptions](https://github.com/css-modules/css-modules/blob/master/docs/composition.md#exceptions) and [composition](https://github.com/css-modules/css-modules/blob/master/docs/composition.md#composition).\n\n### Custom Inject Name \n\nYou can customize the property key of the injected classes object by giving the `module` attribute a value:\n\n```vue\n<template>\n <p :class=\"classes.red\">red</p>\n</template>\n\n<style module=\"classes\">\n.red {\n color: red;\n}\n</style>\n```\n\n### Usage with Composition API \n\nThe injected classes can be accessed in `setup()` and `<script setup>` via the `useCssModule` API. For `<style module>` blocks with custom injection names, `useCssModule` accepts the matching `module` attribute value as the first argument:\n\n```js\nimport { useCssModule } from 'vue'\n\n// inside setup() scope...\n// default, returns classes for <style module>\nuseCssModule()\n\n// named, returns classes for <style module=\"classes\">\nuseCssModule('classes')\n```\n"
560
560
  },
561
561
  "references": [
562
562
  {
@@ -5,7 +5,7 @@
5
5
  "name": "lazy",
6
6
  "description": {
7
7
  "kind": "markdown",
8
- "value": "\nデフォルトでは、 `v-model` は各 `input` イベントの後に、入力とデータを同期します ([上記](#vmodel-ime-tip) の IME による入力は例外とします)。 代わりに `change` イベント後に同期する `lazy` 修飾子を追加することができます。\n\n```html\n<!-- \"input\" の代わりに \"change\" イベント後に同期されます -->\n<input v-model.lazy=\"msg\" />\n```\n"
8
+ "value": "\nデフォルトでは、 `v-model` は各 `input` イベントの後に、入力とデータを同期します([上記](#vmodel-ime-tip) の IME による入力は例外とします)。 代わりに `change` イベント後に同期する `lazy` 修飾子を追加することができます。\n\n```html\n<!-- \"input\" の代わりに \"change\" イベント後に同期されます -->\n<input v-model.lazy=\"msg\" />\n```\n"
9
9
  },
10
10
  "references": [
11
11
  {
@@ -736,7 +736,7 @@
736
736
  "name": "v-bind",
737
737
  "description": {
738
738
  "kind": "markdown",
739
- "value": "\n1 つ以上の属性やコンポーネントの props を式に動的にバインドします。\n\n- **省略記法:**\n - `:` or `.`(`.prop` 修飾子使用時)\n - 値の省略(属性とバインドされた値が同じ名前の場合)<sup class=\"vt-badge\">3.4+</sup>\n\n- **期待する値:** `any(引数ありの場合) | Object(引数なしの場合)`\n\n- **引数:** `attrOrProp(省略可能)`\n\n- **修飾子**\n\n - `.camel` - kebab-case の属性名を camelCase に変換します。\n - `.prop` - バインディングを DOM プロパティとして設定するよう強制します。<sup class=\"vt-badge\">3.2+</sup>\n - `.attr` - バインディングを DOM 属性として設定するよう強制します。<sup class=\"vt-badge\">3.2+</sup>\n\n- **使用法**\n\n `class` や `style` 属性をバインドする際に使用する `v-bind` は、Array や Object などの追加の値の型をサポートします。詳しくは、以下のリンク先のガイドを参照してください。\n\n 要素にバインディングを設定するとき、Vue はデフォルトで、`in` 演算子チェックを使用して、プロパティとして定義されたキーが要素にあるかどうかを確認します。プロパティが定義されている場合、Vue はその値を属性ではなく DOM プロパティとして設定します。これはほとんどの場合において有効ですが、`.prop` や `.attr` という修飾子を明示的に使用することでこの動作をオーバーライドできます。これは、特に[カスタム要素を扱う](https://ja.vuejs.org/guide/extras/web-components.html#passing-dom-properties)ときに必要になることがあります。\n\n コンポーネントの props をバインドするために使用する場合、その props は子コンポーネントで適切に宣言されている必要があります。\n\n 引数なしで使用する場合、属性の名前と値のペアを含むオブジェクトをバインドするために使用できます。\n\n- **例**\n\n ```html\n <!-- 属性をバインドする -->\n <img v-bind:src=\"imageSrc\" />\n\n <!-- 動的な属性名 -->\n <button v-bind:[key]=\"value\"></button>\n\n <!-- 省略記法 -->\n <img :src=\"imageSrc\" />\n\n <!-- 同名省略記法 (3.4+), :src=\"src\" のように展開する -->\n <img :src />\n\n <!-- 動的な属性名の省略記法 -->\n <button :[key]=\"value\"></button>\n\n <!-- インラインの文字列連結 -->\n <img :src=\"'/path/to/images/' + fileName\" />\n\n <!-- クラスのバインド -->\n <div :class=\"{ red: isRed }\"></div>\n <div :class=\"[classA, classB]\"></div>\n <div :class=\"[classA, { classB: isB, classC: isC }]\"></div>\n\n <!-- スタイルのバインド -->\n <div :style=\"{ fontSize: size + 'px' }\"></div>\n <div :style=\"[styleObjectA, styleObjectB]\"></div>\n\n <!-- 属性のオブジェクトをバインド -->\n <div v-bind=\"{ id: someProp, 'other-attr': otherProp }\"></div>\n\n <!-- props のバインド。\"prop\" は子コンポーネントで宣言する必要があります。 -->\n <MyComponent :prop=\"someThing\" />\n\n <!-- 親の props を子コンポーネントと共有するために渡す -->\n <MyComponent v-bind=\"$props\" />\n\n <!-- XLink -->\n <svg><a :xlink:special=\"foo\"></a></svg>\n ```\n\n `.prop` 修飾子には、専用の短縮形 `.` もあります:\n\n ```html\n <div :someProperty.prop=\"someObject\"></div>\n\n <!-- 以下と同じ -->\n <div .someProperty=\"someObject\"></div>\n ```\n\n `.camel` 修飾子は、DOM 内テンプレートを使用する際に、 `v-bind` 属性名をキャメル化できます(例: SVG の `viewBox` 属性):\n\n ```html\n <svg :view-box.camel=\"viewBox\"></svg>\n ```\n\n 文字列テンプレートを使用する場合や、ビルドステップでテンプレートを事前コンパイルする場合は、`.camel` は必要ありません。\n\n- **参照**\n - [クラスとスタイルのバインディング](https://ja.vuejs.org/guide/essentials/class-and-style.html)\n - [コンポーネント - props 渡しの詳細](https://ja.vuejs.org/guide/components/props.html#prop-passing-details)\n"
739
+ "value": "\n1 つ以上の属性やコンポーネントの props を式に動的にバインドします。\n\n- **省略記法:**\n - `:` or `.`(`.prop` 修飾子使用時)\n - 値の省略(属性とバインドされた値が同じ名前の場合)<sup class=\"vt-badge\">3.4+</sup>\n\n- **期待する値:** `any(引数ありの場合)| Object(引数なしの場合)`\n\n- **引数:** `attrOrProp(省略可能)`\n\n- **修飾子**\n\n - `.camel` - kebab-case の属性名を camelCase に変換します。\n - `.prop` - バインディングを DOM プロパティとして設定するよう強制します。<sup class=\"vt-badge\">3.2+</sup>\n - `.attr` - バインディングを DOM 属性として設定するよう強制します。<sup class=\"vt-badge\">3.2+</sup>\n\n- **使用法**\n\n `class` や `style` 属性をバインドする際に使用する `v-bind` は、Array や Object などの追加の値の型をサポートします。詳しくは、以下のリンク先のガイドを参照してください。\n\n 要素にバインディングを設定するとき、Vue はデフォルトで、`in` 演算子チェックを使用して、プロパティとして定義されたキーが要素にあるかどうかを確認します。プロパティが定義されている場合、Vue はその値を属性ではなく DOM プロパティとして設定します。これはほとんどの場合において有効ですが、`.prop` や `.attr` という修飾子を明示的に使用することでこの動作をオーバーライドできます。これは、特に[カスタム要素を扱う](https://ja.vuejs.org/guide/extras/web-components.html#passing-dom-properties)ときに必要になることがあります。\n\n コンポーネントの props をバインドするために使用する場合、その props は子コンポーネントで適切に宣言されている必要があります。\n\n 引数なしで使用する場合、属性の名前と値のペアを含むオブジェクトをバインドするために使用できます。\n\n- **例**\n\n ```html\n <!-- 属性をバインドする -->\n <img v-bind:src=\"imageSrc\" />\n\n <!-- 動的な属性名 -->\n <button v-bind:[key]=\"value\"></button>\n\n <!-- 省略記法 -->\n <img :src=\"imageSrc\" />\n\n <!-- 同名省略記法(3.4+), :src=\"src\" のように展開する -->\n <img :src />\n\n <!-- 動的な属性名の省略記法 -->\n <button :[key]=\"value\"></button>\n\n <!-- インラインの文字列連結 -->\n <img :src=\"'/path/to/images/' + fileName\" />\n\n <!-- クラスのバインド -->\n <div :class=\"{ red: isRed }\"></div>\n <div :class=\"[classA, classB]\"></div>\n <div :class=\"[classA, { classB: isB, classC: isC }]\"></div>\n\n <!-- スタイルのバインド -->\n <div :style=\"{ fontSize: size + 'px' }\"></div>\n <div :style=\"[styleObjectA, styleObjectB]\"></div>\n\n <!-- 属性のオブジェクトをバインド -->\n <div v-bind=\"{ id: someProp, 'other-attr': otherProp }\"></div>\n\n <!-- props のバインド。\"prop\" は子コンポーネントで宣言する必要があります。 -->\n <MyComponent :prop=\"someThing\" />\n\n <!-- 親の props を子コンポーネントと共有するために渡す -->\n <MyComponent v-bind=\"$props\" />\n\n <!-- XLink -->\n <svg><a :xlink:special=\"foo\"></a></svg>\n ```\n\n `.prop` 修飾子には、専用の短縮形 `.` もあります:\n\n ```html\n <div :someProperty.prop=\"someObject\"></div>\n\n <!-- 以下と同じ -->\n <div .someProperty=\"someObject\"></div>\n ```\n\n `.camel` 修飾子は、DOM 内テンプレートを使用する際に、 `v-bind` 属性名をキャメル化できます(例: SVG の `viewBox` 属性):\n\n ```html\n <svg :view-box.camel=\"viewBox\"></svg>\n ```\n\n 文字列テンプレートを使用する場合や、ビルドステップでテンプレートを事前コンパイルする場合は、`.camel` は必要ありません。\n\n- **参照**\n - [クラスとスタイルのバインディング](https://ja.vuejs.org/guide/essentials/class-and-style.html)\n - [コンポーネント - props 渡しの詳細](https://ja.vuejs.org/guide/components/props.html#prop-passing-details)\n"
740
740
  },
741
741
  "references": [
742
742
  {
package/index.d.ts CHANGED
@@ -2,7 +2,7 @@ export * from '@volar/language-service';
2
2
  export * from '@vue/language-core';
3
3
  export * from './lib/ideFeatures/nameCasing';
4
4
  export * from './lib/types';
5
- import type { ServiceContext, ServiceEnvironment, ServicePlugin } from '@volar/language-service';
5
+ import type { ServiceContext, ServiceEnvironment, LanguageServicePlugin } from '@volar/language-service';
6
6
  import type { VueCompilerOptions } from './lib/types';
7
- export declare function createVueServicePlugins(ts: typeof import('typescript'), getVueOptions: (env: ServiceEnvironment) => VueCompilerOptions, getTsPluginClient?: (context: ServiceContext) => typeof import("@vue/typescript-plugin/lib/client") | undefined, hybridMode?: boolean): ServicePlugin[];
7
+ export declare function createVueServicePlugins(ts: typeof import('typescript'), getVueOptions: (env: ServiceEnvironment) => VueCompilerOptions, getTsPluginClient?: (context: ServiceContext) => typeof import("@vue/typescript-plugin/lib/client") | undefined, hybridMode?: boolean): LanguageServicePlugin[];
8
8
  export declare function createDefaultGetTsPluginClient(ts: typeof import('typescript'), getVueOptions: (env: ServiceEnvironment) => VueCompilerOptions): (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined;
package/index.js CHANGED
@@ -42,6 +42,7 @@ const vue_visualize_hidden_callback_param_1 = require("./lib/plugins/vue-visuali
42
42
  const common_1 = require("@vue/typescript-plugin/lib/common");
43
43
  const collectExtractProps_1 = require("@vue/typescript-plugin/lib/requests/collectExtractProps");
44
44
  const componentInfos_1 = require("@vue/typescript-plugin/lib/requests/componentInfos");
45
+ const getImportPathForFile_1 = require("@vue/typescript-plugin/lib/requests/getImportPathForFile");
45
46
  const getPropertiesAtLocation_1 = require("@vue/typescript-plugin/lib/requests/getPropertiesAtLocation");
46
47
  const getQuickInfoAtPosition_1 = require("@vue/typescript-plugin/lib/requests/getQuickInfoAtPosition");
47
48
  function createVueServicePlugins(ts, getVueOptions, getTsPluginClient = createDefaultGetTsPluginClient(ts, getVueOptions), hybridMode = false) {
@@ -60,7 +61,7 @@ function createVueServicePlugins(ts, getVueOptions, getTsPluginClient = createDe
60
61
  }
61
62
  const languageService = created.provide['typescript/languageService']();
62
63
  const vueOptions = getVueOptions(context.env);
63
- (0, common_1.decorateLanguageServiceForVue)(context.language.files, languageService, vueOptions, ts, false);
64
+ (0, common_1.decorateLanguageServiceForVue)(context.language, languageService, vueOptions, ts, false);
64
65
  return created;
65
66
  },
66
67
  };
@@ -71,7 +72,7 @@ function createVueServicePlugins(ts, getVueOptions, getTsPluginClient = createDe
71
72
  else {
72
73
  plugins.push((0, syntactic_1.create)(ts), (0, docCommentTemplate_1.create)(ts));
73
74
  }
74
- plugins.push((0, volar_service_typescript_twoslash_queries_1.create)(ts), (0, css_1.create)(), (0, volar_service_pug_beautify_1.create)(), (0, volar_service_json_1.create)(), (0, vue_template_1.create)('html', ts, getVueOptions, getTsPluginClient), (0, vue_template_1.create)('pug', ts, getVueOptions, getTsPluginClient), (0, vue_sfc_1.create)(), (0, vue_twoslash_queries_1.create)(ts, getTsPluginClient), (0, vue_codelens_references_1.create)(), (0, vue_document_drop_1.create)(ts), (0, vue_autoinsert_dotvalue_1.create)(ts, getTsPluginClient), (0, vue_autoinsert_parentheses_1.create)(ts), (0, vue_autoinsert_space_1.create)(), (0, vue_visualize_hidden_callback_param_1.create)(), (0, vue_directive_comments_1.create)(), (0, vue_extract_file_1.create)(ts, getTsPluginClient), (0, vue_toggle_v_bind_codeaction_1.create)(ts), (0, volar_service_emmet_1.create)());
75
+ plugins.push((0, volar_service_typescript_twoslash_queries_1.create)(ts), (0, css_1.create)(), (0, volar_service_pug_beautify_1.create)(), (0, volar_service_json_1.create)(), (0, vue_template_1.create)('html', ts, getVueOptions, getTsPluginClient), (0, vue_template_1.create)('pug', ts, getVueOptions, getTsPluginClient), (0, vue_sfc_1.create)(), (0, vue_twoslash_queries_1.create)(ts, getTsPluginClient), (0, vue_codelens_references_1.create)(), (0, vue_document_drop_1.create)(ts, getTsPluginClient), (0, vue_autoinsert_dotvalue_1.create)(ts, getTsPluginClient), (0, vue_autoinsert_parentheses_1.create)(ts), (0, vue_autoinsert_space_1.create)(), (0, vue_visualize_hidden_callback_param_1.create)(), (0, vue_directive_comments_1.create)(), (0, vue_extract_file_1.create)(ts, getTsPluginClient), (0, vue_toggle_v_bind_codeaction_1.create)(ts), (0, volar_service_emmet_1.create)());
75
76
  return plugins;
76
77
  }
77
78
  exports.createVueServicePlugins = createVueServicePlugins;
@@ -80,10 +81,15 @@ function createDefaultGetTsPluginClient(ts, getVueOptions) {
80
81
  if (!context.language.typescript) {
81
82
  return;
82
83
  }
84
+ const languageService = context.inject('typescript/languageService');
85
+ if (!languageService) {
86
+ return;
87
+ }
83
88
  const requestContext = {
84
89
  typescript: ts,
85
- files: context.language.files,
86
- languageService: context.inject('typescript/languageService'),
90
+ language: context.language,
91
+ languageService,
92
+ languageServiceHost: context.language.typescript.languageServiceHost,
87
93
  vueOptions: getVueOptions(context.env),
88
94
  isTsPlugin: false,
89
95
  getFileId: context.env.typescript.fileNameToUri,
@@ -95,6 +101,9 @@ function createDefaultGetTsPluginClient(ts, getVueOptions) {
95
101
  async getPropertiesAtLocation(...args) {
96
102
  return await getPropertiesAtLocation_1.getPropertiesAtLocation.apply(requestContext, args);
97
103
  },
104
+ async getImportPathForFile(...args) {
105
+ return await getImportPathForFile_1.getImportPathForFile.apply(requestContext, args);
106
+ },
98
107
  async getComponentEvents(...args) {
99
108
  return await componentInfos_1.getComponentEvents.apply(requestContext, args);
100
109
  },
@@ -115,7 +124,6 @@ function createDefaultGetTsPluginClient(ts, getVueOptions) {
115
124
  },
116
125
  };
117
126
  };
118
- ;
119
127
  }
120
128
  exports.createDefaultGetTsPluginClient = createDefaultGetTsPluginClient;
121
129
  //# sourceMappingURL=index.js.map
@@ -6,11 +6,11 @@ const language_core_1 = require("@vue/language-core");
6
6
  const computeds_1 = require("computeds");
7
7
  const types_1 = require("../types");
8
8
  async function convertTagName(context, uri, casing, tsPluginClient) {
9
- const sourceFile = context.language.files.get(uri);
9
+ const sourceFile = context.language.scripts.get(uri);
10
10
  if (!sourceFile) {
11
11
  return;
12
12
  }
13
- const rootCode = sourceFile?.generated?.code;
13
+ const rootCode = sourceFile?.generated?.root;
14
14
  if (!(rootCode instanceof language_core_1.VueGeneratedCode)) {
15
15
  return;
16
16
  }
@@ -43,11 +43,11 @@ async function convertTagName(context, uri, casing, tsPluginClient) {
43
43
  }
44
44
  exports.convertTagName = convertTagName;
45
45
  async function convertAttrName(context, uri, casing, tsPluginClient) {
46
- const sourceFile = context.language.files.get(uri);
46
+ const sourceFile = context.language.scripts.get(uri);
47
47
  if (!sourceFile) {
48
48
  return;
49
49
  }
50
- const rootCode = sourceFile?.generated?.code;
50
+ const rootCode = sourceFile?.generated?.root;
51
51
  if (!(rootCode instanceof language_core_1.VueGeneratedCode)) {
52
52
  return;
53
53
  }
@@ -100,7 +100,7 @@ async function getNameCasing(context, uri, tsPluginClient) {
100
100
  }
101
101
  exports.getNameCasing = getNameCasing;
102
102
  async function detect(context, uri, tsPluginClient) {
103
- const rootFile = context.language.files.get(uri)?.generated?.code;
103
+ const rootFile = context.language.scripts.get(uri)?.generated?.root;
104
104
  if (!(rootFile instanceof language_core_1.VueGeneratedCode)) {
105
105
  return {
106
106
  tag: [],
@@ -175,7 +175,7 @@ function getTemplateTagsAndAttrs(sourceFile) {
175
175
  const ast = sourceFile.sfc.template?.ast;
176
176
  const tags = new Map();
177
177
  if (ast) {
178
- for (const node of vue.eachElementNode(ast)) {
178
+ for (const node of vue.forEachElementNode(ast)) {
179
179
  if (!tags.has(node.tag)) {
180
180
  tags.set(node.tag, { offsets: [], attrs: new Map() });
181
181
  }
@@ -1,2 +1,2 @@
1
- import type { ServicePlugin } from '@volar/language-service';
2
- export declare function create(): ServicePlugin;
1
+ import type { LanguageServicePlugin } from '@volar/language-service';
2
+ export declare function create(): LanguageServicePlugin;
@@ -1,10 +1,10 @@
1
- import type { ServiceContext, ServicePlugin } from '@volar/language-service';
1
+ import type { ServiceContext, LanguageServicePlugin } from '@volar/language-service';
2
2
  import type * as ts from 'typescript';
3
- import type * as vscode from 'vscode-languageserver-protocol';
4
3
  import type { TextDocument } from 'vscode-languageserver-textdocument';
5
- export declare function create(ts: typeof import('typescript'), getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): ServicePlugin;
6
- export declare function isCharacterTyping(document: TextDocument, lastChange: {
7
- range: vscode.Range;
4
+ export declare function create(ts: typeof import('typescript'), getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): LanguageServicePlugin;
5
+ export declare function isCharacterTyping(document: TextDocument, change: {
8
6
  text: string;
7
+ rangeOffset: number;
8
+ rangeLength: number;
9
9
  }): boolean;
10
10
  export declare function isBlacklistNode(ts: typeof import('typescript'), node: ts.Node, pos: number, allowAccessDotValue: boolean): boolean;
@@ -18,11 +18,15 @@ function create(ts, getTsPluginClient) {
18
18
  const tsPluginClient = getTsPluginClient?.(context);
19
19
  let currentReq = 0;
20
20
  return {
21
- async provideAutoInsertionEdit(document, position, lastChange) {
21
+ async provideAutoInsertionEdit(document, selection, change) {
22
+ // selection must at end of change
23
+ if (document.offsetAt(selection) !== change.rangeOffset + change.text.length) {
24
+ return;
25
+ }
22
26
  if (!isTsDocument(document)) {
23
27
  return;
24
28
  }
25
- if (!isCharacterTyping(document, lastChange)) {
29
+ if (!isCharacterTyping(document, change)) {
26
30
  return;
27
31
  }
28
32
  const req = ++currentReq;
@@ -35,22 +39,24 @@ function create(ts, getTsPluginClient) {
35
39
  if (!enabled) {
36
40
  return;
37
41
  }
38
- const [code, file] = context.documents.getVirtualCodeByUri(document.uri);
39
- if (!file) {
42
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
43
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
44
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
45
+ if (!sourceScript) {
40
46
  return;
41
47
  }
42
48
  let ast;
43
- let sourceCodeOffset = document.offsetAt(position);
44
- const fileName = context.env.typescript.uriToFileName(file.id);
45
- if (file?.generated) {
46
- const script = file.generated.languagePlugin.typescript?.getScript(file.generated.code);
47
- if (script?.code !== code) {
49
+ let sourceCodeOffset = document.offsetAt(selection);
50
+ const fileName = context.env.typescript.uriToFileName(sourceScript.id);
51
+ if (sourceScript.generated) {
52
+ const serviceScript = sourceScript.generated.languagePlugin.typescript?.getServiceScript(sourceScript.generated.root);
53
+ if (!serviceScript || serviceScript?.code !== virtualCode) {
48
54
  return;
49
55
  }
50
- ast = getAst(ts, fileName, script.code.snapshot, script.scriptKind);
56
+ ast = getAst(ts, fileName, virtualCode.snapshot, serviceScript.scriptKind);
51
57
  let mapped = false;
52
- for (const [_1, [_2, map]] of context.language.files.getMaps(code)) {
53
- const sourceOffset = map.getSourceOffset(document.offsetAt(position));
58
+ for (const [_1, [_2, map]] of context.language.maps.forEach(virtualCode)) {
59
+ const sourceOffset = map.getSourceOffset(document.offsetAt(selection));
54
60
  if (sourceOffset !== undefined) {
55
61
  sourceCodeOffset = sourceOffset[0];
56
62
  mapped = true;
@@ -62,9 +68,9 @@ function create(ts, getTsPluginClient) {
62
68
  }
63
69
  }
64
70
  else {
65
- ast = getAst(ts, fileName, file.snapshot);
71
+ ast = getAst(ts, fileName, sourceScript.snapshot);
66
72
  }
67
- if (isBlacklistNode(ts, ast, document.offsetAt(position), false)) {
73
+ if (isBlacklistNode(ts, ast, document.offsetAt(selection), false)) {
68
74
  return;
69
75
  }
70
76
  const props = await tsPluginClient?.getPropertiesAtLocation(fileName, sourceCodeOffset) ?? [];
@@ -87,21 +93,13 @@ function isTsDocument(document) {
87
93
  document.languageId === 'typescriptreact';
88
94
  }
89
95
  const charReg = /\w/;
90
- function isCharacterTyping(document, lastChange) {
91
- const lastCharacter = lastChange.text[lastChange.text.length - 1];
92
- const rangeStart = lastChange.range.start;
93
- const position = {
94
- line: rangeStart.line,
95
- character: rangeStart.character + lastChange.text.length,
96
- };
97
- const nextCharacter = document.getText({
98
- start: position,
99
- end: { line: position.line, character: position.character + 1 },
100
- });
96
+ function isCharacterTyping(document, change) {
97
+ const lastCharacter = change.text[change.text.length - 1];
98
+ const nextCharacter = document.getText().substring(change.rangeOffset + change.text.length, change.rangeOffset + change.text.length + 1);
101
99
  if (lastCharacter === undefined) { // delete text
102
100
  return false;
103
101
  }
104
- if (lastChange.text.indexOf('\n') >= 0) { // multi-line change
102
+ if (change.text.indexOf('\n') >= 0) { // multi-line change
105
103
  return false;
106
104
  }
107
105
  return charReg.test(lastCharacter) && !charReg.test(nextCharacter);
@@ -1,2 +1,2 @@
1
- import type { ServicePlugin } from '@volar/language-service';
2
- export declare function create(ts: typeof import('typescript')): ServicePlugin;
1
+ import type { LanguageServicePlugin } from '@volar/language-service';
2
+ export declare function create(ts: typeof import('typescript')): LanguageServicePlugin;
@@ -7,19 +7,25 @@ function create(ts) {
7
7
  name: 'vue-autoinsert-parentheses',
8
8
  create(context) {
9
9
  return {
10
- async provideAutoInsertionEdit(document, position, lastChange) {
10
+ async provideAutoInsertionEdit(document, selection, change) {
11
+ // selection must at end of change
12
+ if (document.offsetAt(selection) !== change.rangeOffset + change.text.length) {
13
+ return;
14
+ }
11
15
  const enabled = await context.env.getConfiguration?.('vue.autoInsert.parentheses') ?? false;
12
16
  if (!enabled) {
13
17
  return;
14
18
  }
15
- if (!(0, vue_autoinsert_dotvalue_1.isCharacterTyping)(document, lastChange)) {
19
+ if (!(0, vue_autoinsert_dotvalue_1.isCharacterTyping)(document, change)) {
16
20
  return;
17
21
  }
18
- const [virtualCode] = context.documents.getVirtualCodeByUri(document.uri);
19
- if (virtualCode?.id !== 'template_format') {
22
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
23
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
24
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
25
+ if (!virtualCode?.id.startsWith('template_inline_ts_')) {
20
26
  return;
21
27
  }
22
- const offset = document.offsetAt(position);
28
+ const offset = document.offsetAt(selection);
23
29
  for (const mappedRange of virtualCode.mappings) {
24
30
  const generatedCodeEnd = mappedRange.generatedOffsets[mappedRange.generatedOffsets.length - 1]
25
31
  + mappedRange.lengths[mappedRange.lengths.length - 1];
@@ -1,2 +1,2 @@
1
- import type { ServicePlugin } from '@volar/language-service';
2
- export declare function create(): ServicePlugin;
1
+ import type { LanguageServicePlugin } from '@volar/language-service';
2
+ export declare function create(): LanguageServicePlugin;
@@ -6,24 +6,16 @@ function create() {
6
6
  name: 'vue-autoinsert-space',
7
7
  create(context) {
8
8
  return {
9
- async provideAutoInsertionEdit(document, _, lastChange) {
9
+ async provideAutoInsertionEdit(document, selection, change) {
10
10
  if (document.languageId === 'html' || document.languageId === 'jade') {
11
11
  const enabled = await context.env.getConfiguration?.('vue.autoInsert.bracketSpacing') ?? true;
12
12
  if (!enabled) {
13
13
  return;
14
14
  }
15
- if (lastChange.text === '{}'
16
- && document.getText({
17
- start: { line: lastChange.range.start.line, character: lastChange.range.start.character - 1 },
18
- end: { line: lastChange.range.start.line, character: lastChange.range.start.character + 3 }
19
- }) === '{{}}') {
20
- return {
21
- newText: ` $0 `,
22
- range: {
23
- start: { line: lastChange.range.start.line, character: lastChange.range.start.character + 1 },
24
- end: { line: lastChange.range.start.line, character: lastChange.range.start.character + 1 }
25
- },
26
- };
15
+ if (change.text === '{}'
16
+ && document.getText().substring(change.rangeOffset - 1, change.rangeOffset + 3) === '{{}}'
17
+ && document.offsetAt(selection) === change.rangeOffset + 1) {
18
+ return ` $0 `;
27
19
  }
28
20
  }
29
21
  },
@@ -1,2 +1,2 @@
1
- import type { ServicePlugin } from '@volar/language-service';
2
- export declare function create(): ServicePlugin;
1
+ import type { LanguageServicePlugin } from '@volar/language-service';
2
+ export declare function create(): LanguageServicePlugin;
@@ -27,11 +27,13 @@ function create() {
27
27
  },
28
28
  };
29
29
  function worker(uri, callback) {
30
- const [virtualCode, sourceFile] = context.documents.getVirtualCodeByUri(uri);
31
- if (!(sourceFile?.generated?.code instanceof language_core_1.VueGeneratedCode) || !sourceFile) {
30
+ const decoded = context.decodeEmbeddedDocumentUri(uri);
31
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
32
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
33
+ if (!virtualCode || !(sourceScript?.generated?.root instanceof language_core_1.VueGeneratedCode) || !sourceScript) {
32
34
  return;
33
35
  }
34
- return callback(virtualCode, sourceFile);
36
+ return callback(virtualCode, sourceScript);
35
37
  }
36
38
  },
37
39
  };
@@ -1,2 +1,2 @@
1
- import type { ServicePlugin } from '@volar/language-service';
2
- export declare function create(): ServicePlugin;
1
+ import type { LanguageServicePlugin } from '@volar/language-service';
2
+ export declare function create(): LanguageServicePlugin;
@@ -1,2 +1,2 @@
1
- import { ServicePlugin } from '../types';
2
- export declare function create(ts: typeof import('typescript')): ServicePlugin;
1
+ import { LanguageServicePlugin, ServiceContext } from '../types';
2
+ export declare function create(ts: typeof import('typescript'), getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): LanguageServicePlugin;
@@ -6,19 +6,23 @@ const shared_1 = require("@vue/shared");
6
6
  const path = require("path-browserify");
7
7
  const vue_extract_file_1 = require("../plugins/vue-extract-file");
8
8
  const types_1 = require("../types");
9
- function create(ts) {
9
+ const getUserPreferences_1 = require("volar-service-typescript/lib/configs/getUserPreferences");
10
+ function create(ts, getTsPluginClient) {
10
11
  return {
11
12
  name: 'vue-document-drop',
12
13
  create(context) {
13
14
  let casing = types_1.TagNameCasing.Pascal; // TODO
15
+ const tsPluginClient = getTsPluginClient?.(context);
14
16
  return {
15
17
  async provideDocumentDropEdits(document, _position, dataTransfer) {
16
18
  if (document.languageId !== 'html') {
17
19
  return;
18
20
  }
19
- const [virtualCode, sourceFile] = context.documents.getVirtualCodeByUri(document.uri);
20
- const vueVirtualCode = sourceFile?.generated?.code;
21
- if (!virtualCode || !(vueVirtualCode instanceof language_core_1.VueGeneratedCode)) {
21
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
22
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
23
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
24
+ const vueVirtualCode = sourceScript?.generated?.root;
25
+ if (!sourceScript || !virtualCode || !(vueVirtualCode instanceof language_core_1.VueGeneratedCode)) {
22
26
  return;
23
27
  }
24
28
  let importUri;
@@ -41,14 +45,28 @@ function create(ts) {
41
45
  const additionalEdit = {};
42
46
  const code = [...(0, language_core_1.forEachEmbeddedCode)(vueVirtualCode)].find(code => code.id === (sfc.scriptSetup ? 'scriptSetupFormat' : 'scriptFormat'));
43
47
  const lastImportNode = (0, vue_extract_file_1.getLastImportNode)(ts, script.ast);
44
- let importPath = path.relative(path.dirname(document.uri), importUri)
45
- || importUri.substring(importUri.lastIndexOf('/') + 1);
46
- if (!importPath.startsWith('./') && !importPath.startsWith('../')) {
47
- importPath = './' + importPath;
48
+ const incomingFileName = context.env.typescript.uriToFileName(importUri);
49
+ let importPath;
50
+ const serviceScript = sourceScript.generated?.languagePlugin.typescript?.getServiceScript(vueVirtualCode);
51
+ if (tsPluginClient && serviceScript) {
52
+ const tsDocumentUri = context.encodeEmbeddedDocumentUri(sourceScript.id, serviceScript.code.id);
53
+ const tsDocument = context.documents.get(tsDocumentUri, serviceScript.code.languageId, serviceScript.code.snapshot);
54
+ const preferences = await (0, getUserPreferences_1.getUserPreferences)(context, tsDocument);
55
+ const importPathRequest = await tsPluginClient.getImportPathForFile(vueVirtualCode.fileName, incomingFileName, preferences);
56
+ if (importPathRequest) {
57
+ importPath = importPathRequest;
58
+ }
59
+ }
60
+ if (!importPath) {
61
+ importPath = path.relative(path.dirname(vueVirtualCode.fileName), incomingFileName)
62
+ || importUri.substring(importUri.lastIndexOf('/') + 1);
63
+ if (!importPath.startsWith('./') && !importPath.startsWith('../')) {
64
+ importPath = './' + importPath;
65
+ }
48
66
  }
49
67
  additionalEdit.changes ??= {};
50
- additionalEdit.changes[context.documents.getVirtualCodeUri(sourceFile.id, code.id)] = [];
51
- additionalEdit.changes[context.documents.getVirtualCodeUri(sourceFile.id, code.id)].push({
68
+ additionalEdit.changes[context.encodeEmbeddedDocumentUri(sourceScript.id, code.id)] = [];
69
+ additionalEdit.changes[context.encodeEmbeddedDocumentUri(sourceScript.id, code.id)].push({
52
70
  range: lastImportNode ? {
53
71
  start: script.ast.getLineAndCharacterOfPosition(lastImportNode.end),
54
72
  end: script.ast.getLineAndCharacterOfPosition(lastImportNode.end),
@@ -62,7 +80,7 @@ function create(ts) {
62
80
  if (sfc.script) {
63
81
  const edit = (0, vue_extract_file_1.createAddComponentToOptionEdit)(ts, sfc.script.ast, newName);
64
82
  if (edit) {
65
- additionalEdit.changes[context.documents.getVirtualCodeUri(sourceFile.id, code.id)].push({
83
+ additionalEdit.changes[context.encodeEmbeddedDocumentUri(sourceScript.id, code.id)].push({
66
84
  range: {
67
85
  start: document.positionAt(edit.range.start),
68
86
  end: document.positionAt(edit.range.end),
@@ -1,6 +1,6 @@
1
- import type { ServiceContext, ServicePlugin } from '@volar/language-service';
1
+ import type { ServiceContext, LanguageServicePlugin } from '@volar/language-service';
2
2
  import type * as ts from 'typescript';
3
- export declare function create(ts: typeof import('typescript'), getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): ServicePlugin;
3
+ export declare function create(ts: typeof import('typescript'), getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): LanguageServicePlugin;
4
4
  export declare function getLastImportNode(ts: typeof import('typescript'), sourceFile: ts.SourceFile): ts.Node | undefined;
5
5
  export declare function createAddComponentToOptionEdit(ts: typeof import('typescript'), ast: ts.SourceFile, componentName: string): {
6
6
  range: import("@vue/language-core").TextRange;
@@ -15,11 +15,13 @@ function create(ts, getTsPluginClient) {
15
15
  if (startOffset === endOffset) {
16
16
  return;
17
17
  }
18
- const [code, vueCode] = context.documents.getVirtualCodeByUri(document.uri);
19
- if (!(vueCode?.generated?.code instanceof language_core_1.VueGeneratedCode) || code?.id !== 'template') {
18
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
19
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
20
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
21
+ if (!(sourceScript?.generated?.root instanceof language_core_1.VueGeneratedCode) || virtualCode?.id !== 'template') {
20
22
  return;
21
23
  }
22
- const { sfc } = vueCode.generated.code;
24
+ const { sfc } = sourceScript.generated.root;
23
25
  const script = sfc.scriptSetup ?? sfc.script;
24
26
  if (!sfc.template || !script) {
25
27
  return;
@@ -43,13 +45,15 @@ function create(ts, getTsPluginClient) {
43
45
  async resolveCodeAction(codeAction) {
44
46
  const { uri, range, newName } = codeAction.data;
45
47
  const [startOffset, endOffset] = range;
46
- const [code, sourceFile] = context.documents.getVirtualCodeByUri(uri);
47
- if (!(sourceFile?.generated?.code instanceof language_core_1.VueGeneratedCode) || code?.id !== 'template') {
48
+ const decoded = context.decodeEmbeddedDocumentUri(uri);
49
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
50
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
51
+ if (!(sourceScript?.generated?.root instanceof language_core_1.VueGeneratedCode) || virtualCode?.id !== 'template') {
48
52
  return codeAction;
49
53
  }
50
- const document = context.documents.get(uri, code.languageId, code.snapshot);
51
- const sfcDocument = context.documents.get(sourceFile.id, sourceFile.languageId, sourceFile.snapshot);
52
- const { sfc } = sourceFile.generated.code;
54
+ const document = context.documents.get(uri, virtualCode.languageId, virtualCode.snapshot);
55
+ const sfcDocument = context.documents.get(sourceScript.id, sourceScript.languageId, sourceScript.snapshot);
56
+ const { sfc } = sourceScript.generated.root;
53
57
  const script = sfc.scriptSetup ?? sfc.script;
54
58
  if (!sfc.template || !script) {
55
59
  return codeAction;
@@ -58,7 +62,7 @@ function create(ts, getTsPluginClient) {
58
62
  if (!templateCodeRange) {
59
63
  return codeAction;
60
64
  }
61
- const toExtract = await tsPluginClient?.collectExtractProps(sourceFile.generated.code.fileName, templateCodeRange) ?? [];
65
+ const toExtract = await tsPluginClient?.collectExtractProps(sourceScript.generated.root.fileName, templateCodeRange) ?? [];
62
66
  if (!toExtract) {
63
67
  return codeAction;
64
68
  }
@@ -122,7 +126,7 @@ function create(ts, getTsPluginClient) {
122
126
  // editing vue sfc
123
127
  {
124
128
  textDocument: {
125
- uri: sourceFile.id,
129
+ uri: sourceScript.id,
126
130
  version: null,
127
131
  },
128
132
  edits: sfcEdits,
@@ -1,7 +1,7 @@
1
- import type { ServicePlugin } from '@volar/language-service';
1
+ import type { LanguageServicePlugin } from '@volar/language-service';
2
2
  import * as vue from '@vue/language-core';
3
3
  import type { TextDocument } from 'vscode-languageserver-textdocument';
4
4
  export interface Provide {
5
5
  'vue/vueFile': (document: TextDocument) => vue.VueGeneratedCode | undefined;
6
6
  }
7
- export declare function create(): ServicePlugin;
7
+ export declare function create(): LanguageServicePlugin;
@@ -17,8 +17,26 @@ function create() {
17
17
  sfcDataProvider ??= html.newHTMLDataProvider('vue', (0, data_1.loadLanguageBlocks)(context.env.locale ?? 'en'));
18
18
  return [sfcDataProvider];
19
19
  },
20
+ async getFormattingOptions(document, options, context) {
21
+ return await worker(document, async (vueCode) => {
22
+ const formatSettings = await context.env.getConfiguration?.('html.format') ?? {};
23
+ const blockTypes = ['template', 'script', 'style'];
24
+ for (const customBlock of vueCode.sfc.customBlocks) {
25
+ blockTypes.push(customBlock.type);
26
+ }
27
+ return {
28
+ ...options,
29
+ ...formatSettings,
30
+ wrapAttributes: 'auto',
31
+ unformatted: '',
32
+ contentUnformatted: blockTypes.join(','),
33
+ endWithNewline: options.insertFinalNewline ? true
34
+ : options.trimFinalNewlines ? false
35
+ : document.getText().endsWith('\n'),
36
+ };
37
+ }) ?? {};
38
+ },
20
39
  }).create(context);
21
- const htmlLanguageService = htmlPlugin.provide['html/languageService']();
22
40
  return {
23
41
  ...htmlPlugin,
24
42
  provide: {
@@ -28,20 +46,19 @@ function create() {
28
46
  });
29
47
  },
30
48
  },
31
- async resolveEmbeddedCodeFormattingOptions(code, options) {
32
- const sourceFile = context.language.files.getByVirtualCode(code);
33
- if (sourceFile.generated?.code instanceof vue.VueGeneratedCode) {
34
- if (code.id === 'scriptFormat' || code.id === 'scriptSetupFormat') {
49
+ async resolveEmbeddedCodeFormattingOptions(sourceScript, virtualCode, options) {
50
+ if (sourceScript.generated?.root instanceof vue.VueGeneratedCode) {
51
+ if (virtualCode.id === 'scriptFormat' || virtualCode.id === 'scriptSetupFormat') {
35
52
  if (await context.env.getConfiguration?.('vue.format.script.initialIndent') ?? false) {
36
53
  options.initialIndentLevel++;
37
54
  }
38
55
  }
39
- else if (code.id.startsWith('style_')) {
56
+ else if (virtualCode.id.startsWith('style_')) {
40
57
  if (await context.env.getConfiguration?.('vue.format.style.initialIndent') ?? false) {
41
58
  options.initialIndentLevel++;
42
59
  }
43
60
  }
44
- else if (code.id === 'template') {
61
+ else if (virtualCode.id === 'template') {
45
62
  if (await context.env.getConfiguration?.('vue.format.template.initialIndent') ?? true) {
46
63
  options.initialIndentLevel++;
47
64
  }
@@ -134,29 +151,13 @@ function create() {
134
151
  return result;
135
152
  });
136
153
  },
137
- provideDocumentFormattingEdits(document, range, options) {
138
- return worker(document, async (vueCode) => {
139
- const formatSettings = await context.env.getConfiguration?.('html.format') ?? {};
140
- const blockTypes = ['template', 'script', 'style'];
141
- for (const customBlock of vueCode.sfc.customBlocks) {
142
- blockTypes.push(customBlock.type);
143
- }
144
- return htmlLanguageService.format(document, range, {
145
- ...options,
146
- ...formatSettings,
147
- unformatted: '',
148
- contentUnformatted: blockTypes.join(','),
149
- endWithNewline: options.insertFinalNewline ? true
150
- : options.trimFinalNewlines ? false
151
- : document.getText().endsWith('\n'),
152
- });
153
- });
154
- },
155
154
  };
156
155
  function worker(document, callback) {
157
- const [vueFile] = context.documents.getVirtualCodeByUri(document.uri);
158
- if (vueFile instanceof vue.VueGeneratedCode) {
159
- return callback(vueFile);
156
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
157
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
158
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
159
+ if (virtualCode instanceof vue.VueGeneratedCode) {
160
+ return callback(virtualCode);
160
161
  }
161
162
  }
162
163
  },
@@ -1,3 +1,3 @@
1
1
  import type { ServiceContext, ServiceEnvironment } from '@volar/language-service';
2
- import { ServicePlugin, VueCompilerOptions } from '../types';
3
- export declare function create(mode: 'html' | 'pug', ts: typeof import('typescript'), getVueOptions: (env: ServiceEnvironment) => VueCompilerOptions, getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): ServicePlugin;
2
+ import { LanguageServicePlugin, VueCompilerOptions } from '../types';
3
+ export declare function create(mode: 'html' | 'pug', ts: typeof import('typescript'), getVueOptions: (env: ServiceEnvironment) => VueCompilerOptions, getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): LanguageServicePlugin;
@@ -89,9 +89,10 @@ function create(mode, ts, getVueOptions, getTsPluginClient) {
89
89
  }
90
90
  let sync;
91
91
  let currentVersion;
92
- const [_, sourceFile] = context.documents.getVirtualCodeByUri(document.uri);
93
- if (sourceFile?.generated?.code instanceof language_core_1.VueGeneratedCode) {
94
- sync = (await provideHtmlData(sourceFile.id, sourceFile.generated.code)).sync;
92
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
93
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
94
+ if (sourceScript?.generated?.root instanceof language_core_1.VueGeneratedCode) {
95
+ sync = (await provideHtmlData(sourceScript.id, sourceScript.generated.root)).sync;
95
96
  currentVersion = await sync();
96
97
  }
97
98
  let htmlComplete = await baseServiceInstance.provideCompletionItems?.(document, position, completionContext, token);
@@ -101,8 +102,8 @@ function create(mode, ts, getVueOptions, getTsPluginClient) {
101
102
  if (!htmlComplete) {
102
103
  return;
103
104
  }
104
- if (sourceFile?.generated?.code instanceof language_core_1.VueGeneratedCode) {
105
- await afterHtmlCompletion(htmlComplete, context.documents.get(sourceFile.id, sourceFile.languageId, sourceFile.snapshot), sourceFile.generated.code);
105
+ if (sourceScript?.generated?.root instanceof language_core_1.VueGeneratedCode) {
106
+ await afterHtmlCompletion(htmlComplete, context.documents.get(sourceScript.id, sourceScript.languageId, sourceScript.snapshot), sourceScript.generated.root);
106
107
  }
107
108
  return htmlComplete;
108
109
  },
@@ -115,12 +116,14 @@ function create(mode, ts, getVueOptions, getTsPluginClient) {
115
116
  return;
116
117
  }
117
118
  const result = [];
118
- const [virtualCode] = context.documents.getVirtualCodeByUri(document.uri);
119
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
120
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
121
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
119
122
  if (!virtualCode) {
120
123
  return;
121
124
  }
122
125
  for (const map of context.documents.getMaps(virtualCode)) {
123
- const code = context.language.files.get(map.sourceDocument.uri)?.generated?.code;
126
+ const code = context.language.scripts.get(map.sourceDocument.uri)?.generated?.root;
124
127
  const scanner = getScanner(baseServiceInstance, document);
125
128
  if (code instanceof language_core_1.VueGeneratedCode && scanner) {
126
129
  // visualize missing required props
@@ -213,7 +216,7 @@ function create(mode, ts, getVueOptions, getTsPluginClient) {
213
216
  if (!isSupportedDocument(document)) {
214
217
  return;
215
218
  }
216
- if (context.documents.getVirtualCodeByUri(document.uri)[0]) {
219
+ if (context.decodeEmbeddedDocumentUri(document.uri)) {
217
220
  updateExtraCustomData([]);
218
221
  }
219
222
  return baseServiceInstance.provideHover?.(document, position, token);
@@ -223,12 +226,14 @@ function create(mode, ts, getVueOptions, getTsPluginClient) {
223
226
  return;
224
227
  }
225
228
  const originalResult = await baseServiceInstance.provideDiagnostics?.(document, token);
226
- const [virtualCode] = context.documents.getVirtualCodeByUri(document.uri);
229
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
230
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
231
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
227
232
  if (!virtualCode) {
228
233
  return;
229
234
  }
230
235
  for (const map of context.documents.getMaps(virtualCode)) {
231
- const code = context.language.files.get(map.sourceDocument.uri)?.generated?.code;
236
+ const code = context.language.scripts.get(map.sourceDocument.uri)?.generated?.root;
232
237
  if (!(code instanceof language_core_1.VueGeneratedCode)) {
233
238
  continue;
234
239
  }
@@ -269,19 +274,24 @@ function create(mode, ts, getVueOptions, getTsPluginClient) {
269
274
  if (!isSupportedDocument(document)) {
270
275
  return;
271
276
  }
272
- const [_virtualCode, sourceFile] = context.documents.getVirtualCodeByUri(document.uri);
273
- if (!sourceFile
274
- || !(sourceFile.generated?.code instanceof language_core_1.VueGeneratedCode)
275
- || !sourceFile.generated.code.sfc.template) {
277
+ const languageService = context.inject('typescript/languageService');
278
+ if (!languageService) {
279
+ return;
280
+ }
281
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
282
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
283
+ if (!sourceScript
284
+ || !(sourceScript.generated?.root instanceof language_core_1.VueGeneratedCode)
285
+ || !sourceScript.generated.root.sfc.template) {
276
286
  return [];
277
287
  }
278
- const { template } = sourceFile.generated.code.sfc;
288
+ const { template } = sourceScript.generated.root.sfc;
279
289
  const spans = common_1.getComponentSpans.call({
280
- files: context.language.files,
281
- languageService: context.inject('typescript/languageService'),
290
+ files: context.language.scripts,
291
+ languageService,
282
292
  typescript: ts,
283
293
  vueOptions: getVueOptions(context.env),
284
- }, sourceFile.generated.code, template, {
294
+ }, sourceScript.generated.root, template, {
285
295
  start: document.offsetAt(range.start),
286
296
  length: document.offsetAt(range.end) - document.offsetAt(range.start),
287
297
  });
@@ -1,2 +1,2 @@
1
- import type { ServicePlugin } from '@volar/language-service';
2
- export declare function create(ts: typeof import('typescript')): ServicePlugin;
1
+ import type { LanguageServicePlugin } from '@volar/language-service';
2
+ export declare function create(ts: typeof import('typescript')): LanguageServicePlugin;
@@ -10,7 +10,9 @@ function create(ts) {
10
10
  provideCodeActions(document, range, _context) {
11
11
  const startOffset = document.offsetAt(range.start);
12
12
  const endOffset = document.offsetAt(range.end);
13
- const [virtualCode] = context.documents.getVirtualCodeByUri(document.uri);
13
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
14
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
15
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
14
16
  if (!(virtualCode instanceof language_core_1.VueGeneratedCode)) {
15
17
  return;
16
18
  }
@@ -20,7 +22,7 @@ function create(ts) {
20
22
  }
21
23
  const templateStartOffset = template.startTagEnd;
22
24
  const result = [];
23
- for (const node of (0, language_core_1.eachElementNode)(template.ast)) {
25
+ for (const node of (0, language_core_1.forEachElementNode)(template.ast)) {
24
26
  if (startOffset > templateStartOffset + node.loc.end.offset || endOffset < templateStartOffset + node.loc.start.offset) {
25
27
  return;
26
28
  }
@@ -1,2 +1,2 @@
1
- import type { ServiceContext, ServicePlugin } from '@volar/language-service';
2
- export declare function create(ts: typeof import('typescript'), getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): ServicePlugin;
1
+ import type { ServiceContext, LanguageServicePlugin } from '@volar/language-service';
2
+ export declare function create(ts: typeof import('typescript'), getTsPluginClient?: (context: ServiceContext) => typeof import('@vue/typescript-plugin/lib/client') | undefined): LanguageServicePlugin;
@@ -10,8 +10,10 @@ function create(ts, getTsPluginClient) {
10
10
  const tsPluginClient = getTsPluginClient?.(context);
11
11
  return {
12
12
  async provideInlayHints(document, range) {
13
- const [virtualCode, sourceFile] = context.documents.getVirtualCodeByUri(document.uri);
14
- if (!(sourceFile?.generated?.code instanceof vue.VueGeneratedCode) || virtualCode?.id !== 'template') {
13
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
14
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
15
+ const virtualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
16
+ if (!(sourceScript?.generated?.root instanceof vue.VueGeneratedCode) || virtualCode?.id !== 'template') {
15
17
  return;
16
18
  }
17
19
  const hoverOffsets = [];
@@ -25,9 +27,9 @@ function create(ts, getTsPluginClient) {
25
27
  })]);
26
28
  }
27
29
  for (const [pointerPosition, hoverOffset] of hoverOffsets) {
28
- for (const [_1, [_2, map]] of context.language.files.getMaps(virtualCode)) {
30
+ for (const [_1, [_2, map]] of context.language.maps.forEach(virtualCode)) {
29
31
  for (const [sourceOffset] of map.getSourceOffsets(hoverOffset)) {
30
- const quickInfo = await tsPluginClient?.getQuickInfoAtPosition(sourceFile.generated.code.fileName, sourceOffset);
32
+ const quickInfo = await tsPluginClient?.getQuickInfoAtPosition(sourceScript.generated.root.fileName, sourceOffset);
31
33
  if (quickInfo) {
32
34
  inlayHints.push({
33
35
  position: { line: pointerPosition.line, character: pointerPosition.character + 2 },
@@ -1,2 +1,2 @@
1
- import type { ServicePlugin } from '../types';
2
- export declare function create(): ServicePlugin;
1
+ import type { LanguageServicePlugin } from '../types';
2
+ export declare function create(): LanguageServicePlugin;
@@ -9,11 +9,13 @@ function create() {
9
9
  async provideInlayHints(document, range) {
10
10
  const settings = {};
11
11
  const result = [];
12
- const [vitualFile] = context.documents.getVirtualCodeByUri(document.uri);
13
- if (vitualFile) {
12
+ const decoded = context.decodeEmbeddedDocumentUri(document.uri);
13
+ const sourceScript = decoded && context.language.scripts.get(decoded[0]);
14
+ const vitualCode = decoded && sourceScript?.generated?.embeddedCodes.get(decoded[1]);
15
+ if (vitualCode) {
14
16
  const start = document.offsetAt(range.start);
15
17
  const end = document.offsetAt(range.end);
16
- for (const mapping of vitualFile.mappings) {
18
+ for (const mapping of vitualCode.mappings) {
17
19
  const hint = mapping.data.__hint;
18
20
  if (mapping.generatedOffsets[0] >= start
19
21
  && mapping.generatedOffsets[mapping.generatedOffsets.length - 1] + mapping.lengths[mapping.lengths.length - 1] <= end
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vue/language-service",
3
- "version": "2.0.7",
3
+ "version": "2.0.10",
4
4
  "license": "MIT",
5
5
  "files": [
6
6
  "data",
@@ -16,23 +16,23 @@
16
16
  "update-html-data": "node ./scripts/update-html-data.js"
17
17
  },
18
18
  "dependencies": {
19
- "@volar/language-core": "~2.1.3",
20
- "@volar/language-service": "~2.1.3",
21
- "@volar/typescript": "~2.1.3",
19
+ "@volar/language-core": "~2.2.0-alpha.5",
20
+ "@volar/language-service": "~2.2.0-alpha.5",
21
+ "@volar/typescript": "~2.2.0-alpha.5",
22
22
  "@vue/compiler-dom": "^3.4.0",
23
- "@vue/language-core": "2.0.7",
23
+ "@vue/language-core": "2.0.10",
24
24
  "@vue/shared": "^3.4.0",
25
- "@vue/typescript-plugin": "2.0.7",
25
+ "@vue/typescript-plugin": "2.0.10",
26
26
  "computeds": "^0.0.1",
27
27
  "path-browserify": "^1.0.1",
28
- "volar-service-css": "0.0.34",
29
- "volar-service-emmet": "0.0.34",
30
- "volar-service-html": "0.0.34",
31
- "volar-service-json": "0.0.34",
32
- "volar-service-pug": "0.0.34",
33
- "volar-service-pug-beautify": "0.0.34",
34
- "volar-service-typescript": "0.0.34",
35
- "volar-service-typescript-twoslash-queries": "0.0.34",
28
+ "volar-service-css": "0.0.38",
29
+ "volar-service-emmet": "0.0.38",
30
+ "volar-service-html": "0.0.38",
31
+ "volar-service-json": "0.0.38",
32
+ "volar-service-pug": "0.0.38",
33
+ "volar-service-pug-beautify": "0.0.38",
34
+ "volar-service-typescript": "0.0.38",
35
+ "volar-service-typescript-twoslash-queries": "0.0.38",
36
36
  "vscode-html-languageservice": "^5.1.0",
37
37
  "vscode-languageserver-textdocument": "^1.0.11",
38
38
  "vscode-uri": "^3.0.8"
@@ -40,8 +40,8 @@
40
40
  "devDependencies": {
41
41
  "@types/node": "latest",
42
42
  "@types/path-browserify": "latest",
43
- "@volar/kit": "~2.1.3",
43
+ "@volar/kit": "~2.2.0-alpha.5",
44
44
  "vscode-languageserver-protocol": "^3.17.5"
45
45
  },
46
- "gitHead": "4a37e8f3ebcf31ecfd2ea627f7611d5990ec5df6"
46
+ "gitHead": "a20a2ee950b63a949660b7e8faf0faed0e5bad33"
47
47
  }