Skip to content

Commit eae36a3

Browse files
committed
feat: add cmkOptions.keyframes
1 parent 616cad4 commit eae36a3

7 files changed

Lines changed: 51 additions & 10 deletions

File tree

README.md

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -198,6 +198,23 @@ When this option is `true`, `import { button } from '...'` will be added. When t
198198
}
199199
```
200200

201+
### `cmkOptions.keyframes`
202+
203+
Type: `boolean`, Default: `true`
204+
205+
Determines whether to generate the [token](docs/glossary.md#token) of keyframes in the d.ts file.
206+
207+
```jsonc
208+
{
209+
"compilerOptions": {
210+
// ...
211+
},
212+
"cmkOptions": {
213+
"keyframes": false,
214+
},
215+
}
216+
```
217+
201218
## Supported CSS Modules features
202219

203220
- `:local(...)` and `:global(...)`

packages/codegen/src/runner.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -27,14 +27,14 @@ import type { Logger } from './logger/logger.js';
2727
/**
2828
* @throws {ReadCSSModuleFileError} When failed to read CSS Module file.
2929
*/
30-
async function parseCSSModuleByFileName(fileName: string): Promise<ParseCSSModuleResult> {
30+
async function parseCSSModuleByFileName(fileName: string, config: CMKConfig): Promise<ParseCSSModuleResult> {
3131
let text: string;
3232
try {
3333
text = await readFile(fileName, 'utf-8');
3434
} catch (error) {
3535
throw new ReadCSSModuleFileError(fileName, error);
3636
}
37-
return parseCSSModule(text, { fileName, safe: false });
37+
return parseCSSModule(text, { fileName, safe: false, keyframes: config.keyframes });
3838
}
3939

4040
/**
@@ -95,7 +95,7 @@ export async function runCMK(args: ParsedArgs, logger: Logger): Promise<void> {
9595
]);
9696
return;
9797
}
98-
const parseResults = await Promise.all(fileNames.map(async (fileName) => parseCSSModuleByFileName(fileName)));
98+
const parseResults = await Promise.all(fileNames.map(async (fileName) => parseCSSModuleByFileName(fileName, config)));
9999
for (const parseResult of parseResults) {
100100
cssModuleMap.set(parseResult.cssModule.fileName, parseResult.cssModule);
101101
syntacticDiagnostics.push(...parseResult.diagnostics);

packages/core/src/config.test.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,8 @@ describe('readTsConfigFile', () => {
3030
"dtsOutDir": "generated/cmk",
3131
"arbitraryExtensions": false,
3232
"namedExports": true,
33-
"prioritizeNamedImports": true
33+
"prioritizeNamedImports": true,
34+
"keyframes": false
3435
}
3536
}
3637
`,
@@ -44,6 +45,7 @@ describe('readTsConfigFile', () => {
4445
arbitraryExtensions: false,
4546
namedExports: true,
4647
prioritizeNamedImports: true,
48+
keyframes: false,
4749
},
4850
compilerOptions: expect.objectContaining({
4951
module: ts.ModuleKind.ESNext,

packages/core/src/config.ts

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ export interface CMKConfig {
1717
arbitraryExtensions: boolean;
1818
namedExports: boolean;
1919
prioritizeNamedImports: boolean;
20+
keyframes: boolean;
2021
/**
2122
* A root directory to resolve relative path entries in the config file to.
2223
* This is an absolute path.
@@ -72,6 +73,7 @@ interface UnnormalizedRawConfig {
7273
arbitraryExtensions?: boolean;
7374
namedExports?: boolean;
7475
prioritizeNamedImports?: boolean;
76+
keyframes?: boolean;
7577
}
7678

7779
/**
@@ -138,6 +140,16 @@ function parseRawData(raw: unknown, tsConfigSourceFile: ts.TsConfigSourceFile):
138140
});
139141
}
140142
}
143+
if ('keyframes' in raw.cmkOptions) {
144+
if (typeof raw.cmkOptions.keyframes === 'boolean') {
145+
result.config.keyframes = raw.cmkOptions.keyframes;
146+
} else {
147+
result.diagnostics.push({
148+
category: 'error',
149+
text: `\`keyframes\` in ${tsConfigSourceFile.fileName} must be a boolean.`,
150+
});
151+
}
152+
}
141153
if ('namedExports' in raw.cmkOptions) {
142154
if (typeof raw.cmkOptions.namedExports === 'boolean') {
143155
result.config.namedExports = raw.cmkOptions.namedExports;
@@ -247,14 +259,15 @@ export function readConfigFile(project: string): CMKConfig {
247259
const { configFileName, config, compilerOptions, diagnostics } = readTsConfigFile(project);
248260
const basePath = dirname(configFileName);
249261
return {
250-
// If `include` is not specified, fallback to the default include spec.
262+
// If `include` is not specified, fallback to the default include spec
251263
// ref: https://github.com/microsoft/TypeScript/blob/caf1aee269d1660b4d2a8b555c2d602c97cb28d7/src/compiler/commandLineParser.ts#L3102
252264
includes: (config.includes ?? [DEFAULT_INCLUDE_SPEC]).map((i) => join(basePath, i)),
253265
excludes: (config.excludes ?? []).map((e) => join(basePath, e)),
254266
dtsOutDir: join(basePath, config.dtsOutDir ?? 'generated'),
255267
arbitraryExtensions: config.arbitraryExtensions ?? false,
256268
namedExports: config.namedExports ?? false,
257269
prioritizeNamedImports: config.prioritizeNamedImports ?? false,
270+
keyframes: config.keyframes ?? true,
258271
basePath,
259272
configFileName,
260273
compilerOptions,

packages/core/src/parser/css-module-parser.test.ts

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import dedent from 'dedent';
22
import { describe, expect, test } from 'vitest';
33
import { parseCSSModule, type ParseCSSModuleOptions } from './css-module-parser.js';
44

5-
const options: ParseCSSModuleOptions = { fileName: '/test.module.css', safe: false };
5+
const options: ParseCSSModuleOptions = { fileName: '/test.module.css', safe: false, keyframes: true };
66

77
describe('parseCSSModule', () => {
88
test('collects local tokens', () => {
@@ -789,4 +789,8 @@ describe('parseCSSModule', () => {
789789
}
790790
`);
791791
});
792+
test('does not include the token of keyframes if keyframes is false', () => {
793+
const parsed = parseCSSModule('@keyframes slide-in {}', { ...options, keyframes: false });
794+
expect(parsed.cssModule.localTokens).toMatchInlineSnapshot(`[]`);
795+
});
792796
});

packages/core/src/parser/css-module-parser.ts

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ function isRuleNode(node: Node): node is Rule {
4040
/**
4141
* Collect tokens from the AST.
4242
*/
43-
function collectTokens(ast: Root) {
43+
function collectTokens(ast: Root, keyframes: boolean) {
4444
const allDiagnostics: DiagnosticWithDetachedLocation[] = [];
4545
const localTokens: Token[] = [];
4646
const tokenImporters: TokenImporter[] = [];
@@ -59,7 +59,7 @@ function collectTokens(ast: Root) {
5959
} else if (atValue.type === 'valueImportDeclaration') {
6060
tokenImporters.push({ ...atValue, type: 'value' });
6161
}
62-
} else if (isAtKeyframesNode(node)) {
62+
} else if (keyframes && isAtKeyframesNode(node)) {
6363
const { keyframe, diagnostics } = parseAtKeyframes(node);
6464
allDiagnostics.push(...diagnostics);
6565
if (keyframe) {
@@ -79,14 +79,18 @@ function collectTokens(ast: Root) {
7979
export interface ParseCSSModuleOptions {
8080
fileName: string;
8181
safe: boolean;
82+
keyframes: boolean;
8283
}
8384

8485
export interface ParseCSSModuleResult {
8586
cssModule: CSSModule;
8687
diagnostics: DiagnosticWithLocation[];
8788
}
8889

89-
export function parseCSSModule(text: string, { fileName, safe }: ParseCSSModuleOptions): ParseCSSModuleResult {
90+
export function parseCSSModule(
91+
text: string,
92+
{ fileName, safe, keyframes }: ParseCSSModuleOptions,
93+
): ParseCSSModuleResult {
9094
let ast: Root;
9195
const diagnosticSourceFile = { fileName, text };
9296
try {
@@ -110,7 +114,7 @@ export function parseCSSModule(text: string, { fileName, safe }: ParseCSSModuleO
110114
}
111115
throw e;
112116
}
113-
const { localTokens, tokenImporters, diagnostics } = collectTokens(ast);
117+
const { localTokens, tokenImporters, diagnostics } = collectTokens(ast, keyframes);
114118
const cssModule = {
115119
fileName,
116120
text,

packages/ts-plugin/src/language-plugin.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ export function createCSSLanguagePlugin(
5252
// The CSS in the process of being written in an editor often contains invalid syntax.
5353
// So, ts-plugin uses a fault-tolerant Parser to parse CSS.
5454
safe: true,
55+
keyframes: config.keyframes,
5556
});
5657
// eslint-disable-next-line prefer-const
5758
let { text, mapping, linkedCodeMapping } = createDts(

0 commit comments

Comments
 (0)