Getting started
solid-labels targets Solid 2.0 (solid-js@2.0.0-rc.21 and @solidjs/web@2.0.0-rc.21). For Solid 1.x, use solid-labels@0.17 or older.
#Install
Add the compiler and the plugin for your bundler.
pnpm add -D solid-labels unplugin-solid-labelsnpm install -D solid-labels unplugin-solid-labelsyarn add -D solid-labels unplugin-solid-labelsTell TypeScript about the compile-time functions in any .d.ts file of your project.
/// <reference types="solid-labels" />#Vite
Register solidLabels.vite() next to @solidjs/vite-plugin. The plugin moves itself ahead of the Solid plugin, so the order in the array does not matter.
import solidPlugin from '@solidjs/vite-plugin';
import { defineConfig } from 'vite';
import solidLabels from 'unplugin-solid-labels';
export default defineConfig({
plugins: [
solidPlugin({}),
solidLabels.vite({
filter: {
include: 'src/**/*.{ts,js,tsx,jsx}',
exclude: 'node_modules/**/*.{ts,js,tsx,jsx}',
},
}),
],
});The dev option defaults to false. In a Vite dev server it follows the mode, and it adds name options to signals and memos.
#Rollup
solidLabels.rollup() has the same options. It has to run before the step that compiles Solid JSX.
import { transformAsync } from '@solidjs/compiler';
import solidLabels from 'unplugin-solid-labels';
export default {
input: 'src/main.tsx',
plugins: [
solidLabels.rollup(),
{
name: 'solid-jsx',
async transform(code, id) {
if (!/\.[jt]sx$/.test(id)) {
return null;
}
const result = await transformAsync(code, {
filename: id,
generate: 'dom',
sourceMap: true,
});
return { code: result.code, map: result.map };
},
},
],
};#Bun
Bun uses the first onLoad that returns contents for a file, so solidLabels.bun() and a separate Solid JSX plugin never chain, in either order. Put both in one unplugin factory instead. The factory runs their transform hooks in order inside a single onLoad and combines their source maps. solidLabels.bun() needs Bun 1.2.22 or later.
import { transformAsync } from '@solidjs/compiler';
import { createUnplugin } from 'unplugin';
import type { UnpluginOptions } from 'unplugin';
import solidLabels from 'unplugin-solid-labels';
const solidJsx: UnpluginOptions = {
name: 'solid-jsx',
transform: {
filter: { id: /\/src\/.*\.[jt]sx$/ },
async handler(code, id) {
const result = await transformAsync(code, { filename: id, generate: 'dom', sourceMap: true });
return { code: result.code, map: result.map };
},
},
};
const solidBun = createUnplugin((_options: undefined, meta) => [
solidLabels.raw({ filter: { include: '**/src/**/*.{ts,tsx}' } }, meta),
solidJsx,
]).bun;
await Bun.build({
entrypoints: ['./src/main.tsx'],
outdir: './dist',
sourcemap: 'external',
plugins: [solidBun()],
});Solid 2.0 has no maintained Bun plugin. @solidjs/compiler is the compiler that @solidjs/vite-plugin uses. Bun plugins such as bun-plugin-solid use babel-preset-solid 1.x, which emits Solid 1 output.
The examples/bun folder has a full build, and a check that runs the bundle.
#Your first signal
Write the variable, and read and write it like any other.
let count = $signal(0);
count += 1;
console.log(count);import { createSignal as _createSignal } from "solid-js";
let [count, setcount_1] = _createSignal(0);
setcount_1(current_1 => current_1 += 1);
console.log(count());import { createSignal as _createSignal } from "solid-js";
let [count, setcount_1] = _createSignal(0, { name: "count" });
setcount_1(current_1 => current_1 += 1);
console.log(count());Reads become count(). Writes become setcount_1(...). Open the REPL to try your own code.
#Options
Turn off single compile-time functions with disabled.
solidLabels.vite({
disabled: {
ctf: {
$signal: true,
},
},
});#Programmatic use
compile() is synchronous. It returns the code and a source map, or null when the module has nothing to compile.
import { compile } from 'solid-labels/compiler';
const output = compile('App.tsx', source, { dev: true });The compiler parses with oxc-parser and emits span edits through magic-string. The untouched parts of your code keep their formatting, and the source map is high-resolution. The REPL runs this same compiler in your browser.