Skip to content

Commit 636f192

Browse files
committed
Refactor
1 parent c9e4aef commit 636f192

File tree

3 files changed

+111
-95
lines changed

3 files changed

+111
-95
lines changed

packages/tailwindcss-language-server/src/projects.ts

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -223,18 +223,22 @@ export async function createProjectService(
223223
try {
224224
directory = path.resolve(path.dirname(getFileFsPath(document.uri)), directory)
225225
let dirents = await fs.promises.readdir(directory, { withFileTypes: true })
226+
226227
let result: Array<[string, { isDirectory: boolean }] | null> = await Promise.all(
227228
dirents.map(async (dirent) => {
228229
let isDirectory = dirent.isDirectory()
229-
return (await isExcluded(
230+
let shouldRemove = await isExcluded(
230231
state,
231232
document,
232233
path.join(directory, dirent.name, isDirectory ? '/' : ''),
233-
))
234-
? null
235-
: [dirent.name, { isDirectory }]
234+
)
235+
236+
if (shouldRemove) return null
237+
238+
return [dirent.name, { isDirectory }]
236239
}),
237240
)
241+
238242
return result.filter((item) => item !== null)
239243
} catch {
240244
return []

packages/tailwindcss-language-service/src/completionProvider.ts

Lines changed: 91 additions & 88 deletions
Original file line numberDiff line numberDiff line change
@@ -1396,106 +1396,106 @@ function provideCssDirectiveCompletions(
13961396

13971397
if (match === null) return null
13981398

1399-
const items: CompletionItem[] = [
1400-
{
1401-
label: '@tailwind',
1399+
let items: CompletionItem[] = []
1400+
1401+
items.push({
1402+
label: '@tailwind',
1403+
documentation: {
1404+
kind: 'markdown' as typeof MarkupKind.Markdown,
1405+
value: `Use the \`@tailwind\` directive to insert Tailwind’s \`base\`, \`components\`, \`utilities\` and \`${
1406+
state.jit && semver.gte(state.version, '2.1.99') ? 'variants' : 'screens'
1407+
}\` styles into your CSS.\n\n[Tailwind CSS Documentation](${docsUrl(
1408+
state.version,
1409+
'functions-and-directives/#tailwind',
1410+
)})`,
1411+
},
1412+
})
1413+
1414+
items.push({
1415+
label: '@screen',
1416+
documentation: {
1417+
kind: 'markdown' as typeof MarkupKind.Markdown,
1418+
value: `The \`@screen\` directive allows you to create media queries that reference your breakpoints by name instead of duplicating their values in your own CSS.\n\n[Tailwind CSS Documentation](${docsUrl(
1419+
state.version,
1420+
'functions-and-directives/#screen',
1421+
)})`,
1422+
},
1423+
})
1424+
1425+
items.push({
1426+
label: '@apply',
1427+
documentation: {
1428+
kind: 'markdown' as typeof MarkupKind.Markdown,
1429+
value: `Use \`@apply\` to inline any existing utility classes into your own custom CSS.\n\n[Tailwind CSS Documentation](${docsUrl(
1430+
state.version,
1431+
'functions-and-directives/#apply',
1432+
)})`,
1433+
},
1434+
})
1435+
1436+
if (semver.gte(state.version, '1.8.0')) {
1437+
items.push({
1438+
label: '@layer',
14021439
documentation: {
14031440
kind: 'markdown' as typeof MarkupKind.Markdown,
1404-
value: `Use the \`@tailwind\` directive to insert Tailwind’s \`base\`, \`components\`, \`utilities\` and \`${
1405-
state.jit && semver.gte(state.version, '2.1.99') ? 'variants' : 'screens'
1406-
}\` styles into your CSS.\n\n[Tailwind CSS Documentation](${docsUrl(
1441+
value: `Use the \`@layer\` directive to tell Tailwind which "bucket" a set of custom styles belong to. Valid layers are \`base\`, \`components\`, and \`utilities\`.\n\n[Tailwind CSS Documentation](${docsUrl(
14071442
state.version,
1408-
'functions-and-directives/#tailwind',
1443+
'functions-and-directives/#layer',
14091444
)})`,
14101445
},
1411-
},
1412-
{
1413-
label: '@screen',
1446+
})
1447+
}
1448+
1449+
if (semver.gte(state.version, '2.99.0')) {
1450+
//
1451+
} else {
1452+
items.push({
1453+
label: '@variants',
14141454
documentation: {
14151455
kind: 'markdown' as typeof MarkupKind.Markdown,
1416-
value: `The \`@screen\` directive allows you to create media queries that reference your breakpoints by name instead of duplicating their values in your own CSS.\n\n[Tailwind CSS Documentation](${docsUrl(
1456+
value: `You can generate \`responsive\`, \`hover\`, \`focus\`, \`active\`, and other variants of your own utilities by wrapping their definitions in the \`@variants\` directive.\n\n[Tailwind CSS Documentation](${docsUrl(
14171457
state.version,
1418-
'functions-and-directives/#screen',
1458+
'functions-and-directives/#variants',
14191459
)})`,
14201460
},
1421-
},
1422-
{
1423-
label: '@apply',
1461+
})
1462+
items.push({
1463+
label: '@responsive',
14241464
documentation: {
14251465
kind: 'markdown' as typeof MarkupKind.Markdown,
1426-
value: `Use \`@apply\` to inline any existing utility classes into your own custom CSS.\n\n[Tailwind CSS Documentation](${docsUrl(
1466+
value: `You can generate responsive variants of your own classes by wrapping their definitions in the \`@responsive\` directive.\n\n[Tailwind CSS Documentation](${docsUrl(
14271467
state.version,
1428-
'functions-and-directives/#apply',
1468+
'functions-and-directives/#responsive',
14291469
)})`,
14301470
},
1431-
},
1432-
...(semver.gte(state.version, '1.8.0')
1433-
? [
1434-
{
1435-
label: '@layer',
1436-
documentation: {
1437-
kind: 'markdown' as typeof MarkupKind.Markdown,
1438-
value: `Use the \`@layer\` directive to tell Tailwind which "bucket" a set of custom styles belong to. Valid layers are \`base\`, \`components\`, and \`utilities\`.\n\n[Tailwind CSS Documentation](${docsUrl(
1439-
state.version,
1440-
'functions-and-directives/#layer',
1441-
)})`,
1442-
},
1443-
},
1444-
]
1445-
: []),
1446-
...(semver.gte(state.version, '2.99.0')
1447-
? []
1448-
: [
1449-
{
1450-
label: '@variants',
1451-
documentation: {
1452-
kind: 'markdown' as typeof MarkupKind.Markdown,
1453-
value: `You can generate \`responsive\`, \`hover\`, \`focus\`, \`active\`, and other variants of your own utilities by wrapping their definitions in the \`@variants\` directive.\n\n[Tailwind CSS Documentation](${docsUrl(
1454-
state.version,
1455-
'functions-and-directives/#variants',
1456-
)})`,
1457-
},
1458-
},
1459-
{
1460-
label: '@responsive',
1461-
documentation: {
1462-
kind: 'markdown' as typeof MarkupKind.Markdown,
1463-
value: `You can generate responsive variants of your own classes by wrapping their definitions in the \`@responsive\` directive.\n\n[Tailwind CSS Documentation](${docsUrl(
1464-
state.version,
1465-
'functions-and-directives/#responsive',
1466-
)})`,
1467-
},
1468-
},
1469-
]),
1470-
...(semver.gte(state.version, '3.2.0')
1471-
? [
1472-
{
1473-
label: '@config',
1474-
documentation: {
1475-
kind: 'markdown' as typeof MarkupKind.Markdown,
1476-
value: `Use the \`@config\` directive to specify which config file Tailwind should use when compiling that CSS file.\n\n[Tailwind CSS Documentation](${docsUrl(
1477-
state.version,
1478-
'functions-and-directives/#config',
1479-
)})`,
1480-
},
1481-
},
1482-
]
1483-
: []),
1484-
...(semver.gte(state.version, '4.0.0')
1485-
? [
1486-
{
1487-
label: '@theme',
1488-
documentation: {
1489-
kind: 'markdown' as typeof MarkupKind.Markdown,
1490-
value: `Use the \`@theme\` directive to specify which config file Tailwind should use when compiling that CSS file.\n\n[Tailwind CSS Documentation](${docsUrl(
1491-
state.version,
1492-
'functions-and-directives/#config',
1493-
)})`,
1494-
},
1495-
},
1496-
]
1497-
: []),
1498-
]
1471+
})
1472+
}
1473+
1474+
if (semver.gte(state.version, '3.2.0')) {
1475+
items.push({
1476+
label: '@config',
1477+
documentation: {
1478+
kind: 'markdown' as typeof MarkupKind.Markdown,
1479+
value: `Use the \`@config\` directive to specify which config file Tailwind should use when compiling that CSS file.\n\n[Tailwind CSS Documentation](${docsUrl(
1480+
state.version,
1481+
'functions-and-directives/#config',
1482+
)})`,
1483+
},
1484+
})
1485+
}
1486+
1487+
if (semver.gte(state.version, '4.0.0')) {
1488+
items.push({
1489+
label: '@theme',
1490+
documentation: {
1491+
kind: 'markdown' as typeof MarkupKind.Markdown,
1492+
value: `Use the \`@theme\` directive to specify which config file Tailwind should use when compiling that CSS file.\n\n[Tailwind CSS Documentation](${docsUrl(
1493+
state.version,
1494+
'functions-and-directives/#config',
1495+
)})`,
1496+
},
1497+
})
1498+
}
14991499

15001500
return withDefaults(
15011501
{
@@ -1522,7 +1522,8 @@ function provideCssDirectiveCompletions(
15221522
)
15231523
}
15241524

1525-
async function provideConfigDirectiveCompletions(
1525+
// Provide completions for directives that take file paths
1526+
async function provideFileDirectiveCompletions(
15261527
state: State,
15271528
document: TextDocument,
15281529
position: Position,
@@ -1535,8 +1536,10 @@ async function provideConfigDirectiveCompletions(
15351536
return null
15361537
}
15371538

1539+
let pattern = /@config\s*(?<partial>'[^']*|"[^"]*)$/
1540+
15381541
let text = document.getText({ start: { line: position.line, character: 0 }, end: position })
1539-
let match = text.match(/@config\s*(?<partial>'[^']*|"[^"]*)$/)
1542+
let match = text.match(pattern)
15401543
if (!match) {
15411544
return null
15421545
}
@@ -1667,7 +1670,7 @@ export async function doComplete(
16671670
provideVariantsDirectiveCompletions(state, document, position) ||
16681671
provideTailwindDirectiveCompletions(state, document, position) ||
16691672
provideLayerDirectiveCompletions(state, document, position) ||
1670-
(await provideConfigDirectiveCompletions(state, document, position)) ||
1673+
(await provideFileDirectiveCompletions(state, document, position)) ||
16711674
(await provideCustomClassNameCompletions(state, document, position, context)) ||
16721675
provideThemeVariableCompletions(state, document, position, context)
16731676

packages/tailwindcss-language-service/src/documentLinksProvider.ts

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,12 +13,17 @@ export function getDocumentLinks(
1313
document: TextDocument,
1414
resolveTarget: (linkPath: string) => string,
1515
): DocumentLink[] {
16-
return getConfigDirectiveLinks(state, document, resolveTarget)
16+
let patterns = [
17+
/@config\s*(?<path>'[^']+'|"[^"]+")/g,
18+
]
19+
20+
return getDirectiveLinks(state, document, patterns, resolveTarget)
1721
}
1822

19-
function getConfigDirectiveLinks(
23+
function getDirectiveLinks(
2024
state: State,
2125
document: TextDocument,
26+
patterns: RegExp[],
2227
resolveTarget: (linkPath: string) => string,
2328
): DocumentLink[] {
2429
if (!semver.gte(state.version, '3.2.0')) {
@@ -38,7 +43,11 @@ function getConfigDirectiveLinks(
3843

3944
for (let range of ranges) {
4045
let text = getTextWithoutComments(document, 'css', range)
41-
let matches = findAll(/@config\s*(?<path>'[^']+'|"[^"]+")/g, text)
46+
let matches: RegExpMatchArray[] = []
47+
48+
for (let pattern of patterns) {
49+
matches.push(...findAll(pattern, text))
50+
}
4251

4352
for (let match of matches) {
4453
links.push({

0 commit comments

Comments
 (0)