@cioky/vike-tailwindcss 0.3.2
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 +81 -0
- package/index.d.ts +5 -0
- package/package.json +39 -0
- package/src/index.js +19 -0
- package/src/setup.js +73 -0
package/README.md
ADDED
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
# @cioky/vike-tailwindcss
|
|
2
|
+
|
|
3
|
+
> ⚠️ **HIGHLY EXPERIMENTAL** — This package is in early development. APIs may change without notice, parts may not work, and documentation may be incomplete. Use at your own risk.
|
|
4
|
+
|
|
5
|
+
[Tailwind CSS v4](https://tailwindcss.com) integration for [Ripple TS](https://ripple-ts.com) — enables `@apply` inside Ripple `<style>` blocks with full theme/utility resolution.
|
|
6
|
+
|
|
7
|
+
Part of the [vike-ripple monorepo](https://github.com/Opaius/vike-ripple).
|
|
8
|
+
|
|
9
|
+
## Quick Start
|
|
10
|
+
|
|
11
|
+
```bash
|
|
12
|
+
npx create-vike-ripple my-app --style tailwind
|
|
13
|
+
cd my-app && npm run dev
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
## Manual Install
|
|
17
|
+
|
|
18
|
+
```sh
|
|
19
|
+
npm install @cioky/vike-tailwindcss
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
### 1. Run setup
|
|
23
|
+
|
|
24
|
+
```sh
|
|
25
|
+
npx @cioky/vike-tailwindcss setup
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
### 2. Add plugin to `vite.config.ts`
|
|
29
|
+
|
|
30
|
+
```ts
|
|
31
|
+
import vikeRippleTailwindcss from '@cioky/vike-tailwindcss'
|
|
32
|
+
import tailwindcss from '@tailwindcss/vite'
|
|
33
|
+
|
|
34
|
+
export default defineConfig({
|
|
35
|
+
plugins: [
|
|
36
|
+
vikeRipple(),
|
|
37
|
+
ripple({ excludeRippleExternalModules: true }),
|
|
38
|
+
vike(),
|
|
39
|
+
vikeRippleTailwindcss(),
|
|
40
|
+
tailwindcss(),
|
|
41
|
+
],
|
|
42
|
+
})
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
### 3. Add CSS entry point
|
|
46
|
+
|
|
47
|
+
Create `src/tailwind.css`:
|
|
48
|
+
|
|
49
|
+
```css
|
|
50
|
+
@import "tailwindcss";
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
Import it in your Layout or page:
|
|
54
|
+
|
|
55
|
+
```tsx
|
|
56
|
+
import '../src/tailwind.css'
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
## Usage
|
|
60
|
+
|
|
61
|
+
```tsrx
|
|
62
|
+
<style>
|
|
63
|
+
.my-button {
|
|
64
|
+
@apply bg-blue-500 text-white font-bold py-2 px-4 rounded;
|
|
65
|
+
}
|
|
66
|
+
</style>
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
## How it works
|
|
70
|
+
|
|
71
|
+
Ripple extracts CSS from `<style>` blocks and emits it as a virtual module. This plugin patches `@ripple-ts/vite-plugin` to prepend `@import "tailwindcss" layer(reference)` to the extracted CSS, making Tailwind utilities available for `@apply` without generating duplicate CSS output.
|
|
72
|
+
|
|
73
|
+
## Known Issues
|
|
74
|
+
|
|
75
|
+
- **HMR hang**: Editing files with `@apply` during dev may occasionally cause HMR to hang.
|
|
76
|
+
- **`</style>` in template literals**: If a file contains `</style>` inside a JavaScript string, the Tailwind Oxide scanner may emit a `CssSyntaxError`. Workaround: break the literal.
|
|
77
|
+
|
|
78
|
+
## Related Packages
|
|
79
|
+
- [`@cioky/vike-core`](https://github.com/Opaius/vike-ripple/tree/main/vike-ripple) — Core Vike + Ripple integration
|
|
80
|
+
- [`vike-ripple-pandacss`](https://github.com/Opaius/vike-ripple/tree/main/vike-ripple-pandacss) — Panda CSS alternative
|
|
81
|
+
- [`create-vike-ripple`](https://github.com/Opaius/vike-ripple/tree/main/create-vike-ripple) — Project scaffold
|
package/index.d.ts
ADDED
package/package.json
ADDED
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@cioky/vike-tailwindcss",
|
|
3
|
+
"version": "0.3.2",
|
|
4
|
+
"description": "Tailwind CSS v4 integration for Ripple TS — @apply in <style> blocks, class scanning",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "./src/index.js",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": {
|
|
9
|
+
"types": "./index.d.ts",
|
|
10
|
+
"default": "./src/index.js"
|
|
11
|
+
}
|
|
12
|
+
},
|
|
13
|
+
"bin": {
|
|
14
|
+
"@cioky/vike-tailwindcss": "src/setup.js"
|
|
15
|
+
},
|
|
16
|
+
"files": [
|
|
17
|
+
"src",
|
|
18
|
+
"index.d.ts"
|
|
19
|
+
],
|
|
20
|
+
"repository": {
|
|
21
|
+
"type": "git",
|
|
22
|
+
"url": "https://github.com/Opaius/vike-ripple.git"
|
|
23
|
+
},
|
|
24
|
+
"homepage": "https://github.com/Opaius/vike-ripple",
|
|
25
|
+
"bugs": {
|
|
26
|
+
"url": "https://github.com/Opaius/vike-ripple/issues"
|
|
27
|
+
},
|
|
28
|
+
"keywords": [
|
|
29
|
+
"tailwindcss",
|
|
30
|
+
"ripple",
|
|
31
|
+
"ripplets",
|
|
32
|
+
"vike"
|
|
33
|
+
],
|
|
34
|
+
"license": "MIT",
|
|
35
|
+
"peerDependencies": {
|
|
36
|
+
"@tailwindcss/vite": ">=4.0.0",
|
|
37
|
+
"@ripple-ts/vite-plugin": ">=0.3.0"
|
|
38
|
+
}
|
|
39
|
+
}
|
package/src/index.js
ADDED
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @cioky/vike-tailwindcss — Tailwind CSS v4 integration for Ripple TS.
|
|
3
|
+
*
|
|
4
|
+
* Enables @apply in Ripple <style> blocks.
|
|
5
|
+
*
|
|
6
|
+
* ## Setup
|
|
7
|
+
* Also install @cioky/vike-core and run its setup:
|
|
8
|
+
* npx @cioky/vike-tailwindcss setup
|
|
9
|
+
*
|
|
10
|
+
* Then add the Vite plugin to vite.config.ts:
|
|
11
|
+
* import vikeRippleTailwindcss from '@cioky/vike-tailwindcss'
|
|
12
|
+
* // in plugins: vikeRippleTailwindcss(),
|
|
13
|
+
*/
|
|
14
|
+
export default function vikeRippleTailwindcss() {
|
|
15
|
+
return {
|
|
16
|
+
name: '@cioky/vike-tailwindcss',
|
|
17
|
+
enforce: 'pre'
|
|
18
|
+
};
|
|
19
|
+
}
|
package/src/setup.js
ADDED
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* @cioky/vike-tailwindcss setup — enables @apply in Ripple <style> blocks.
|
|
4
|
+
*
|
|
5
|
+
* Run once: npx @cioky/vike-tailwindcss setup
|
|
6
|
+
* Or add to project's package.json: "postinstall": "@cioky/vike-tailwindcss setup"
|
|
7
|
+
*/
|
|
8
|
+
import { createRequire } from 'module';
|
|
9
|
+
import { join } from 'path';
|
|
10
|
+
import { readFileSync, writeFileSync, existsSync } from 'fs';
|
|
11
|
+
import { fileURLToPath } from 'url';
|
|
12
|
+
|
|
13
|
+
const __dirname = fileURLToPath(new URL('.', import.meta.url));
|
|
14
|
+
const projectRoot = process.cwd();
|
|
15
|
+
let exitCode = 0;
|
|
16
|
+
|
|
17
|
+
function log(msg) {
|
|
18
|
+
console.log('[@cioky/vike-tailwindcss]', msg);
|
|
19
|
+
}
|
|
20
|
+
function warn(msg) {
|
|
21
|
+
console.warn('[@cioky/vike-tailwindcss]', msg);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
function patchRippleApply() {
|
|
25
|
+
const target = resolveModule('@ripple-ts/vite-plugin/src/index.js');
|
|
26
|
+
if (!target) {
|
|
27
|
+
warn('@ripple-ts/vite-plugin not found — skipping');
|
|
28
|
+
return;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
let src = readFileSync(target, 'utf-8');
|
|
32
|
+
if (src.includes('TW_PATCH_APPLY')) {
|
|
33
|
+
log('@apply patch already applied');
|
|
34
|
+
return;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
const orig =
|
|
38
|
+
'\t\t\t\t\tif (css) {\n' +
|
|
39
|
+
"\t\t\t\t\t\tconst cssId = createVirtualImportId(filename, root, 'style');\n" +
|
|
40
|
+
'\t\t\t\t\t\tcssCache.set(cssId, css);';
|
|
41
|
+
const patched =
|
|
42
|
+
'\t\t\t\t\tif (css) {\n' +
|
|
43
|
+
'\t\t\t\t\t\t// TW_PATCH_APPLY: bring tailwindcss into scope for @apply\n' +
|
|
44
|
+
'\t\t\t\t\t\tcss = \'@import "tailwindcss";\\n\' + css;\n' +
|
|
45
|
+
"\t\t\t\t\t\tconst cssId = createVirtualImportId(filename, root, 'style');\n" +
|
|
46
|
+
'\t\t\t\t\t\tcssCache.set(cssId, css);';
|
|
47
|
+
|
|
48
|
+
const result = src.replace(orig, patched);
|
|
49
|
+
if (result === src) {
|
|
50
|
+
warn('Could not find target in Ripple plugin');
|
|
51
|
+
exitCode = 1;
|
|
52
|
+
return;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
writeFileSync(target, result, 'utf-8');
|
|
56
|
+
log('Patched Ripple plugin for @apply support in <style> blocks');
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
function resolveModule(rel) {
|
|
60
|
+
const p = join(projectRoot, 'node_modules', rel);
|
|
61
|
+
if (existsSync(p)) return p;
|
|
62
|
+
try {
|
|
63
|
+
const r = createRequire(join(projectRoot, 'package.json'));
|
|
64
|
+
return r.resolve(rel);
|
|
65
|
+
} catch {
|
|
66
|
+
return null;
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
log('Applying @apply patch...');
|
|
71
|
+
patchRippleApply();
|
|
72
|
+
log('Done');
|
|
73
|
+
process.exit(exitCode);
|