Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(css): css.devSourcemap option #7471

Merged
merged 3 commits into from Mar 26, 2022
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
1 change: 1 addition & 0 deletions packages/playground/css-sourcemap/vite.config.js
Expand Up @@ -10,6 +10,7 @@ module.exports = {
}
},
css: {
devSourcemap: true,
preprocessorOptions: {
less: {
additionalData: '@color: red;'
Expand Down
1 change: 1 addition & 0 deletions packages/playground/vue-sourcemap/vite.config.js
Expand Up @@ -5,6 +5,7 @@ const vuePlugin = require('@vitejs/plugin-vue')
*/
module.exports = {
css: {
devSourcemap: true,
preprocessorOptions: {
less: {
additionalData: '@color: red;'
Expand Down
3 changes: 3 additions & 0 deletions packages/plugin-vue/src/index.ts
Expand Up @@ -63,6 +63,7 @@ export interface ResolvedOptions extends Options {
compiler: typeof _compiler
root: string
sourceMap: boolean
cssDevSourcemap: boolean
devServer?: ViteDevServer
devToolsEnabled?: boolean
}
Expand Down Expand Up @@ -99,6 +100,7 @@ export default function vuePlugin(rawOptions: Options = {}): Plugin {
reactivityTransform,
root: process.cwd(),
sourceMap: true,
cssDevSourcemap: false,
devToolsEnabled: process.env.NODE_ENV !== 'production'
}

Expand Down Expand Up @@ -137,6 +139,7 @@ export default function vuePlugin(rawOptions: Options = {}): Plugin {
...options,
root: config.root,
sourceMap: config.command === 'build' ? !!config.build.sourcemap : true,
cssDevSourcemap: config.css?.devSourcemap ?? false,
patak-dev marked this conversation as resolved.
Show resolved Hide resolved
isProduction: config.isProduction,
devToolsEnabled:
!!config.define!.__VUE_PROD_DEVTOOLS__ || !config.isProduction
Expand Down
18 changes: 11 additions & 7 deletions packages/plugin-vue/src/style.ts
Expand Up @@ -23,13 +23,17 @@ export async function transformStyle(
isProd: options.isProduction,
source: code,
scoped: block.scoped,
postcssOptions: {
map: {
from: filename,
inline: false,
annotation: false
}
}
...(options.cssDevSourcemap
? {
postcssOptions: {
map: {
from: filename,
inline: false,
annotation: false
}
}
}
: {})
})

if (result.errors.length) {
Expand Down
88 changes: 66 additions & 22 deletions packages/vite/src/node/plugins/css.ts
Expand Up @@ -62,6 +62,12 @@ export interface CSSOptions {
| (Postcss.ProcessOptions & {
plugins?: Postcss.Plugin[]
})
/**
* Enables css sourcemaps during dev
*
* @experimental
patak-dev marked this conversation as resolved.
Show resolved Hide resolved
*/
devSourcemap?: boolean
patak-dev marked this conversation as resolved.
Show resolved Hide resolved
}

export interface CSSModulesOptions {
Expand Down Expand Up @@ -301,9 +307,12 @@ export function cssPostPlugin(config: ResolvedConfig): Plugin {
return `export default ${JSON.stringify(css)}`
}

const sourcemap = this.getCombinedSourcemap()
await injectSourcesContent(sourcemap, cleanUrl(id), config.logger)
const cssContent = getCodeWithSourcemap('css', css, sourcemap)
let cssContent = css
if (config.css?.devSourcemap) {
const sourcemap = this.getCombinedSourcemap()
await injectSourcesContent(sourcemap, cleanUrl(id), config.logger)
cssContent = getCodeWithSourcemap('css', css, sourcemap)
}

return [
`import { updateStyle as __vite__updateStyle, removeStyle as __vite__removeStyle } from ${JSON.stringify(
Expand Down Expand Up @@ -604,7 +613,11 @@ async function compileCSS(
modules?: Record<string, string>
deps?: Set<string>
}> {
const { modules: modulesOptions, preprocessorOptions } = config.css || {}
const {
modules: modulesOptions,
preprocessorOptions,
devSourcemap
} = config.css || {}
const isModule = modulesOptions !== false && cssModuleRE.test(id)
// although at serve time it can work without processing, we do need to
// crawl them in order to register watch dependencies.
Expand Down Expand Up @@ -653,6 +666,7 @@ async function compileCSS(
}
// important: set this for relative import resolving
opts.filename = cleanUrl(id)
opts.enableSourcemap = devSourcemap ?? false
patak-dev marked this conversation as resolved.
Show resolved Hide resolved

const preprocessResult = await preProcessor(
code,
Expand Down Expand Up @@ -807,6 +821,16 @@ async function compileCSS(
}
}

if (!devSourcemap) {
return {
ast: postcssResult,
code: postcssResult.css,
map: { mappings: '' },
modules,
deps
}
}

const rawPostcssMap = postcssResult.map.toJSON()

const postcssMap = formatPostcssSourceMap(
Expand Down Expand Up @@ -1078,6 +1102,7 @@ type StylePreprocessorOptions = {
additionalData?: PreprocessorAdditionalData
filename: string
alias: Alias[]
enableSourcemap: boolean
}

type SassStylePreprocessorOptions = StylePreprocessorOptions & Sass.Options
Expand Down Expand Up @@ -1167,17 +1192,22 @@ const scss: SassStylePreprocessor = async (
const { content: data, map: additionalMap } = await getSource(
source,
options.filename,
options.additionalData
options.additionalData,
options.enableSourcemap
)
const finalOptions: Sass.Options = {
...options,
data,
file: options.filename,
outFile: options.filename,
importer,
sourceMap: true,
omitSourceMapUrl: true,
sourceMapRoot: path.dirname(options.filename)
...(options.enableSourcemap
? {
sourceMap: true,
omitSourceMapUrl: true,
sourceMapRoot: path.dirname(options.filename)
}
: {})
}

try {
Expand Down Expand Up @@ -1291,18 +1321,23 @@ const less: StylePreprocessor = async (source, root, options, resolvers) => {
const { content, map: additionalMap } = await getSource(
source,
options.filename,
options.additionalData
options.additionalData,
options.enableSourcemap
)

let result: Less.RenderOutput | undefined
try {
result = await nodeLess.render(content, {
...options,
plugins: [viteResolverPlugin, ...(options.plugins || [])],
sourceMap: {
outputSourceFiles: true,
sourceMapFileInline: false
}
...(options.enableSourcemap
? {
sourceMap: {
outputSourceFiles: true,
sourceMapFileInline: false
}
}
: {})
})
} catch (e) {
const error = e as Less.RenderError
Expand Down Expand Up @@ -1410,6 +1445,7 @@ const styl: StylePreprocessor = async (source, root, options) => {
source,
options.filename,
options.additionalData,
options.enableSourcemap,
'\n'
)
// Get preprocessor options.imports dependencies as stylus
Expand All @@ -1419,19 +1455,21 @@ const styl: StylePreprocessor = async (source, root, options) => {
)
try {
const ref = nodeStylus(content, options)
ref.set('sourcemap', {
comment: false,
inline: false,
basePath: root
})
if (options.enableSourcemap) {
ref.set('sourcemap', {
comment: false,
inline: false,
basePath: root
})
}

const result = ref.render()

// Concat imports deps with computed deps
const deps = [...ref.deps(), ...importsDeps]

// @ts-expect-error sourcemap exists
const map: ExistingRawSourceMap = ref.sourcemap
const map: ExistingRawSourceMap | undefined = ref.sourcemap

return {
code: result,
Expand All @@ -1446,9 +1484,10 @@ const styl: StylePreprocessor = async (source, root, options) => {
}

function formatStylusSourceMap(
mapBefore: ExistingRawSourceMap,
mapBefore: ExistingRawSourceMap | undefined,
root: string
): ExistingRawSourceMap {
): ExistingRawSourceMap | undefined {
if (!mapBefore) return undefined
const map = { ...mapBefore }

const resolveFromRoot = (p: string) => normalizePath(path.resolve(root, p))
Expand All @@ -1464,7 +1503,8 @@ function formatStylusSourceMap(
async function getSource(
source: string,
filename: string,
additionalData?: PreprocessorAdditionalData,
additionalData: PreprocessorAdditionalData | undefined,
enableSourcemap: boolean,
sep: string = ''
): Promise<{ content: string; map?: ExistingRawSourceMap }> {
if (!additionalData) return { content: source }
Expand All @@ -1477,6 +1517,10 @@ async function getSource(
return newContent
}

if (!enableSourcemap) {
return { content: additionalData + sep + source }
}

const ms = new MagicString(source)
ms.appendLeft(0, sep)
ms.appendLeft(0, additionalData)
Expand Down