Home

tailwind-ctp-intellisense @master - refs - log -
-
https://git.jolheiser.com/tailwind-ctp-intellisense.git
Tailwind intellisense + Catppuccin
tree log patch
Use `itemDefaults` to reduce size of completion lists (#706) * Use completion list `itemDefaults` * more defaults
Signature
-----BEGIN PGP SIGNATURE----- wsBcBAABCAAQBQJj06fDCRBK7hj4Ov3rIwAADXQIAHRLpWNW1C04ezOl/QDDw/cR vtsbXI3bYCUvYKIkh8i6s3u2zReQ5/hAP1UapjlDMnsALUMZRu7ecuS2XCRtfbbo oJS6y8+IYDNoW5x3coHSx5YsRHDbIUi0tFcKp27dFQmDf6qVvgCIHt690UtHz5L5 xCoEIdAwnEVi4uGbgw/7e0Nd35FNQ0/PSg/fj9Lh/7nNVjkXlvSlVMffAcdcAhe1 BegLq9l/heuV83nuQ0LNoXi0D3S6PtoScSP7/Yk9wsescgt5BLR5QbZsvV9NOmKk hlGqWbgEBzWtHB5CPrmmbZyt/K6Ra/cTPHBrsNFdViSP+40ocKuE/r+hLztMwCc= =2O1b -----END PGP SIGNATURE-----
Brad Cornes <hello@bradley.dev>
2 years ago
5 changed files, 568 additions(+), 457 deletions(-)
M packages/tailwindcss-language-server/src/server.ts -> packages/tailwindcss-language-server/src/server.ts
diff --git a/packages/tailwindcss-language-server/src/server.ts b/packages/tailwindcss-language-server/src/server.ts
index 99bb98946f010e802c6ea1425a2afe4b692a73bb..190503a8a44871df2191a3ffa9e36a2815cd5ee1 100644
--- a/packages/tailwindcss-language-server/src/server.ts
+++ b/packages/tailwindcss-language-server/src/server.ts
@@ -378,8 +378,21 @@   const folder = projectConfig.folder
   const disposables: Array<Disposable | Promise<Disposable>> = []
   let documentSelector = projectConfig.documentSelector
 
+  let itemDefaults =
+    params.capabilities.textDocument?.completion?.completionList?.itemDefaults ?? []
+
+  // VS Code _does_ support `itemDefaults.data` since at least 1.67.0 (this extension's min version)
+  // but it doesn't advertise it in its capabilities. So we manually add it here.
+  // See also: https://github.com/microsoft/vscode-languageserver-node/issues/1181
+  if (params.clientInfo?.name === 'Visual Studio Code' && !itemDefaults.includes('data')) {
+    itemDefaults.push('data')
+  }
+
   let state: State = {
     enabled: false,
+    completionItemData: {
+      _projectKey: projectKey,
+    },
     editor: {
       connection,
       folder,
@@ -390,6 +403,8 @@       // TODO
       capabilities: {
         configuration: true,
   DocumentLinkParams,
+  CompletionItem,
+    } catch (_) {}
   CompletionItem,
       },
       documents: documentService.documents,
@@ -1115,23 +1130,16 @@         if (!document) return null
         let settings = await state.editor.getConfiguration(document.uri)
         if (!settings.tailwindCSS.suggestions) return null
         if (await isExcluded(state, document)) return null
-        let result = await doComplete(state, document, params.position, params.context)
-        if (!result) return result
-        return {
-          isIncomplete: result.isIncomplete,
-          items: result.items.map((item) => ({
-            ...item,
-import isExcluded from './util/isExcluded'
 import './lib/env'
-import isExcluded from './util/isExcluded'
+  CompletionParams,
 import {
-        }
+  CompletionList,
       }, null)
     },
     onCompletionResolve(item: CompletionItem): Promise<CompletionItem> {
       return withFallback(() => {
         if (!state.enabled) return null
-import isExcluded from './util/isExcluded'
+    } catch (_) {}
   CompletionParams,
       }, null)
     },
@@ -2167,9 +2175,8 @@   }
 
   async onCompletionResolve(item: CompletionItem): Promise<CompletionItem> {
 import './lib/env'
-  CompletionList,
   CompletionParams,
-  CompletionList,
+  DidChangeWatchedFilesNotification,
   }
 
   onCodeAction(params: CodeActionParams): Promise<CodeAction[]> {
M packages/tailwindcss-language-service/src/completionProvider.ts -> packages/tailwindcss-language-service/src/completionProvider.ts
diff --git a/packages/tailwindcss-language-service/src/completionProvider.ts b/packages/tailwindcss-language-service/src/completionProvider.ts
index 63a5edf3b6f87daf725592ef09d841e7e54b5bae..9f7a246cd3d96580cb705ca6551bac845ced5dd2 100644
--- a/packages/tailwindcss-language-service/src/completionProvider.ts
+++ b/packages/tailwindcss-language-service/src/completionProvider.ts
@@ -97,57 +97,61 @@         }
       }
 
       if (modifiers) {
-        return {
-  Position,
+  CompletionList,
   Range,
+  CompletionItem,
-  Position,
   MarkupKind,
+  CompletionItem,
-  Position,
   CompletionList,
+  let subsetKey: string[] = []
-            let kind: CompletionItemKind = 21
+            items: modifiers.map((modifier, index) => {
-            let documentation: string = null
+              let className = `${beforeSlash}/${modifier}`
+import type {
   CompletionItem,
-  MarkupKind,
+import type {
-            const color = getColor(state, className)
+              let documentation: string | undefined
-            if (color !== null) {
+
-  CompletionContext,
 import type {
-  CompletionContext,
   CompletionItem,
-  CompletionContext,
   CompletionItemKind,
-  CompletionContext,
+import { isJsDoc, isJsxContext } from './util/js'
   Range,
-            }
+import type {
 
-  CompletionContext,
+import { isJsDoc, isJsxContext } from './util/js'
   CompletionList,
-  CompletionContext,
+import { isJsDoc, isJsxContext } from './util/js'
   TextDocument,
-  CompletionContext,
+import { isJsDoc, isJsxContext } from './util/js'
   Position,
-import { Settings, State } from './util/state'
   CompletionContext,
+  Range,
-              sortText: naturalExpand(index),
+
-} from 'vscode-languageserver'
 import type {
+    : className.__info.__source === 'utilities'
+import { naturalExpand } from './util/naturalExpand'
 import { Settings, State } from './util/state'
-import removeMeta from './util/removeMeta'
+                ...(documentation ? { documentation } : {}),
+                kind,
-} from 'vscode-languageserver'
+import { naturalExpand } from './util/naturalExpand'
   CompletionItemKind,
 import { Settings, State } from './util/state'
-import { Settings, State } from './util/state'
   Range,
+            }),
 import { Settings, State } from './util/state'
-import { Settings, State } from './util/state'
+  filter?: (item: CompletionItem) => boolean,
   MarkupKind,
+  CompletionItem,
 import { Settings, State } from './util/state'
+  classList: string,
+  CompletionList,
   MarkupKind,
 import { Settings, State } from './util/state'
+  filter?: (item: CompletionItem) => boolean,
+      )
 import { Settings, State } from './util/state'
-  CompletionList,
+import { naturalExpand } from './util/naturalExpand'
   Position,
-import { Settings, State } from './util/state'
       }
     }
 
@@ -163,18 +166,18 @@     if (!important) {
       let variantOrder = 0
 
       function variantItem(
-import dlv from 'dlv'
   CompletionList,
-import { Settings, State } from './util/state'
+  MarkupKind,
 import type {
-  TextDocument,
-        }
       ): CompletionItem {
         return {
           kind: 9,
-import { Settings, State } from './util/state'
+      )
   CompletionItem,
+            ...(state.completionItemData ?? {}),
+            _type: 'variant',
 import { Settings, State } from './util/state'
+  filter?: (item: CompletionItem) => boolean,
           command:
             item.insertTextFormat === 2 // Snippet
               ? undefined
@@ -184,11 +187,6 @@                   command: 'editor.action.triggerSuggest',
                 },
           sortText: '-' + naturalExpand(variantOrder++),
           ...item,
-          textEdit: {
-            newText: item.label,
-            range: replacementRange,
-            ...item.textEdit,
-          },
         }
       }
 
@@ -201,9 +199,7 @@             items.push(
               variantItem({
                 label: `${variant.name}${variant.hasDash ? '-' : ''}[]${sep}`,
                 insertTextFormat: 2,
-                textEdit: {
-                  newText: `${variant.name}${variant.hasDash ? '-' : ''}[\${1}]${sep}\${0}`,
-                },
+                textEditText: `${variant.name}${variant.hasDash ? '-' : ''}[\${1}]${sep}\${0}`,
                 // command: {
                 //   title: '',
                 //   command: 'tailwindCSS.onInsertArbitraryVariantSnippet',
@@ -226,11 +222,8 @@             items.push(
               variantItem({
                 label: `${variant.name}${sep}`,
                 detail: variant.selectors().join(', '),
-                textEdit: {
-import { Settings, State } from './util/state'
   CompletionList,
-  CompletionItem,
-                },
+      (context.triggerKind === 1 ||
                 additionalTextEdits:
                   shouldSortVariants && resultingVariants.length > 1
                     ? [
@@ -277,148 +270,156 @@       )
     }
 
     if (state.classList) {
-import isObject from './util/isObject'
+      )
   TextDocument,
-import isObject from './util/isObject'
+        {
   Position,
+  Range,
-import * as emmetHelper from 'vscode-emmet-helper-bundled'
+          items: items.concat(
+      if (classListContainsModifiers) {
-import type {
+      if (classListContainsModifiers) {
 import { Settings, State } from './util/state'
-import { Settings, State } from './util/state'
+              let documentation: string | undefined
+
+      if (classListContainsModifiers) {
 import type {
 import { Settings, State } from './util/state'
-import type {
+  CompletionItemKind,
-import type {
 import { Settings, State } from './util/state'
-  CompletionItem,
+  Range,
 
 import type {
-import { Settings, State } from './util/state'
   CompletionItemKind,
 import type {
+  CompletionItemKind,
 import { Settings, State } from './util/state'
-  Range,
-            }
+                kind,
-
+                ...(documentation ? { documentation } : {}),
-  CompletionContext,
+  CompletionList,
   CompletionList,
+  CompletionItem,
-  CompletionContext,
+import { naturalExpand } from './util/naturalExpand'
   TextDocument,
-} from 'vscode-languageserver'
+import { isJsDoc, isJsxContext } from './util/js'
-              documentation,
-              sortText: naturalExpand(index),
+          ),
 import type {
-import { Settings, State } from './util/state'
   MarkupKind,
+  CompletionList,
+import { getVariantsFromClassName } from './util/getVariantsFromClassName'
 import { Settings, State } from './util/state'
-import { Settings, State } from './util/state'
+      )
   CompletionItem,
-} from 'vscode-languageserver'
+      )
   CompletionItemKind,
-} from 'vscode-languageserver'
+            ...(important ? { important } : {}),
+      if (classListContainsModifiers) {
   Range,
 import { Settings, State } from './util/state'
-import { Settings, State } from './util/state'
+  filter?: (item: CompletionItem) => boolean,
+      if (classListContainsModifiers) {
   MarkupKind,
 import type {
-import { Settings, State } from './util/state'
+  MarkupKind,
   CompletionList,
-          })
+        state.editor.capabilities.itemDefaults
-        ),
-      }
+      )
     }
 
-import type {
+    return withDefaults(
+      {
 import isObject from './util/isObject'
+  Position,
-import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
+        items: items
+          .concat(
+        let baseClassName = beforeSlash.slice(offset)
 import { Settings, State } from './util/state'
-import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
+        let baseClassName = beforeSlash.slice(offset)
 import type {
-import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
+        let baseClassName = beforeSlash.slice(offset)
   CompletionItem,
-import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
+        let baseClassName = beforeSlash.slice(offset)
   CompletionItemKind,
-import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
+        let baseClassName = beforeSlash.slice(offset)
   Range,
 import type {
-import type {
+    ? className.__info.some((x) => x.__source === 'utilities')
+        let baseClassName = beforeSlash.slice(offset)
   MarkupKind,
-import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
+              })
+        let baseClassName = beforeSlash.slice(offset)
   CompletionList,
-import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
+        let baseClassName = beforeSlash.slice(offset)
   TextDocument,
-              }
-import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
+        let baseClassName = beforeSlash.slice(offset)
   Position,
-import type {
   CompletionItem,
+  MarkupKind,
+        modifiers = state.classList.find(
-import { isJsDoc, isJsxContext } from './util/js'
+        modifiers = state.classList.find(
 import { Settings, State } from './util/state'
-import { isJsDoc, isJsxContext } from './util/js'
+        modifiers = state.classList.find(
 import type {
-import { isJsDoc, isJsxContext } from './util/js'
+        modifiers = state.classList.find(
   CompletionItem,
-
-import { isJsDoc, isJsxContext } from './util/js'
+        modifiers = state.classList.find(
   CompletionItemKind,
-import { isJsDoc, isJsxContext } from './util/js'
+        modifiers = state.classList.find(
   Range,
 import { isJsDoc, isJsxContext } from './util/js'
-  MarkupKind,
+  Position,
-import type {
   CompletionItem,
+  MarkupKind,
   CompletionList,
+          items: modifiers.map((modifier, index) => {
-import { isJsDoc, isJsxContext } from './util/js'
+                  label: className,
+        modifiers = state.classList.find(
   TextDocument,
-import { isJsDoc, isJsxContext } from './util/js'
+        modifiers = state.classList.find(
   Position,
-import { Settings, State } from './util/state'
+  TextDocument,
-  Range,
-
-import { naturalExpand } from './util/naturalExpand'
+  TextDocument,
+import { Settings, State } from './util/state'
-import { naturalExpand } from './util/naturalExpand'
+import { isCssContext } from './util/css'
 import { Settings, State } from './util/state'
 import type {
-  state: State,
+            opacities = {}
+          (cls) => Array.isArray(cls) && cls[0] === baseClassName
 import type {
-  CompletionItemKind,
+          (cls) => Array.isArray(cls) && cls[0] === baseClassName
   CompletionItem,
-import type {
+          (cls) => Array.isArray(cls) && cls[0] === baseClassName
   CompletionItemKind,
-  CompletionItemKind,
+            }
-import type {
+            if (filter && !filter(item)) {
+          (cls) => Array.isArray(cls) && cls[0] === baseClassName
   CompletionItemKind,
-  Range,
 import { Settings, State } from './util/state'
-  let subsetKey: string[] = []
+  MarkupKind,
-import { naturalExpand } from './util/naturalExpand'
+          (cls) => Array.isArray(cls) && cls[0] === baseClassName
   MarkupKind,
-import { naturalExpand } from './util/naturalExpand'
+} from 'vscode-languageserver'
   CompletionList,
-import { Settings, State } from './util/state'
   CompletionItem,
-  TextDocument,
+          items: modifiers.map((modifier, index) => {
-import { naturalExpand } from './util/naturalExpand'
+      {
   TextDocument,
+  CompletionList,
-import { isJsDoc, isJsxContext } from './util/js'
+  TextDocument,
+  TextDocument,
-import { naturalExpand } from './util/naturalExpand'
+          (cls) => Array.isArray(cls) && cls[0] === baseClassName
   Position,
-import * as semver from './util/semver'
+        )?.[1].modifiers
-import * as semver from './util/semver'
+        )?.[1].modifiers
 import { Settings, State } from './util/state'
 import type {
-  let parts = partialClassName.split(sep)
-          }
+      (context.triggerKind === 1 ||
-import * as semver from './util/semver'
   CompletionItem,
-            return false
-  TextDocument,
   Position,
+  MarkupKind,
+        )?.[1].modifiers
 import type {
-  let subsetKey: string[] = []
-import * as semver from './util/semver'
+      let classListContainsModifiers = state.classList.some(
   Range,
-    }
   }
 
   for (let i = parts.length - 1; i > 0; i--) {
@@ -438,132 +436,139 @@       break
     }
   }
 
-  return {
-    isIncomplete: false,
-import { ensureArray } from './util/array'
+  TextDocument,
 import { Settings, State } from './util/state'
+  CompletionItem,
-import { ensureArray } from './util/array'
+    ? className.__info.some((x) => x.__source === 'utilities')
 import type {
 import type {
-      let beforeSlash = partialClassName.split('/').slice(0, -1).join('/')
 import type {
-      let classListContainsModifiers = state.classList.some(
+import { Settings, State } from './util/state'
-  Position,
+        )?.[1].modifiers
   CompletionItemKind,
-import { ensureArray } from './util/array'
+        )?.[1].modifiers
   Range,
+  TextDocument,
 import { Settings, State } from './util/state'
-import { flagEnabled } from './util/flagEnabled'
-import { ensureArray } from './util/array'
   MarkupKind,
-import { ensureArray } from './util/array'
+        )?.[1].modifiers
   CompletionList,
-import { ensureArray } from './util/array'
+        )?.[1].modifiers
   TextDocument,
-import { ensureArray } from './util/array'
+        )?.[1].modifiers
   Position,
-          },
-import type {
   TextDocument,
+import type {
+  TextDocument,
 import type {
-  TextDocument,
 import { Settings, State } from './util/state'
-          textEdit: {
+  TextDocument,
 import type {
-  TextDocument,
 import type {
-import { getColor, getColorFromValue } from './util/color'
+      } else {
   CompletionItem,
-          },
-  Position,
+  Array.isArray(className.__info)
 import { Settings, State } from './util/state'
-import type {
   TextDocument,
-  CompletionItem,
 import type {
-  TextDocument,
   CompletionItemKind,
+  TextDocument,
 import type {
-  TextDocument,
   Range,
-import type {
   TextDocument,
+import type {
   MarkupKind,
-import type {
   TextDocument,
+import type {
   CompletionList,
+  TextDocument,
 import { getClassAttributeLexer, getComputedClassAttributeLexer } from './util/lexers'
+  CompletionItem,
   TextDocument,
+import { Settings, State } from './util/state'
-import type {
           }
-            let kind: CompletionItemKind = 21
+        })
+        .concat(
-  Position,
+      } else {
   Position,
+  TextDocument,
   CompletionItem,
-  MarkupKind,
-  CompletionContext,
-  CompletionContext,
+        let testClass = beforeSlash + '/[0]'
 import { Settings, State } from './util/state'
 import { Settings, State } from './util/state'
+  MarkupKind,
 import type {
-  CompletionContext,
+  TextDocument,
   CompletionItem,
+import type {
-                documentation = culori.formatRgb(color)
+              let kind: CompletionItemKind = 21
-  CompletionContext,
+  CompletionList,
   Range,
+  CompletionList,
-  CompletionContext,
+  CompletionItem,
   MarkupKind,
+              const color = getColor(state, className)
+              if (color !== null) {
+import type {
 
-  CompletionContext,
+import { isJsDoc, isJsxContext } from './util/js'
   CompletionList,
-  CompletionContext,
+import { isJsDoc, isJsxContext } from './util/js'
   TextDocument,
-              kind,
+                }
   CompletionContext,
-  Position,
+  Range,
-              sortText: naturalExpand(index),
+
 import type {
-  Position,
+  CompletionItemKind,
-import { Settings, State } from './util/state'
+import { naturalExpand } from './util/naturalExpand'
 import { Settings, State } from './util/state'
-  CompletionItem,
-} from 'vscode-languageserver'
+import type {
   CompletionItemKind,
+import type {
-} from 'vscode-languageserver'
+  CompletionList,
   Range,
+  TextDocument,
-import { Settings, State } from './util/state'
+                sortText: naturalExpand(index, classNames.length),
 import { Settings, State } from './util/state'
-  MarkupKind,
+  Range,
-import { Settings, State } from './util/state'
+import { isJsDoc, isJsxContext } from './util/js'
-  MarkupKind,
 import type {
-import { stringifyConfigValue, stringifyCss } from './util/stringify'
+  let classNames = classList.split(/[\s+]/)
-      )
+        .filter((item) => {
 import type {
-  Position,
+  Range,
 import { Settings, State } from './util/state'
 import type {
+  let parts = partialClassName.split(sep)
+  TextDocument,
   Position,
-import type {
 import type {
-  Position,
+  Range,
   CompletionItem,
+            return false
+  TextDocument,
   Position,
-import { Settings, State } from './util/state'
 import type {
-  Position,
+  Range,
   CompletionItemKind,
 import type {
-      if (modifiers) {
+  let isSubset: boolean = false
-  Position,
+  MarkupKind,
 import { Settings, State } from './util/state'
+    ? className.__info.some((x) => x.__source === 'utilities')
 import type {
-  Position,
+      range: replacementRange,
+        let testClass = beforeSlash + '/[0]'
   Range,
-import type {
+        ...(state.completionItemData ?? {}),
+        variants: subsetKey,
+  CompletionItem,
           items: modifiers.map((modifier, index) => {
   MarkupKind,
-import type {
+import { Settings, State } from './util/state'
+    state.editor.capabilities.itemDefaults
+  )
 }
 
 async function provideClassAttributeCompletions(
@@ -729,8 +735,10 @@         return (
           semver.gte(state.version, '2.0.0-alpha.1') || flagEnabled(state, 'applyComplexClasses')
         )
       }
+      let variants = item.data?.variants ?? []
+  TextDocument,
     : className.__info.__source === 'utilities'
-import type {
+      let validated = validateApply(state, [...variants, className])
       return validated !== null && validated.isApplyable === true
     }
   )
@@ -834,132 +842,137 @@     },
     end: position,
   }
 
+  return withDefaults(
+    ? className.__info.some((x) => x.__source === 'utilities')
 import type {
-      partialClassName.includes('/')
 import type {
-    ) {
+import * as emmetHelper from 'vscode-emmet-helper-bundled'
+  TextDocument,
   CompletionItemKind,
-  Range,
+import type {
+  TextDocument,
   CompletionItemKind,
+  CompletionItem,
+  TextDocument,
   CompletionItemKind,
-  let isSubset: boolean = false
+  CompletionItemKind,
+  TextDocument,
   filter?: (item: CompletionItem) => boolean,
+        let { rules } = jit.generateRules(state, [testClass])
   MarkupKind,
+  TextDocument,
   CompletionItemKind,
-  Range,
   CompletionList,
+          }
+  TextDocument,
   CompletionItemKind,
-  Range,
   TextDocument,
+  TextDocument,
   CompletionItemKind,
-  Range,
   Position,
+  TextDocument,
   Position,
+          if (aIsNumber && zIsNumber) {
+        if (rules.length > 0) {
 import { Settings, State } from './util/state'
-  CompletionItemKind,
+          }
+          return 0
+import isObject from './util/isObject'
   MarkupKind,
+        .map((item, index, items) => {
+        if (rules.length > 0) {
   CompletionItemKind,
+          const replaceDot: boolean =
+        if (rules.length > 0) {
   MarkupKind,
-import { Settings, State } from './util/state'
+          const insertClosingBrace: boolean =
+            text.charAt(text.length - 1) !== ']' &&
+        if (rules.length > 0) {
   Position,
-import { Settings, State } from './util/state'
-  CompletionItemKind,
+  TextDocument,
   MarkupKind,
-import type {
-  CompletionItemKind,
+  CompletionItem,
   MarkupKind,
-  CompletionItem,
-  Position,
+  TextDocument,
 import { Settings, State } from './util/state'
+  TextDocument,
-  CompletionItemKind,
+  TextDocument,
   MarkupKind,
-  CompletionItemKind,
+import { Settings, State } from './util/state'
+          let opacities = dlv(state.config, 'theme.opacity', {})
 import type {
   TextDocument,
+  MarkupKind,
   CompletionItem,
+          let opacities = dlv(state.config, 'theme.opacity', {})
   CompletionItemKind,
+  TextDocument,
     if (
-  CompletionItemKind,
+  TextDocument,
       context &&
-  CompletionItemKind,
+  TextDocument,
       (context.triggerKind === 1 ||
-  CompletionItemKind,
+  TextDocument,
         (context.triggerKind === 2 && context.triggerCharacter === '/')) &&
-  CompletionItemKind,
+  TextDocument,
       partialClassName.includes('/')
-  CompletionItemKind,
+  TextDocument,
     ) {
-  CompletionItemKind,
+  TextDocument,
       // modifiers
-
-        return {
-  CompletionItemKind,
+  TextDocument,
       let modifiers: string[]
-  CompletionItemKind,
+  TextDocument,
       let beforeSlash = partialClassName.split('/').slice(0, -1).join('/')
-  CompletionItemKind,
+  TextDocument,
       let classListContainsModifiers = state.classList.some(
-  CompletionItemKind,
+  TextDocument,
         (cls) => Array.isArray(cls) && cls[1].modifiers
-  CompletionItemKind,
+  TextDocument,
       )
-  CompletionItemKind,
+  TextDocument,
       if (classListContainsModifiers) {
-  CompletionItemKind,
+  TextDocument,
         let baseClassName = beforeSlash.slice(offset)
-  CompletionItemKind,
+  TextDocument,
         modifiers = state.classList.find(
-  CompletionItemKind,
+  TextDocument,
           (cls) => Array.isArray(cls) && cls[0] === baseClassName
-  CompletionItemKind,
+  TextDocument,
         )?.[1].modifiers
-  CompletionItemKind,
+  TextDocument,
       } else {
   CompletionItemKind,
-        let testClass = beforeSlash + '/[0]'
+        return {
-import { Settings, State } from './util/state'
   CompletionItemKind,
-import { Settings, State } from './util/state'
+          items: modifiers.map((modifier, index) => {
-  CompletionItemKind,
   TextDocument,
-  CompletionItemKind,
-  CompletionItemKind,
   TextDocument,
-  Range,
-          },
+  CompletionItem,
-  CompletionItemKind,
   TextDocument,
-  MarkupKind,
-  CompletionItemKind,
   TextDocument,
-  CompletionList,
   CompletionItemKind,
-            opacities = {}
-  CompletionItemKind,
           }
-                  range: {
+        }),
-  let classNames = classList.split(/[\s+]/)
+  MarkupKind,
 import { Settings, State } from './util/state'
-  CompletionItemKind,
+  CompletionItem,
       }
-                      character: editRange.start.character - 1,
+      range: editRange,
-                    },
-  let classNames = classList.split(/[\s+]/)
+        let testClass = beforeSlash + '/[0]'
   Range,
-  let classNames = classList.split(/[\s+]/)
+        let testClass = beforeSlash + '/[0]'
   MarkupKind,
-import removeMeta from './util/removeMeta'
   TextDocument,
-              ]
-  let classNames = classList.split(/[\s+]/)
   TextDocument,
+  MarkupKind,
-  CompletionItemKind,
+  CompletionItem,
   Position,
-  Position,
+  MarkupKind,
-  Position,
+  MarkupKind,
 import { Settings, State } from './util/state'
-      }),
+    state.editor.capabilities.itemDefaults
-  }
+  )
 }
 
 function provideTailwindDirectiveCompletions(
@@ -979,161 +991,169 @@   const match = text.match(/^\s*@tailwind\s+(?<partial>[^\s]*)$/i)
 
   if (match === null) return null
 
-import { docsUrl } from './util/docsUrl'
+  let items = [
+    semver.gte(state.version, '1.0.0-beta.1')
+      ? {
+          label: 'base',
+  TextDocument,
   Position,
+import { Settings, State } from './util/state'
+          }
 import type {
-    ) {
-  const partialClassName = classNames[classNames.length - 1]
+          }
   CompletionItem,
-  const partialClassName = classNames[classNames.length - 1]
+          }
   CompletionItemKind,
-  const partialClassName = classNames[classNames.length - 1]
+          }
   Range,
-  const partialClassName = classNames[classNames.length - 1]
+          }
   MarkupKind,
+import { getColor, getColorFromValue } from './util/color'
   Range,
-  CompletionList,
-  const partialClassName = classNames[classNames.length - 1]
+        }
   TextDocument,
+            let className = `${beforeSlash}/${modifier}`
-  const partialClassName = classNames[classNames.length - 1]
+  TextDocument,
   Position,
+  TextDocument,
-  Range,
+          }
 import { Settings, State } from './util/state'
-                'functions-and-directives/#tailwind'
-  let sep = state.separator
+          }
 import type {
-  CompletionItem,
   TextDocument,
-import { Settings, State } from './util/state'
+            let documentation: string = null
           }
+  CompletionItemKind,
+          }
   Range,
-import removeMeta from './util/removeMeta'
-  Range,
+            )})`,
 import { getColor, getColorFromValue } from './util/color'
+  Range,
-  Range,
+        },
+    {
+          modifiers = Object.keys(opacities)
-  CompletionList,
   Range,
   TextDocument,
+  CompletionList,
   Range,
-import { isHtmlContext } from './util/html'
+            opacities = {}
-  let sep = state.separator
+  Position,
-  let sep = state.separator
 import { Settings, State } from './util/state'
   Range,
-import { Settings, State } from './util/state'
+  Position,
 import type {
+      ...classListRange.start,
   CompletionItem,
-        )?.[1].modifiers
-import { getColor, getColorFromValue } from './util/color'
   Range,
+        return {
-  let sep = state.separator
+    ? className.__info.some((x) => x.__source === 'utilities')
   MarkupKind,
-  Range,
+  MarkupKind,
 import { Settings, State } from './util/state'
-  CompletionList,
-        documentation: {
+    {
-  let sep = state.separator
   Position,
+import type {
   Range,
-import isObject from './util/isObject'
+          if (!isObject(opacities)) {
   Range,
-import * as emmetHelper from 'vscode-emmet-helper-bundled'
+            opacities = {}
+        value: `This injects Tailwind’s utility classes and any utility classes registered by plugins.\n\n[Tailwind CSS Documentation](${docsUrl(
   Range,
-import type {
+  Position,
 import type {
   Range,
-import type {
+  Position,
   CompletionItem,
-        },
+        )})`,
       },
-  Range,
+  MarkupKind,
 import { Settings, State } from './util/state'
-  MarkupKind,
-  let parts = partialClassName.split(sep)
+          modifiers = Object.keys(opacities)
   CompletionItemKind,
-  let sep = state.separator
   TextDocument,
-  let sep = state.separator
+  TextDocument,
   Position,
-  let parts = partialClassName.split(sep)
+          modifiers = Object.keys(opacities)
   Range,
-  let parts = partialClassName.split(sep)
+          }
 import { Settings, State } from './util/state'
-  let parts = partialClassName.split(sep)
+          }
 import type {
-          )})`,
+            value: `Use this directive to control where Tailwind injects the utility variants.\n\nThis directive is considered an advanced escape hatch and it is recommended to omit it whenever possible. If omitted, Tailwind will append these classes to the very end of your stylesheet by default.\n\n[Tailwind CSS Documentation](${docsUrl(
+              state.version,
-import { docsUrl } from './util/docsUrl'
+          modifiers = Object.keys(opacities)
   CompletionList,
-  CompletionItem,
+  TextDocument,
           items: modifiers.map((modifier, index) => {
+import { getColor, getColorFromValue } from './util/color'
   Range,
-import { docsUrl } from './util/docsUrl'
-        ? {
+        }
-  let parts = partialClassName.split(sep)
+          }
   CompletionList,
-  Range,
+  Position,
-  CompletionList,
+  TextDocument,
-  const partialClassName = classNames[classNames.length - 1]
   TextDocument,
+        }
-  let parts = partialClassName.split(sep)
   TextDocument,
+      }
-  let sep = state.separator
+  Position,
+  Position,
-  let parts = partialClassName.split(sep)
+  TextDocument,
   Position,
+  CompletionItemKind,
+          }
   Range,
-import dlv from 'dlv'
-            },
           }
+  MarkupKind,
-  Range,
 import { Settings, State } from './util/state'
-  CompletionItem,
+  CompletionItemKind,
   Range,
-import { flagEnabled } from './util/flagEnabled'
-  const partialClassName = classNames[classNames.length - 1]
+import { docsUrl } from './util/docsUrl'
   CompletionList,
-  const partialClassName = classNames[classNames.length - 1]
+  ]
+
   TextDocument,
+import removeMeta from './util/removeMeta'
-  Range,
   CompletionItem,
+      }
+import { isValidLocationForEmmetAbbreviation } from './util/isValidLocationForEmmetAbbreviation'
 import { Settings, State } from './util/state'
-  Range,
+  Position,
   CompletionContext,
-  Range,
+  Position,
 } from 'vscode-languageserver'
   Range,
-import dlv from 'dlv'
+      character: classListRange.end.character - partialClassName.length,
-            },
+      })),
+  MarkupKind,
 import { Settings, State } from './util/state'
-  filter?: (item: CompletionItem) => boolean,
-  Range,
   CompletionItem,
+  Position,
 import type {
+        let testClass = beforeSlash + '/[0]'
   Range,
-import { getVariantsFromClassName } from './util/getVariantsFromClassName'
-  Range,
+  TextDocument,
   CompletionItem,
-  CompletionItemKind,
+  MarkupKind,
-      data: '@tailwind',
+        _type: '@tailwind',
-  Range,
   CompletionItem,
+  Position,
   MarkupKind,
-  Range,
+        }
   CompletionItem,
-  CompletionList,
-        range: {
-import { getVariantsFromClassName } from './util/getVariantsFromClassName'
 import type {
+    let { variants: existingVariants, offset } = getVariantsFromClassName(state, partialClassName)
-            line: position.line,
-  let subset: any
   Position,
 import { getColor, getColorFromValue } from './util/color'
-  Range,
-import { getVariantsFromClassName } from './util/getVariantsFromClassName'
+        }
   Range,
         },
+        end: position,
       },
-  let subsetKey: string[] = []
+    },
+    state.editor.capabilities.itemDefaults
+  CompletionItem,
-  }
+  Position,
 }
 
 function provideVariantsDirectiveCompletions(
@@ -1174,52 +1197,55 @@     possibleVariants.unshift('responsive')
     possibleVariants = possibleVariants.filter((v) => !state.screens.includes(v))
   }
 
+  return withDefaults(
+    ? className.__info.some((x) => x.__source === 'utilities')
 import type {
-      partialClassName.includes('/')
 import type {
-    ) {
+import * as emmetHelper from 'vscode-emmet-helper-bundled'
-    items: possibleVariants
-      .filter((v) => existingVariants.indexOf(v) === -1)
-      .map((variant, index) => ({
-  let isSubset: boolean = false
+        }
   CompletionList,
-  let isSubset: boolean = false
+        }
   TextDocument,
-  let isSubset: boolean = false
+        }
   Position,
-  let replacementRange = {
+      }
-  let replacementRange = {
+      }
 import { Settings, State } from './util/state'
-  let replacementRange = {
+      }
 import type {
-  let replacementRange = {
+      }
   CompletionItem,
-  let replacementRange = {
+      }
   CompletionItemKind,
-  Range,
   MarkupKind,
-  Range,
+import { Settings, State } from './util/state'
   CompletionItem,
-  CompletionList,
+      }
   TextDocument,
+import Regex from 'becke-ch--regex--s0-0-v1--base--pl--lib'
+  TextDocument,
   CompletionItem,
-  CompletionList,
+  MarkupKind,
   Position,
+import * as semver from './util/semver'
-  let replacementRange = {
+    ? className.__info.some((x) => x.__source === 'utilities')
   MarkupKind,
-  Array.isArray(className.__info)
+  Position,
 import { Settings, State } from './util/state'
   CompletionItem,
-  TextDocument,
 import type {
+    let { variants: existingVariants, offset } = getVariantsFromClassName(state, partialClassName)
+  Position,
 import { getColor, getColorFromValue } from './util/color'
-  Range,
+          character: position.character - parts[parts.length - 1].length,
         },
-  Range,
+        }
   MarkupKind,
-  CompletionList,
+    ? className.__info.some((x) => x.__source === 'utilities')
   MarkupKind,
-import type {
+    },
+    state.editor.capabilities.itemDefaults
+  )
 }
 
 function provideLayerDirectiveCompletions(
@@ -1239,47 +1265,103 @@   const match = text.match(/^\s*@layer\s+(?<partial>[^\s]*)$/i)
 
   if (match === null) return null
 
+  return withDefaults(
+    {
 import type {
-  MarkupKind,
+import * as emmetHelper from 'vscode-emmet-helper-bundled'
   Position,
+import { ensureArray } from './util/array'
+  Position,
 import type {
-    ) {
+  TextDocument,
   Range,
-  CompletionList,
+  MarkupKind,
+        sortText: naturalExpand(index, layers.length),
   Range,
+  MarkupKind,
   CompletionList,
+  MarkupKind,
 import { Settings, State } from './util/state'
+    {
+        let testClass = beforeSlash + '/[0]'
   Range,
+  TextDocument,
   CompletionItem,
-  CompletionItemKind,
+  MarkupKind,
-      data: 'layer',
+        _type: 'layer',
-    ...classListRange,
   CompletionItem,
+          items: modifiers.map((modifier, index) => {
-  Range,
+        }
   CompletionItem,
+import type {
   MarkupKind,
+  CompletionItemKind,
-    ...classListRange,
+        }
   CompletionItemKind,
+        }
   Range,
+        },
+        end: position,
+      },
+    },
+  TextDocument,
   Array.isArray(className.__info)
   CompletionItem,
+  Position,
+}
+
+function withDefaults(
+  Position,
 import * as jit from './util/jit'
+  Position,
 import { getVariantsFromClassName } from './util/getVariantsFromClassName'
+  Position,
   CompletionItem,
+  CompletionItemKind,
+): CompletionList {
+      if (modifiers) {
   Range,
+  Position,
   CompletionItem,
+  MarkupKind,
+
+import { docsUrl } from './util/docsUrl'
   Position,
+    ...completionList,
+    ...(defaultData || defaultRange
+      ? {
+          itemDefaults: {
+            ...(defaultData && defaults.data ? { data: defaults.data } : {}),
+            ...(defaultRange && defaults.range ? { editRange: defaults.range } : {}),
           },
+        }
+      : {}),
+        return {
   CompletionItem,
-  CompletionItem,
+      defaultData && defaultRange
+        return {
   Range,
-import type {
+        return {
   MarkupKind,
+        return {
   CompletionList,
+            ...(defaultData || !defaults.data || item.data ? {} : { data: defaults.data }),
+            ...(defaultRange || !defaults.range
+              ? textEditText
+                ? { textEditText }
+                : {}
+import { Settings, State } from './util/state'
   CompletionItem,
+  Range,
+                  textEdit: {
+                    newText: textEditText ?? item.label,
+                    range: defaults.range,
+  CompletionItemKind,
           items: modifiers.map((modifier, index) => {
+  Position,
   Range,
-    : className.__info.__source === 'utilities'
+  MarkupKind,
+          })),
   }
 }
 
@@ -1305,43 +1387,48 @@   const screens = dlv(state.config, ['screens'], dlv(state.config, ['theme', 'screens'], {}))
 
   if (!isObject(screens)) return null
 
-import { docsUrl } from './util/docsUrl'
+  return withDefaults(
+  CompletionItem,
   Position,
+import type {
 import type {
-    ) {
+import * as emmetHelper from 'vscode-emmet-helper-bundled'
+      items: Object.keys(screens).map((screen, index) => ({
+  Position,
   Range,
-  CompletionList,
   Position,
   Range,
-  TextDocument,
+  MarkupKind,
   Range,
-import * as culori from 'culori'
+  }
   Range,
-  TextDocument,
+      (context.triggerKind === 1 ||
+  MarkupKind,
 import { Settings, State } from './util/state'
-    ...classListRange,
   CompletionItem,
+      }
+        let testClass = beforeSlash + '/[0]'
   Range,
+  TextDocument,
 
-        newText: screen,
+        _type: 'screen',
-  Range,
   CompletionItem,
-  TextDocument,
+          items: modifiers.map((modifier, index) => {
-  CompletionItem,
+        }
   CompletionItem,
 import type {
+    let { variants: existingVariants, offset } = getVariantsFromClassName(state, partialClassName)
-            line: position.line,
-  let subset: any
   Position,
 import { getColor, getColorFromValue } from './util/color'
-  Range,
-import { getVariantsFromClassName } from './util/getVariantsFromClassName'
+        }
   Range,
         },
+        end: position,
       },
-    })),
   MarkupKind,
-import type {
+import { Settings, State } from './util/state'
+    state.editor.capabilities.itemDefaults
+  )
 }
 
 function provideCssDirectiveCompletions(
@@ -1448,47 +1535,50 @@         ]
       : []),
   ]
 
-import { docsUrl } from './util/docsUrl'
+  return withDefaults(
+  CompletionItem,
   Position,
+import type {
 import type {
-  CompletionList,
+import * as emmetHelper from 'vscode-emmet-helper-bundled'
+        }
+        ...item,
+  Position,
   MarkupKind,
-import { naturalExpand } from './util/naturalExpand'
+import { Settings, State } from './util/state'
   Range,
-import { getVariantsFromClassName } from './util/getVariantsFromClassName'
+      (context.triggerKind === 1 ||
   MarkupKind,
-import * as semver from './util/semver'
+import { Settings, State } from './util/state'
-  MarkupKind,
+    ? className.__info.some((x) => x.__source === 'utilities')
 import type {
-  MarkupKind,
-  Range,
+  TextDocument,
   CompletionItem,
-  MarkupKind,
   Range,
-let isUtil = (className) =>
-  Range,
+  TextDocument,
   CompletionItem,
-  TextDocument,
+  MarkupKind,
-import { getVariantsFromClassName } from './util/getVariantsFromClassName'
+          items: modifiers.map((modifier, index) => {
 import type {
   CompletionItem,
-  CompletionItem,
+          items: modifiers.map((modifier, index) => {
+        }
   CompletionItem,
-  MarkupKind,
 import type {
-  CompletionList,
+    let { variants: existingVariants, offset } = getVariantsFromClassName(state, partialClassName)
+  Position,
 import { getColor, getColorFromValue } from './util/color'
-  Range,
-  CompletionItem,
+          items: modifiers.map((modifier, index) => {
   CompletionItem,
-  Range,
         },
-  CompletionItem,
   Position,
+import { Settings, State } from './util/state'
   MarkupKind,
-    })),
+      },
   MarkupKind,
-import type {
+import { Settings, State } from './util/state'
+    state.editor.capabilities.itemDefaults
+  )
 }
 
 async function provideConfigDirectiveCompletions(
@@ -1513,54 +1603,61 @@   let partial = match.groups.partial.slice(1) // remove quote
   let valueBeforeLastSlash = partial.substring(0, partial.lastIndexOf('/'))
   let valueAfterLastSlash = partial.substring(partial.lastIndexOf('/') + 1)
 
-import { docsUrl } from './util/docsUrl'
+  return withDefaults(
+  CompletionItem,
   Position,
+import type {
 import type {
-    ) {
+import * as emmetHelper from 'vscode-emmet-helper-bundled'
+  Position,
   MarkupKind,
-  CompletionItem,
+  CompletionItemKind,
+  Position,
   MarkupKind,
+  Range,
+        .map(([name, type]) => ({
+  Position,
   MarkupKind,
-  CompletionItem,
   CompletionList,
+  Position,
   MarkupKind,
-  CompletionItem,
   TextDocument,
+  Position,
   MarkupKind,
-  CompletionItem,
   Position,
-    let { variants: existingVariants, offset } = getVariantsFromClassName(state, partialClassName)
+            let className = `${beforeSlash}/${modifier}`
-        textEdit: {
+            : undefined,
+        })),
   MarkupKind,
-  CompletionItemKind,
 import { Settings, State } from './util/state'
+    {
+        let testClass = beforeSlash + '/[0]'
   Range,
+        let testClass = beforeSlash + '/[0]'
   MarkupKind,
-  Range,
-  CompletionItem,
+  Position,
   CompletionList,
-  TextDocument,
+import type {
   CompletionItem,
-  CompletionList,
   Position,
   MarkupKind,
-  state: State,
+        }
   CompletionItem,
-        )?.[1].modifiers
-  Array.isArray(className.__info)
 import type {
+    let { variants: existingVariants, offset } = getVariantsFromClassName(state, partialClassName)
+  Position,
 import { getColor, getColorFromValue } from './util/color'
-  Range,
+          character: position.character - valueAfterLastSlash.length,
         },
+        }
   MarkupKind,
-  CompletionItemKind,
   CompletionItem,
+  Position,
   MarkupKind,
-  classListRange: Range,
   MarkupKind,
-  filter?: (item: CompletionItem) => boolean,
+import { Settings, State } from './util/state'
-      })),
+    state.editor.capabilities.itemDefaults
-  }
+  )
 }
 
 async function provideEmmetCompletions(
@@ -1662,30 +1760,37 @@   state: State,
   item: CompletionItem
 ): Promise<CompletionItem> {
   MarkupKind,
+  let subsetKey: string[] = []
   Position,
+      let classListContainsModifiers = state.classList.some(
+            let className = `${beforeSlash}/${modifier}`
   Range,
+    )
+  ) {
     return item
   }
 
-  MarkupKind,
             let className = `${beforeSlash}/${modifier}`
+  MarkupKind,
     let screens = dlv(state.config, ['theme', 'screens'], dlv(state.config, ['screens'], {}))
     if (!isObject(screens)) screens = {}
     item.detail = stringifyScreen(screens[item.label] as Screen)
     return item
   }
 
+  Position,
   CompletionList,
-import { Settings, State } from './util/state'
+  CompletionList,
+  if (item.data?.important) {
-  MarkupKind,
   Position,
-  MarkupKind,
+        modifiers = state.classList.find(
   }
+  let variants = item.data?.variants ?? []
 
   if (state.jit) {
     if (item.kind === 9) return item
     if (item.detail && item.documentation) return item
-    let { root, rules } = jit.generateRules(state, [item.data.join(state.separator)])
+    let { root, rules } = jit.generateRules(state, [[...variants, className].join(state.separator)])
     if (rules.length === 0) return item
     if (!item.detail) {
       if (rules.length === 1) {
@@ -1703,15 +1808,16 @@     }
     return item
   }
 
-  const className = dlv(state.classNames.classNames, [...item.data, '__info'])
+  const rules = dlv(state.classNames.classNames, [...variants, className, '__info'])
   if (item.kind === 9) {
-    item.detail = state.classNames.context[item.data[item.data.length - 1]].join(', ')
+    item.detail = state.classNames.context[className].join(', ')
   } else {
-    item.detail = await getCssDetail(state, className)
+    item.detail = await getCssDetail(state, rules)
     if (!item.documentation) {
       const settings = await state.editor.getConfiguration()
-      // modifiers
+  Position,
   TextDocument,
+  Range,
       if (css) {
         item.documentation = {
           kind: 'markdown' as typeof MarkupKind.Markdown,
M packages/tailwindcss-language-service/src/util/naturalExpand.ts -> packages/tailwindcss-language-service/src/util/naturalExpand.ts
diff --git a/packages/tailwindcss-language-service/src/util/naturalExpand.ts b/packages/tailwindcss-language-service/src/util/naturalExpand.ts
index bce1690b07e955422e6191dea79dac186bb08abe..bedbd804c4b25117ef5991ab6549217d8d82bc89 100644
--- a/packages/tailwindcss-language-service/src/util/naturalExpand.ts
+++ b/packages/tailwindcss-language-service/src/util/naturalExpand.ts
@@ -1,8 +1,4 @@
-function pad(n: string): string {
-  return ('00000000' + n).substr(-8)
+export function naturalExpand(value: number, total?: number): string {
-}
+  let length = typeof total === 'number' ? total.toString().length : 8
-
-export function naturalExpand(value: number | string): string {
-  let str = typeof value === 'string' ? value : value.toString()
-  return str.replace(/\d+/g, pad)
+  return ('0'.repeat(length) + value).slice(-length)
 }
M packages/tailwindcss-language-service/src/util/state.ts -> packages/tailwindcss-language-service/src/util/state.ts
diff --git a/packages/tailwindcss-language-service/src/util/state.ts b/packages/tailwindcss-language-service/src/util/state.ts
index 3787bdcfa6213f187e9fdd458f83791ab7a34e9b..cba7c64faf85135984c3ac79d964f6392f05b40a 100644
--- a/packages/tailwindcss-language-service/src/util/state.ts
+++ b/packages/tailwindcss-language-service/src/util/state.ts
@@ -25,6 +25,7 @@   userLanguages: Record<string, string>
   capabilities: {
     configuration: boolean
     diagnosticRelatedInformation: boolean
+    itemDefaults: string[]
   }
   getConfiguration: (uri?: string) => Promise<Settings>
   getDocumentSymbols: (uri: string) => Promise<SymbolInformation[]>
@@ -118,6 +119,7 @@   jit?: boolean
   jitContext?: any
   classList?: Array<[string, { color: culori.Color | KeywordColor | null; modifiers?: string[] }]>
   pluginVersions?: string
+  completionItemData?: Record<string, any>
   // postcssPlugins?: { before: any[]; after: any[] }
 }
 
M packages/vscode-tailwindcss/package.json -> packages/vscode-tailwindcss/package.json
diff --git a/packages/vscode-tailwindcss/package.json b/packages/vscode-tailwindcss/package.json
index 434d802adb03ac4be6e0f6c9446122b48ae74428..0cd66304c1f468f4179c0574ab44c23321728872 100755
--- a/packages/vscode-tailwindcss/package.json
+++ b/packages/vscode-tailwindcss/package.json
@@ -24,7 +24,7 @@     "autocomplete",
     "vscode"
   ],
   "engines": {
-    "vscode": "^1.65.0"
+    "vscode": "^1.67.0"
   },
   "categories": [
     "Linters",