Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions .changeset/add-css-source-map-diagnostics.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
"@lynx-js/css-serializer": patch
"@lynx-js/template-webpack-plugin": minor
---

Add CSS source map support and source-mapped template encode diagnostics.
5 changes: 5 additions & 0 deletions .changeset/enable-rspeedy-css-sourcemap.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@lynx-js/rspeedy": patch
---

Enable CSS source maps by default in Rspeedy output config.
5 changes: 5 additions & 0 deletions .changeset/legal-phones-tell.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@lynx-js/react-webpack-plugin": patch
---

Support `@lynx-js/template-webpack-plugin` v0.11.0.
5 changes: 5 additions & 0 deletions .changeset/tender-bees-lick.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@lynx-js/css-extract-webpack-plugin": patch
---

Support `@lynx-js/template-webpack-plugin` v0.11.0.
5 changes: 5 additions & 0 deletions .github/css-source-map-diagnostics.instructions.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
applyTo: "packages/{tools/css-serializer,webpack/template-webpack-plugin,rspeedy/core}/**"
---

When adding CSS diagnostics or source map plumbing across Rspeedy, css-serializer, and the template webpack plugin, preserve bundle-space `loc` data during debundle so warnings can be remapped through the main CSS source map back to original source files. Keep `cssSource` stable as `/cssId/<id>.css`, and only surface real source filenames in diagnostics when the mapped source path resolves to an existing file.
4 changes: 4 additions & 0 deletions packages/rspeedy/core/src/config/defaults.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,10 @@ export function applyDefaultRspeedyConfig(config: Config): Config {
// from the `output.filename.bundle` field.
filename: getFilename(config.output?.filename),

sourceMap: {
css: true,
},
Comment thread
luhc228 marked this conversation as resolved.

// inlineScripts defaults to false when chunk splitting is enabled, true otherwise
inlineScripts: !enableChunkSplitting,

Expand Down
7 changes: 4 additions & 3 deletions packages/rspeedy/core/src/config/output/source-map.ts
Original file line number Diff line number Diff line change
Expand Up @@ -78,18 +78,19 @@ export interface SourceMap {
*
* @remarks
*
* Defaults to `false`.
* Defaults to `true`.
*
* @example
*
* Disable CSS sourcemap.
*
* ```js
* import { defineConfig } from '@lynx-js/rspeedy'
*
* export default defineConfig({
* output: {
* sourceMap: {
* js: 'cheap-module-source-map',
* css: true,
* css: false,
* },
* },
* })
Expand Down
63 changes: 63 additions & 0 deletions packages/rspeedy/core/test/config/output/source-map.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
// Copyright 2026 The Lynx Authors. All rights reserved.
// Licensed under the Apache License Version 2.0 that can be found in the
// LICENSE file in the root directory of this source tree.
import { describe, expect, test } from 'vitest'

import { createRspeedy } from '../../../src/index.js'

describe('output.sourceMap', () => {
test('defaults css source map to true', async () => {
const rspeedy = await createRspeedy({
rspeedyConfig: {},
})

expect(rspeedy.getRspeedyConfig().output?.sourceMap).toEqual({
css: true,
})
})

test('respects output.sourceMap false', async () => {
const rspeedy = await createRspeedy({
rspeedyConfig: {
output: {
sourceMap: false,
},
},
})

expect(rspeedy.getRspeedyConfig().output?.sourceMap).toBe(false)
})

test('respects output.sourceMap.css false', async () => {
const rspeedy = await createRspeedy({
rspeedyConfig: {
output: {
sourceMap: {
css: false,
},
},
},
})

expect(rspeedy.getRspeedyConfig().output?.sourceMap).toEqual({
css: false,
})
})

test('merges css default with user js source map config', async () => {
const rspeedy = await createRspeedy({
rspeedyConfig: {
output: {
sourceMap: {
js: 'source-map',
},
},
},
})

expect(rspeedy.getRspeedyConfig().output?.sourceMap).toEqual({
css: true,
js: 'source-map',
})
})
})
54 changes: 41 additions & 13 deletions packages/rspeedy/core/test/plugins/output.plugin.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -196,6 +196,34 @@ describe('Plugins - Output', () => {
`)
})

test('output.sourceMap.css: false', async () => {
const rsbuild = await createStubRspeedy({
output: {
sourceMap: {
css: false,
},
},
})

const config = await rsbuild.unwrapConfig()

const options = getLoaderOptions(config, /css-loader/)

expect(options).toMatchInlineSnapshot(`
{
"importLoaders": 1,
"modules": {
"auto": true,
"exportGlobals": false,
"exportLocalsConvention": "camelCase",
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
}
`)
})

describe('output.cssModules', () => {
test('defaults', async () => {
const rsbuild = await createStubRspeedy({})
Expand All @@ -214,7 +242,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down Expand Up @@ -242,7 +270,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down Expand Up @@ -270,7 +298,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down Expand Up @@ -298,7 +326,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down Expand Up @@ -328,7 +356,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand All @@ -355,7 +383,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down Expand Up @@ -383,7 +411,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down Expand Up @@ -411,7 +439,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down Expand Up @@ -439,7 +467,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand All @@ -464,7 +492,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand All @@ -489,7 +517,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand All @@ -513,7 +541,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[local]-[hash:base64:6]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down Expand Up @@ -541,7 +569,7 @@ describe('Plugins - Output', () => {
"localIdentName": "[path][name]__[local]-[hash:base64:8]",
"namedExport": false,
},
"sourceMap": false,
"sourceMap": true,
}
`)
})
Expand Down
2 changes: 1 addition & 1 deletion packages/rspeedy/plugin-react/test/sourcemap.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -158,10 +158,10 @@ describe('Sourcemap', () => {
expect(sourceMapFiles).toEqual([
'.rspeedy/main/background.js.map',
'.rspeedy/main/main-thread.js.map',
'.rspeedy/main/main.css.map',
'static/js/async/lazy-bundle-comp.jsx-react__background.js.map',
'static/js/async/lazy-bundle-comp.jsx-react__main-thread.js.map',
])
expect(sourceMapFiles).not.toContain('.rspeedy/main/main.css.map')
}, 25_000)

test(
Expand Down
9 changes: 5 additions & 4 deletions packages/tools/css-serializer/src/css/ast.ts
Original file line number Diff line number Diff line change
@@ -1,14 +1,15 @@
// Copyright 2024 The Lynx Authors. All rights reserved.
// Licensed under the Apache License Version 2.0 that can be found in the
// LICENSE file in the root directory of this source tree.
import * as CSS from '../index.js';
import type { Plugin } from '../index.js';
import { parse } from '../parse.js';
import type { LynxStyleNode } from '../types/LynxStyleNode.js';
import type { ParserError, Plugin } from '../types/Plugin.js';

export function cssToAst(
content: string,
plugins: Plugin[],
): [CSS.LynxStyleNode[], CSS.ParserError[]] {
const parsedCSS = CSS.parse(content, {
): [LynxStyleNode[], ParserError[]] {
const parsedCSS = parse(content, {
plugins,
});
return [parsedCSS.root, parsedCSS.errors] as const;
Expand Down
Loading
Loading