@fullhuman/purgecss-from-tsx 7.0.2 → 9.0.0
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.
- package/README.md +132 -4
- package/lib/purgecss-from-tsx.esm.js +1 -0
- package/lib/purgecss-from-tsx.js +1 -0
- package/package.json +13 -11
package/README.md
CHANGED
|
@@ -1,11 +1,139 @@
|
|
|
1
|
-
#
|
|
1
|
+
# @fullhuman/purgecss-from-tsx
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
[](https://www.npmjs.com/package/@fullhuman/purgecss-from-tsx)
|
|
4
|
+
|
|
5
|
+
TSX extractor for [PurgeCSS](https://purgecss.com). This extractor parses TSX files (TypeScript + JSX) and extracts used selectors from component names, `className`, and `id` attributes.
|
|
6
|
+
|
|
7
|
+
## Installation
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
npm install @fullhuman/purgecss-from-tsx --save-dev
|
|
11
|
+
```
|
|
4
12
|
|
|
5
13
|
## Usage
|
|
6
14
|
|
|
15
|
+
### With PurgeCSS
|
|
16
|
+
|
|
17
|
+
```js
|
|
18
|
+
import { PurgeCSS } from "purgecss";
|
|
19
|
+
import purgeFromTsx from "@fullhuman/purgecss-from-tsx";
|
|
20
|
+
|
|
21
|
+
const result = await new PurgeCSS().purge({
|
|
22
|
+
content: ["**/*.tsx"],
|
|
23
|
+
css: ["**/*.css"],
|
|
24
|
+
extractors: [
|
|
25
|
+
{
|
|
26
|
+
extractor: purgeFromTsx(),
|
|
27
|
+
extensions: ["tsx"],
|
|
28
|
+
},
|
|
29
|
+
],
|
|
30
|
+
});
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
### With Custom Options
|
|
34
|
+
|
|
35
|
+
You can pass custom options for both the TypeScript compiler and the acorn parser:
|
|
36
|
+
|
|
37
|
+
```js
|
|
38
|
+
import purgeFromTsx from "@fullhuman/purgecss-from-tsx";
|
|
39
|
+
|
|
40
|
+
const extractor = purgeFromTsx({
|
|
41
|
+
// Acorn parser options
|
|
42
|
+
acornOptions: {
|
|
43
|
+
ecmaVersion: 2020,
|
|
44
|
+
sourceType: "module",
|
|
45
|
+
},
|
|
46
|
+
// TypeScript compiler options
|
|
47
|
+
tsOptions: {
|
|
48
|
+
target: ts.ScriptTarget.ES2020,
|
|
49
|
+
},
|
|
50
|
+
});
|
|
7
51
|
```
|
|
8
|
-
const purgecssFromTsx = require('purgecss-from-tsx');
|
|
9
52
|
|
|
10
|
-
|
|
53
|
+
### Standalone
|
|
54
|
+
|
|
55
|
+
You can use the extractor standalone to extract selectors from TSX content:
|
|
56
|
+
|
|
57
|
+
```js
|
|
58
|
+
import purgeFromTsx from "@fullhuman/purgecss-from-tsx";
|
|
59
|
+
|
|
60
|
+
const tsx = `
|
|
61
|
+
interface Props {
|
|
62
|
+
title: string;
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
function Card({ title }: Props): JSX.Element {
|
|
66
|
+
return (
|
|
67
|
+
<div className="card">
|
|
68
|
+
<h2 id="card-title" className="card-title">{title}</h2>
|
|
69
|
+
<Button className="btn btn-primary" />
|
|
70
|
+
</div>
|
|
71
|
+
);
|
|
72
|
+
}
|
|
73
|
+
`;
|
|
74
|
+
|
|
75
|
+
const selectors = purgeFromTsx()(tsx);
|
|
76
|
+
|
|
77
|
+
console.log(selectors);
|
|
78
|
+
// ["div", "card", "h2", "card-title", "card-title", "Button", "btn", "btn-primary"]
|
|
11
79
|
```
|
|
80
|
+
|
|
81
|
+
## API
|
|
82
|
+
|
|
83
|
+
### `purgeFromTsx(options?: Options): (content: string) => string[]`
|
|
84
|
+
|
|
85
|
+
Creates an extractor function for TSX content.
|
|
86
|
+
|
|
87
|
+
#### Parameters
|
|
88
|
+
|
|
89
|
+
- `options` (optional) - Configuration object with:
|
|
90
|
+
- `acornOptions` - [Acorn parser options](https://github.com/acornjs/acorn#interface). Defaults to `{ ecmaVersion: "latest" }`
|
|
91
|
+
- `tsOptions` - [TypeScript compiler options](https://www.typescriptlang.org/tsconfig). JSX is always preserved for parsing.
|
|
92
|
+
|
|
93
|
+
#### Returns
|
|
94
|
+
|
|
95
|
+
A function that takes TSX content as a string and returns an array of selectors.
|
|
96
|
+
|
|
97
|
+
## How It Works
|
|
98
|
+
|
|
99
|
+
This extractor works in two steps:
|
|
100
|
+
|
|
101
|
+
1. **TypeScript Transpilation** - Uses the TypeScript compiler to transpile TSX to JSX, stripping type annotations while preserving JSX syntax
|
|
102
|
+
2. **JSX Extraction** - Uses [@fullhuman/purgecss-from-jsx](https://www.npmjs.com/package/@fullhuman/purgecss-from-jsx) to extract selectors from the resulting JSX
|
|
103
|
+
|
|
104
|
+
## What It Extracts
|
|
105
|
+
|
|
106
|
+
The extractor parses TSX and extracts:
|
|
107
|
+
|
|
108
|
+
1. **Component names** - JSX element names (e.g., `div`, `Header`, `MyComponent`), including elements inside the value of another attribute (e.g., `icon={<Icon />}`)
|
|
109
|
+
2. **className values** - String values from `className` attributes, split by whitespace
|
|
110
|
+
3. **id values** - String values from `id` attributes
|
|
111
|
+
|
|
112
|
+
When `className` or `id` is an expression, its static parts are extracted the same way as by the [JSX extractor](https://github.com/FullHuman/purgecss/tree/main/packages/purgecss-from-jsx#what-it-extracts): for example, `className={active ? "on" : "off"}` gives `on` and `off`, and ``className={`card ${size}`}`` gives `card`. The TypeScript syntax is stripped first, so `className={"card" as string}` gives `card`.
|
|
113
|
+
|
|
114
|
+
### Example
|
|
115
|
+
|
|
116
|
+
```tsx
|
|
117
|
+
interface CardProps {
|
|
118
|
+
variant: "primary" | "secondary";
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
const Card: React.FC<CardProps> = ({ variant }) => (
|
|
122
|
+
<article className="card card-hover" id="featured">
|
|
123
|
+
<CardHeader className="p-4" />
|
|
124
|
+
<CardBody />
|
|
125
|
+
</article>
|
|
126
|
+
);
|
|
127
|
+
```
|
|
128
|
+
|
|
129
|
+
Extracted selectors: `["article", "card", "card-hover", "featured", "CardHeader", "p-4", "CardBody"]`
|
|
130
|
+
|
|
131
|
+
## Limitations
|
|
132
|
+
|
|
133
|
+
- Only extracts static string values from `className` and `id`
|
|
134
|
+
- Values computed at runtime, like `className={styles.container}` or the `size` of ``className={`btn-${size}`}``, are not extracted
|
|
135
|
+
- For dynamic class names, consider using PurgeCSS's [safelist](https://purgecss.com/safelisting.html) option
|
|
136
|
+
|
|
137
|
+
## License
|
|
138
|
+
|
|
139
|
+
MIT License
|
|
@@ -14,6 +14,7 @@ function purgeFromTsx(options) {
|
|
|
14
14
|
return purgeFromJsx(options === null || options === void 0 ? void 0 : options.acornOptions)(ts.transpileModule(content, {
|
|
15
15
|
compilerOptions: {
|
|
16
16
|
jsx: ts.JsxEmit.Preserve,
|
|
17
|
+
module: ts.ModuleKind.CommonJS,
|
|
17
18
|
...options === null || options === void 0 ? void 0 : options.tsOptions,
|
|
18
19
|
},
|
|
19
20
|
}).outputText);
|
package/lib/purgecss-from-tsx.js
CHANGED
|
@@ -35,6 +35,7 @@ function purgeFromTsx(options) {
|
|
|
35
35
|
return purgeFromJsx(options === null || options === void 0 ? void 0 : options.acornOptions)(ts__namespace.transpileModule(content, {
|
|
36
36
|
compilerOptions: {
|
|
37
37
|
jsx: ts__namespace.JsxEmit.Preserve,
|
|
38
|
+
module: ts__namespace.ModuleKind.CommonJS,
|
|
38
39
|
...options === null || options === void 0 ? void 0 : options.tsOptions,
|
|
39
40
|
},
|
|
40
41
|
}).outputText);
|
package/package.json
CHANGED
|
@@ -1,10 +1,13 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fullhuman/purgecss-from-tsx",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "9.0.0",
|
|
4
4
|
"description": "TSX extractor for PurgeCSS",
|
|
5
5
|
"author": "Ffloriel",
|
|
6
6
|
"homepage": "https://github.com/FullHuman/purgecss#readme",
|
|
7
|
-
"license": "
|
|
7
|
+
"license": "MIT",
|
|
8
|
+
"engines": {
|
|
9
|
+
"node": ">=22.12.0"
|
|
10
|
+
},
|
|
8
11
|
"main": "./lib/purgecss-from-tsx.js",
|
|
9
12
|
"module": "./lib/purgecss-from-tsx.esm.js",
|
|
10
13
|
"types": "./lib/purgecss-from-tsx.d.ts",
|
|
@@ -19,21 +22,20 @@
|
|
|
19
22
|
"type": "git",
|
|
20
23
|
"url": "git+https://github.com/FullHuman/purgecss.git"
|
|
21
24
|
},
|
|
22
|
-
"scripts": {
|
|
23
|
-
"build": "ts-node build.ts",
|
|
24
|
-
"test": "jest"
|
|
25
|
-
},
|
|
26
25
|
"bugs": {
|
|
27
26
|
"url": "https://github.com/FullHuman/purgecss/issues"
|
|
28
27
|
},
|
|
29
28
|
"dependencies": {
|
|
30
|
-
"@fullhuman/purgecss-from-jsx": "^
|
|
31
|
-
"acorn": "^8.
|
|
32
|
-
"typescript": "^
|
|
29
|
+
"@fullhuman/purgecss-from-jsx": "^9.0.0",
|
|
30
|
+
"acorn": "^8.19.0",
|
|
31
|
+
"typescript": "^6.0.3"
|
|
33
32
|
},
|
|
34
33
|
"publishConfig": {
|
|
35
34
|
"access": "public",
|
|
36
35
|
"registry": "https://registry.npmjs.org/"
|
|
37
36
|
},
|
|
38
|
-
"
|
|
39
|
-
|
|
37
|
+
"scripts": {
|
|
38
|
+
"build": "ts-node build.ts",
|
|
39
|
+
"test": "jest"
|
|
40
|
+
}
|
|
41
|
+
}
|