From b3cab28cf6d1d4b52afd3d338a58365d12e83efb Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Thu, 16 Jan 2020 23:57:45 -0700 Subject: [PATCH 01/34] Add built-in Sass support --- .../build/webpack/config/blocks/css/index.ts | 173 ++++++++++++++---- packages/next/package.json | 1 + 2 files changed, 136 insertions(+), 38 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index ef8fb5a60185a..8f050419cc704 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -132,13 +132,58 @@ export const css = curry(async function css( true ) + function getModuleStyleLoader( + cssOptions: webpack.ParserOptions, + preProcessor: string + ) { + const loaders: webpack.RuleSetUseItem[] = [ + // Resolve CSS `@import`s and `url()`s + { + loader: require.resolve('css-loader'), + options: cssOptions, + }, + + // Compile CSS + { + loader: require.resolve('postcss-loader'), + options: { + ident: '__nextjs_postcss', + plugins: postCssPlugins, + sourceMap: true, + }, + }, + ].filter(Boolean) + + // Add appropriate development mode or production mode style loader first + if (ctx.isClient) { + loaders.unshift( + getClientStyleLoader({ + isDevelopment: ctx.isDevelopment, + assetPrefix: ctx.assetPrefix, + }) + ) + } + + // Add preprocessor loader + if (preProcessor) { + loaders.push({ + loader: require.resolve(preProcessor), + options: { + sourceMap: true, + }, + }) + } + + return loaders + } + // CSS cannot be imported in _document. This comes before everything because // global CSS nor CSS modules work in said file. fns.push( loader({ oneOf: [ { - test: /\.css$/, + test: /\.(css|scss|sass)$/, // Use a loose regex so we don't have to crawl the file system to // find the real file name (if present). issuer: { test: /pages[\\/]_document\./ }, @@ -173,46 +218,62 @@ export const css = curry(async function css( exclude: /node_modules/, }, - use: ([ - // Add appropriate development more or production mode style - // loader - ctx.isClient && - getClientStyleLoader({ - isDevelopment: ctx.isDevelopment, - assetPrefix: ctx.assetPrefix, - }), - - // Resolve CSS `@import`s and `url()`s + use: getModuleStyleLoader( { - loader: require.resolve('css-loader'), - options: { - importLoaders: 1, - sourceMap: true, - onlyLocals: ctx.isServer, - modules: { - // Disallow global style exports so we can code-split CSS and - // not worry about loading order. - mode: 'pure', - // Generate a friendly production-ready name so it's - // reasonably understandable. The same name is used for - // development. - // TODO: Consider making production reduce this to a single - // character? - getLocalIdent: getCssModuleLocalIdent, - }, + importLoaders: 1, + sourceMap: true, + onlyLocals: ctx.isServer, + modules: { + // Disallow global style exports so we can code-split CSS and + // not worry about loading order. + mode: 'pure', + // Generate a friendly production-ready name so it's + // reasonably understandable. The same name is used for + // development. + // TODO: Consider making production reduce this to a single + // character? + getLocalIdent: getCssModuleLocalIdent, }, }, + 'sass-loader' + ), + }, + // Opt-in support for SASS (using .scss or .sass extensions). + // By default we support SASS Modules with the + // extensions .module.scss or .module.sass + { + // CSS Modules should never have side effects. This setting will + // allow unused CSS to be removed from the production build. + // We ensure this by disallowing `:global()` CSS at the top-level + // via the `pure` mode in `css-loader`. + sideEffects: false, + test: /\.module\.(scss|sass)$/, + // CSS Modules are only supported in the user's application. We're + // not yet allowing CSS imports _within_ `node_modules`. + issuer: { + include: [ctx.rootDirectory], + exclude: /node_modules/, + }, - // Compile CSS + use: getModuleStyleLoader( { - loader: require.resolve('postcss-loader'), - options: { - ident: '__nextjs_postcss', - plugins: postCssPlugins, - sourceMap: true, + importLoaders: 2, + sourceMap: true, + onlyLocals: ctx.isServer, + modules: { + // Disallow global style exports so we can code-split CSS and + // not worry about loading order. + mode: 'pure', + // Generate a friendly production-ready name so it's + // reasonably understandable. The same name is used for + // development. + // TODO: Consider making production reduce this to a single + // character? + getLocalIdent: getCssModuleLocalIdent, }, }, - ] as webpack.RuleSetUseItem[]).filter(Boolean), + 'sass-loader' + ), }, ], }) @@ -223,7 +284,7 @@ export const css = curry(async function css( loader({ oneOf: [ { - test: /\.module\.css$/, + test: /\.module\.(css|scss|sass)$/, use: { loader: 'error-loader', options: { @@ -238,7 +299,9 @@ export const css = curry(async function css( if (ctx.isServer) { fns.push( loader({ - oneOf: [{ test: /\.css$/, use: require.resolve('ignore-loader') }], + oneOf: [ + { test: /\.(css|scss|sass)$/, use: require.resolve('ignore-loader') }, + ], }) ) } else if (ctx.customAppFile) { @@ -254,6 +317,40 @@ export const css = curry(async function css( test: /\.css$/, issuer: { include: ctx.customAppFile }, + use: [ + // Add appropriate development more or production mode style + // loader + getClientStyleLoader({ + isDevelopment: ctx.isDevelopment, + assetPrefix: ctx.assetPrefix, + }), + + // Resolve CSS `@import`s and `url()`s + { + loader: require.resolve('css-loader'), + options: { importLoaders: 1, sourceMap: true }, + }, + + // Compile CSS + { + loader: require.resolve('postcss-loader'), + options: { + ident: '__nextjs_postcss', + plugins: postCssPlugins, + sourceMap: true, + }, + }, + ], + }, + { + // A global CSS import always has side effects. Webpack will tree + // shake the CSS without this option if the issuer claims to have + // no side-effects. + // See https://github.com/webpack/webpack/issues/6571 + sideEffects: true, + test: /\.(scss|sass)$/, + issuer: { include: ctx.customAppFile }, + use: [ // Add appropriate development more or production mode style // loader @@ -289,7 +386,7 @@ export const css = curry(async function css( loader({ oneOf: [ { - test: /\.css$/, + test: /\.(css|scss|sass)$/, issuer: { include: [/node_modules/] }, use: { loader: 'error-loader', @@ -307,7 +404,7 @@ export const css = curry(async function css( loader({ oneOf: [ { - test: /\.css$/, + test: /\.(css|scss|sass)$/, use: { loader: 'error-loader', options: { diff --git a/packages/next/package.json b/packages/next/package.json index 2ea73069d9756..f2235fdc645c3 100644 --- a/packages/next/package.json +++ b/packages/next/package.json @@ -123,6 +123,7 @@ "raw-body": "2.4.0", "react-error-overlay": "5.1.6", "react-is": "16.8.6", + "sass-loader": "8.0.2", "send": "0.17.1", "source-map": "0.6.1", "string-hash": "1.1.3", From 49f47aff5204bce374d5a37b9c62f8c88a17d7c5 Mon Sep 17 00:00:00 2001 From: Tim Neutkens Date: Sun, 19 Jan 2020 11:55:50 +0100 Subject: [PATCH 02/34] Add copy of CSS tests for SCSS --- .../3rd-party-module/pages/index.js | 5 + .../3rd-party-module/pages/index.module.scss | 17 + .../.postcssrc.json | 3 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../styles/global.scss | 14 + .../.postcssrc.json | 3 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../styles/global.scss | 14 + .../.postcssrc.json | 3 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../styles/global.scss | 14 + .../.postcssrc.json | 3 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../styles/global.scss | 14 + .../.postcssrc.json | 3 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../styles/global.scss | 14 + .../.postcssrc.json | 1 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../styles/global.scss | 14 + .../.postcssrc.json | 3 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../styles/global.scss | 14 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../postcss.config.js | 3 + .../styles/global.scss | 14 + .../pages/_app.js | 12 + .../pages/index.js | 3 + .../postcss.config.js | 3 + .../styles/global.scss | 4 + .../bad-custom-configuration/.postcssrc.json | 13 + .../bad-custom-configuration/pages/_app.js | 12 + .../bad-custom-configuration/pages/index.js | 3 + .../styles/global.scss | 4 + .../scss-fixtures/basic-module/pages/index.js | 9 + .../basic-module/pages/index.module.scss | 3 + .../compilation-and-prefixing/pages/_app.js | 12 + .../compilation-and-prefixing/pages/index.js | 3 + .../styles/global.scss | 5 + .../composes-basic/pages/index.js | 9 + .../composes-basic/pages/index.module.scss | 9 + .../composes-external/pages/index.js | 9 + .../composes-external/pages/index.module.scss | 4 + .../composes-external/pages/other.scss | 4 + .../custom-configuration-arr/.postcssrc.json | 16 + .../custom-configuration-arr/pages/_app.js | 12 + .../custom-configuration-arr/pages/index.js | 3 + .../styles/global.scss | 14 + .../next.config.js | 15 + .../custom-configuration-legacy/pages/_app.js | 12 + .../pages/index.js | 3 + .../postcss.config.js | 10 + .../styles/global.scss | 11 + .../custom-configuration/.postcssrc.json | 11 + .../custom-configuration/pages/_app.js | 12 + .../custom-configuration/pages/index.js | 3 + .../custom-configuration/styles/global.scss | 11 + .../scss-fixtures/dev-module/pages/index.js | 9 + .../dev-module/pages/index.module.scss | 3 + .../scss-fixtures/hmr-module/pages/index.js | 15 + .../hmr-module/pages/index.module.scss | 3 + .../node_modules/example/index.js | 1 + .../node_modules/example/index.mjs | 1 + .../node_modules/example/index.scss | 3 + .../node_modules/example/package.json | 4 + .../invalid-global-module/pages/index.js | 7 + .../invalid-global-with-app/pages/_app.js | 11 + .../invalid-global-with-app/pages/index.js | 5 + .../styles/global.scss | 3 + .../invalid-global/pages/index.js | 5 + .../invalid-global/styles/global.scss | 3 + .../pages/_document.js | 23 + .../invalid-module-document/pages/index.js | 3 + .../styles.module.scss | 3 + .../node_modules/example/index.js | 1 + .../node_modules/example/index.mjs | 1 + .../node_modules/example/index.module.scss | 3 + .../node_modules/example/package.json | 4 + .../invalid-module/pages/index.js | 7 + .../multi-global-reversed/pages/_app.js | 13 + .../multi-global-reversed/pages/index.js | 3 + .../multi-global-reversed/styles/global1.scss | 3 + .../multi-global-reversed/styles/global2.scss | 3 + .../scss-fixtures/multi-global/pages/_app.js | 13 + .../scss-fixtures/multi-global/pages/index.js | 3 + .../multi-global/styles/global1.scss | 3 + .../multi-global/styles/global2.scss | 3 + .../scss-fixtures/multi-module/pages/blue.js | 20 + .../multi-module/pages/blue.module.scss | 3 + .../scss-fixtures/multi-module/pages/none.js | 19 + .../scss-fixtures/multi-module/pages/red.js | 20 + .../multi-module/pages/red.module.scss | 3 + .../scss-fixtures/multi-page/pages/_app.js | 13 + .../scss-fixtures/multi-page/pages/page1.js | 14 + .../scss-fixtures/multi-page/pages/page2.js | 14 + .../multi-page/styles/global1.css | 1 + .../multi-page/styles/global1.scss | 3 + .../multi-page/styles/global2.scss | 3 + .../scss-fixtures/nested-global/pages/_app.js | 13 + .../nested-global/pages/index.js | 3 + .../nested-global/styles/global1.scss | 5 + .../nested-global/styles/global1b.scss | 4 + .../nested-global/styles/global2.scss | 5 + .../nested-global/styles/global2b.scss | 4 + test/integration/scss-fixtures/next.config.js | 10 + .../node_modules/example/index.js | 3 + .../node_modules/example/index.mjs | 1 + .../node_modules/example/index.module.scss | 6 + .../node_modules/example/other.scss | 6 + .../node_modules/example/other2.scss | 3 + .../node_modules/example/other3.scss | 3 + .../node_modules/example/package.json | 4 + .../nm-module-nested/pages/index.js | 12 + .../nm-module/node_modules/example/index.js | 3 + .../nm-module/node_modules/example/index.mjs | 1 + .../node_modules/example/index.module.scss | 3 + .../node_modules/example/package.json | 4 + .../scss-fixtures/nm-module/pages/index.js | 12 + .../npm-import-bad/pages/_app.js | 12 + .../npm-import-bad/pages/index.js | 3 + .../npm-import-bad/styles/global.scss | 1 + .../node_modules/example/index.js | 3 + .../node_modules/example/index.mjs | 1 + .../node_modules/example/other.scss | 3 + .../node_modules/example/package.json | 4 + .../node_modules/example/test.scss | 5 + .../npm-import-nested/pages/_app.js | 12 + .../npm-import-nested/pages/index.js | 3 + .../npm-import-nested/styles/global.scss | 1 + .../scss-fixtures/npm-import/pages/_app.js | 12 + .../scss-fixtures/npm-import/pages/index.js | 3 + .../npm-import/styles/global.scss | 1 + .../scss-fixtures/prod-module/pages/index.js | 9 + .../prod-module/pages/index.module.scss | 3 + .../single-global-src/src/pages/_app.js | 12 + .../single-global-src/src/pages/index.js | 3 + .../single-global-src/styles/global.scss | 3 + .../scss-fixtures/single-global/pages/_app.js | 12 + .../single-global/pages/index.js | 3 + .../single-global/styles/global.scss | 3 + .../scss-fixtures/unused/pages/index.js | 3 + .../assets/light.svg | 17 + .../url-global-asset-prefix-1/next.config.js | 5 + .../url-global-asset-prefix-1/pages/_app.js | 13 + .../url-global-asset-prefix-1/pages/index.js | 3 + .../url-global-asset-prefix-1/styles/dark.svg | 17 + .../styles/dark2.svg | 17 + .../styles/global1.scss | 4 + .../styles/global2.scss | 5 + .../styles/global2b.scss | 5 + .../assets/light.svg | 17 + .../url-global-asset-prefix-2/next.config.js | 5 + .../url-global-asset-prefix-2/pages/_app.js | 13 + .../url-global-asset-prefix-2/pages/index.js | 3 + .../url-global-asset-prefix-2/styles/dark.svg | 17 + .../styles/dark2.svg | 17 + .../styles/global1.scss | 4 + .../styles/global2.scss | 5 + .../styles/global2b.scss | 5 + .../scss-fixtures/url-global/assets/light.svg | 17 + .../scss-fixtures/url-global/pages/_app.js | 13 + .../scss-fixtures/url-global/pages/index.js | 3 + .../scss-fixtures/url-global/styles/dark.svg | 17 + .../scss-fixtures/url-global/styles/dark2.svg | 17 + .../url-global/styles/global1.scss | 4 + .../url-global/styles/global2.scss | 5 + .../url-global/styles/global2b.scss | 5 + .../valid-and-invalid-global/pages/_app.js | 12 + .../valid-and-invalid-global/pages/index.js | 5 + .../styles/global.scss | 3 + .../with-styled-jsx/pages/_app.js | 12 + .../with-styled-jsx/pages/index.js | 12 + .../with-styled-jsx/styles/global.scss | 3 + .../pages/_app.js | 5 + .../pages/index.js | 38 + .../postcss.config.js | 13 + .../styles/global.scss | 3 + .../with-tailwindcss/package.json | 7 + .../with-tailwindcss/pages/_app.js | 5 + .../with-tailwindcss/pages/index.js | 3 + .../with-tailwindcss/styles/global.scss | 3 + test/integration/scss/test/index.test.js | 815 ++++++++++++++++++ yarn.lock | 35 + 191 files changed, 2252 insertions(+) create mode 100644 test/integration/scss-fixtures/3rd-party-module/pages/index.js create mode 100644 test/integration/scss-fixtures/3rd-party-module/pages/index.module.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-1/.postcssrc.json create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-1/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-2/.postcssrc.json create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-2/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-3/.postcssrc.json create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-3/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-4/.postcssrc.json create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-4/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-5/.postcssrc.json create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-5/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-6/.postcssrc.json create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-6/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-7/.postcssrc.json create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-7/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-8/postcss.config.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-8/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-func/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-func/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-func/postcss.config.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration-func/styles/global.scss create mode 100644 test/integration/scss-fixtures/bad-custom-configuration/.postcssrc.json create mode 100644 test/integration/scss-fixtures/bad-custom-configuration/pages/_app.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration/pages/index.js create mode 100644 test/integration/scss-fixtures/bad-custom-configuration/styles/global.scss create mode 100644 test/integration/scss-fixtures/basic-module/pages/index.js create mode 100644 test/integration/scss-fixtures/basic-module/pages/index.module.scss create mode 100644 test/integration/scss-fixtures/compilation-and-prefixing/pages/_app.js create mode 100644 test/integration/scss-fixtures/compilation-and-prefixing/pages/index.js create mode 100644 test/integration/scss-fixtures/compilation-and-prefixing/styles/global.scss create mode 100644 test/integration/scss-fixtures/composes-basic/pages/index.js create mode 100644 test/integration/scss-fixtures/composes-basic/pages/index.module.scss create mode 100644 test/integration/scss-fixtures/composes-external/pages/index.js create mode 100644 test/integration/scss-fixtures/composes-external/pages/index.module.scss create mode 100644 test/integration/scss-fixtures/composes-external/pages/other.scss create mode 100644 test/integration/scss-fixtures/custom-configuration-arr/.postcssrc.json create mode 100644 test/integration/scss-fixtures/custom-configuration-arr/pages/_app.js create mode 100644 test/integration/scss-fixtures/custom-configuration-arr/pages/index.js create mode 100644 test/integration/scss-fixtures/custom-configuration-arr/styles/global.scss create mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/next.config.js create mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/pages/_app.js create mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/pages/index.js create mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/postcss.config.js create mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/styles/global.scss create mode 100644 test/integration/scss-fixtures/custom-configuration/.postcssrc.json create mode 100644 test/integration/scss-fixtures/custom-configuration/pages/_app.js create mode 100644 test/integration/scss-fixtures/custom-configuration/pages/index.js create mode 100644 test/integration/scss-fixtures/custom-configuration/styles/global.scss create mode 100644 test/integration/scss-fixtures/dev-module/pages/index.js create mode 100644 test/integration/scss-fixtures/dev-module/pages/index.module.scss create mode 100644 test/integration/scss-fixtures/hmr-module/pages/index.js create mode 100644 test/integration/scss-fixtures/hmr-module/pages/index.module.scss create mode 100644 test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.js create mode 100644 test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.mjs create mode 100644 test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.scss create mode 100644 test/integration/scss-fixtures/invalid-global-module/node_modules/example/package.json create mode 100644 test/integration/scss-fixtures/invalid-global-module/pages/index.js create mode 100644 test/integration/scss-fixtures/invalid-global-with-app/pages/_app.js create mode 100644 test/integration/scss-fixtures/invalid-global-with-app/pages/index.js create mode 100644 test/integration/scss-fixtures/invalid-global-with-app/styles/global.scss create mode 100644 test/integration/scss-fixtures/invalid-global/pages/index.js create mode 100644 test/integration/scss-fixtures/invalid-global/styles/global.scss create mode 100644 test/integration/scss-fixtures/invalid-module-document/pages/_document.js create mode 100644 test/integration/scss-fixtures/invalid-module-document/pages/index.js create mode 100644 test/integration/scss-fixtures/invalid-module-document/styles.module.scss create mode 100644 test/integration/scss-fixtures/invalid-module/node_modules/example/index.js create mode 100644 test/integration/scss-fixtures/invalid-module/node_modules/example/index.mjs create mode 100644 test/integration/scss-fixtures/invalid-module/node_modules/example/index.module.scss create mode 100644 test/integration/scss-fixtures/invalid-module/node_modules/example/package.json create mode 100644 test/integration/scss-fixtures/invalid-module/pages/index.js create mode 100644 test/integration/scss-fixtures/multi-global-reversed/pages/_app.js create mode 100644 test/integration/scss-fixtures/multi-global-reversed/pages/index.js create mode 100644 test/integration/scss-fixtures/multi-global-reversed/styles/global1.scss create mode 100644 test/integration/scss-fixtures/multi-global-reversed/styles/global2.scss create mode 100644 test/integration/scss-fixtures/multi-global/pages/_app.js create mode 100644 test/integration/scss-fixtures/multi-global/pages/index.js create mode 100644 test/integration/scss-fixtures/multi-global/styles/global1.scss create mode 100644 test/integration/scss-fixtures/multi-global/styles/global2.scss create mode 100644 test/integration/scss-fixtures/multi-module/pages/blue.js create mode 100644 test/integration/scss-fixtures/multi-module/pages/blue.module.scss create mode 100644 test/integration/scss-fixtures/multi-module/pages/none.js create mode 100644 test/integration/scss-fixtures/multi-module/pages/red.js create mode 100644 test/integration/scss-fixtures/multi-module/pages/red.module.scss create mode 100644 test/integration/scss-fixtures/multi-page/pages/_app.js create mode 100644 test/integration/scss-fixtures/multi-page/pages/page1.js create mode 100644 test/integration/scss-fixtures/multi-page/pages/page2.js create mode 100644 test/integration/scss-fixtures/multi-page/styles/global1.css create mode 100644 test/integration/scss-fixtures/multi-page/styles/global1.scss create mode 100644 test/integration/scss-fixtures/multi-page/styles/global2.scss create mode 100644 test/integration/scss-fixtures/nested-global/pages/_app.js create mode 100644 test/integration/scss-fixtures/nested-global/pages/index.js create mode 100644 test/integration/scss-fixtures/nested-global/styles/global1.scss create mode 100644 test/integration/scss-fixtures/nested-global/styles/global1b.scss create mode 100644 test/integration/scss-fixtures/nested-global/styles/global2.scss create mode 100644 test/integration/scss-fixtures/nested-global/styles/global2b.scss create mode 100644 test/integration/scss-fixtures/next.config.js create mode 100644 test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.js create mode 100644 test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.mjs create mode 100644 test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss create mode 100644 test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss create mode 100644 test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss create mode 100644 test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss create mode 100644 test/integration/scss-fixtures/nm-module-nested/node_modules/example/package.json create mode 100644 test/integration/scss-fixtures/nm-module-nested/pages/index.js create mode 100644 test/integration/scss-fixtures/nm-module/node_modules/example/index.js create mode 100644 test/integration/scss-fixtures/nm-module/node_modules/example/index.mjs create mode 100644 test/integration/scss-fixtures/nm-module/node_modules/example/index.module.scss create mode 100644 test/integration/scss-fixtures/nm-module/node_modules/example/package.json create mode 100644 test/integration/scss-fixtures/nm-module/pages/index.js create mode 100644 test/integration/scss-fixtures/npm-import-bad/pages/_app.js create mode 100644 test/integration/scss-fixtures/npm-import-bad/pages/index.js create mode 100644 test/integration/scss-fixtures/npm-import-bad/styles/global.scss create mode 100644 test/integration/scss-fixtures/npm-import-nested/node_modules/example/index.js create mode 100644 test/integration/scss-fixtures/npm-import-nested/node_modules/example/index.mjs create mode 100644 test/integration/scss-fixtures/npm-import-nested/node_modules/example/other.scss create mode 100644 test/integration/scss-fixtures/npm-import-nested/node_modules/example/package.json create mode 100644 test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss create mode 100644 test/integration/scss-fixtures/npm-import-nested/pages/_app.js create mode 100644 test/integration/scss-fixtures/npm-import-nested/pages/index.js create mode 100644 test/integration/scss-fixtures/npm-import-nested/styles/global.scss create mode 100644 test/integration/scss-fixtures/npm-import/pages/_app.js create mode 100644 test/integration/scss-fixtures/npm-import/pages/index.js create mode 100644 test/integration/scss-fixtures/npm-import/styles/global.scss create mode 100644 test/integration/scss-fixtures/prod-module/pages/index.js create mode 100644 test/integration/scss-fixtures/prod-module/pages/index.module.scss create mode 100644 test/integration/scss-fixtures/single-global-src/src/pages/_app.js create mode 100644 test/integration/scss-fixtures/single-global-src/src/pages/index.js create mode 100644 test/integration/scss-fixtures/single-global-src/styles/global.scss create mode 100644 test/integration/scss-fixtures/single-global/pages/_app.js create mode 100644 test/integration/scss-fixtures/single-global/pages/index.js create mode 100644 test/integration/scss-fixtures/single-global/styles/global.scss create mode 100644 test/integration/scss-fixtures/unused/pages/index.js create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/assets/light.svg create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/next.config.js create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/pages/_app.js create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/pages/index.js create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/styles/dark.svg create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/styles/dark2.svg create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global1.scss create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2.scss create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2b.scss create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/assets/light.svg create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/next.config.js create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/pages/_app.js create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/pages/index.js create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/styles/dark.svg create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/styles/dark2.svg create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global1.scss create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2.scss create mode 100644 test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2b.scss create mode 100644 test/integration/scss-fixtures/url-global/assets/light.svg create mode 100644 test/integration/scss-fixtures/url-global/pages/_app.js create mode 100644 test/integration/scss-fixtures/url-global/pages/index.js create mode 100644 test/integration/scss-fixtures/url-global/styles/dark.svg create mode 100644 test/integration/scss-fixtures/url-global/styles/dark2.svg create mode 100644 test/integration/scss-fixtures/url-global/styles/global1.scss create mode 100644 test/integration/scss-fixtures/url-global/styles/global2.scss create mode 100644 test/integration/scss-fixtures/url-global/styles/global2b.scss create mode 100644 test/integration/scss-fixtures/valid-and-invalid-global/pages/_app.js create mode 100644 test/integration/scss-fixtures/valid-and-invalid-global/pages/index.js create mode 100644 test/integration/scss-fixtures/valid-and-invalid-global/styles/global.scss create mode 100644 test/integration/scss-fixtures/with-styled-jsx/pages/_app.js create mode 100644 test/integration/scss-fixtures/with-styled-jsx/pages/index.js create mode 100644 test/integration/scss-fixtures/with-styled-jsx/styles/global.scss create mode 100644 test/integration/scss-fixtures/with-tailwindcss-and-purgecss/pages/_app.js create mode 100644 test/integration/scss-fixtures/with-tailwindcss-and-purgecss/pages/index.js create mode 100644 test/integration/scss-fixtures/with-tailwindcss-and-purgecss/postcss.config.js create mode 100644 test/integration/scss-fixtures/with-tailwindcss-and-purgecss/styles/global.scss create mode 100644 test/integration/scss-fixtures/with-tailwindcss/package.json create mode 100644 test/integration/scss-fixtures/with-tailwindcss/pages/_app.js create mode 100644 test/integration/scss-fixtures/with-tailwindcss/pages/index.js create mode 100644 test/integration/scss-fixtures/with-tailwindcss/styles/global.scss create mode 100644 test/integration/scss/test/index.test.js diff --git a/test/integration/scss-fixtures/3rd-party-module/pages/index.js b/test/integration/scss-fixtures/3rd-party-module/pages/index.js new file mode 100644 index 0000000000000..57f5707a4c221 --- /dev/null +++ b/test/integration/scss-fixtures/3rd-party-module/pages/index.js @@ -0,0 +1,5 @@ +import { foo } from './index.module.scss' + +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/3rd-party-module/pages/index.module.scss b/test/integration/scss-fixtures/3rd-party-module/pages/index.module.scss new file mode 100644 index 0000000000000..99d63206009a1 --- /dev/null +++ b/test/integration/scss-fixtures/3rd-party-module/pages/index.module.scss @@ -0,0 +1,17 @@ +.foo { + position: relative; +} + +.foo :global(.bar), +.foo :global(.baz) { + height: 100%; + overflow: hidden; +} + +.foo :global(.lol) { + width: 80%; +} + +.foo > :global(.lel) { + width: 80%; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/.postcssrc.json new file mode 100644 index 0000000000000..ab27508fd95ca --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/.postcssrc.json @@ -0,0 +1,3 @@ +{ + "plugins": [["postcss-trolling"]] +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/.postcssrc.json new file mode 100644 index 0000000000000..c6df57bdda0fa --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/.postcssrc.json @@ -0,0 +1,3 @@ +{ + "plugins": [["postcss-trolling", null]] +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/.postcssrc.json new file mode 100644 index 0000000000000..e886576085efd --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/.postcssrc.json @@ -0,0 +1,3 @@ +{ + "plugins": [[5, null]] +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/.postcssrc.json new file mode 100644 index 0000000000000..05e159725dc23 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/.postcssrc.json @@ -0,0 +1,3 @@ +{ + "plugins": [5] +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/.postcssrc.json new file mode 100644 index 0000000000000..1e02e994a48d5 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/.postcssrc.json @@ -0,0 +1,3 @@ +{ + "plugins": null +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/.postcssrc.json new file mode 100644 index 0000000000000..0967ef424bce6 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/.postcssrc.json @@ -0,0 +1 @@ +{} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/.postcssrc.json new file mode 100644 index 0000000000000..561d0cb76ddf9 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/.postcssrc.json @@ -0,0 +1,3 @@ +{ + "plugins": [["postcss-trolling", 5]] +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/postcss.config.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/postcss.config.js new file mode 100644 index 0000000000000..5f1f2140125eb --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/postcss.config.js @@ -0,0 +1,3 @@ +module.exports = { + plugins: [require('postcss-trolling')], +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-func/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-func/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-func/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-func/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-func/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-func/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-func/postcss.config.js b/test/integration/scss-fixtures/bad-custom-configuration-func/postcss.config.js new file mode 100644 index 0000000000000..9bf5d079edf9b --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-func/postcss.config.js @@ -0,0 +1,3 @@ +module.exports = function() { + return { plugins: [] } +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-func/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-func/styles/global.scss new file mode 100644 index 0000000000000..e535e1983057d --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration-func/styles/global.scss @@ -0,0 +1,4 @@ +/* this should be transformed to width/height */ +.video { + max-size: 400px 300px; +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration/.postcssrc.json new file mode 100644 index 0000000000000..8c058dc78d1e0 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration/.postcssrc.json @@ -0,0 +1,13 @@ +{ + "sourceMap": false, + "plugins": { + "postcss-modules-extract-imports": {}, + "postcss-modules-local-by-default": {}, + "postcss-modules-scope": {}, + "postcss-modules-values": {}, + "postcss-modules": {}, + + // Test a non-standard feature that wouldn't be normally enabled + "postcss-short-size": {} + } +} diff --git a/test/integration/scss-fixtures/bad-custom-configuration/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/bad-custom-configuration/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration/styles/global.scss new file mode 100644 index 0000000000000..e535e1983057d --- /dev/null +++ b/test/integration/scss-fixtures/bad-custom-configuration/styles/global.scss @@ -0,0 +1,4 @@ +/* this should be transformed to width/height */ +.video { + max-size: 400px 300px; +} diff --git a/test/integration/scss-fixtures/basic-module/pages/index.js b/test/integration/scss-fixtures/basic-module/pages/index.js new file mode 100644 index 0000000000000..7b42859a67e32 --- /dev/null +++ b/test/integration/scss-fixtures/basic-module/pages/index.js @@ -0,0 +1,9 @@ +import { redText } from './index.module.scss' + +export default function Home() { + return ( +
+ This text should be red. +
+ ) +} diff --git a/test/integration/scss-fixtures/basic-module/pages/index.module.scss b/test/integration/scss-fixtures/basic-module/pages/index.module.scss new file mode 100644 index 0000000000000..08a38e09ef8ea --- /dev/null +++ b/test/integration/scss-fixtures/basic-module/pages/index.module.scss @@ -0,0 +1,3 @@ +.redText { + color: red; +} diff --git a/test/integration/scss-fixtures/compilation-and-prefixing/pages/_app.js b/test/integration/scss-fixtures/compilation-and-prefixing/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/compilation-and-prefixing/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/compilation-and-prefixing/pages/index.js b/test/integration/scss-fixtures/compilation-and-prefixing/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/compilation-and-prefixing/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/compilation-and-prefixing/styles/global.scss b/test/integration/scss-fixtures/compilation-and-prefixing/styles/global.scss new file mode 100644 index 0000000000000..19e8290b4cd41 --- /dev/null +++ b/test/integration/scss-fixtures/compilation-and-prefixing/styles/global.scss @@ -0,0 +1,5 @@ +@media (480px <= width < 768px) { + ::placeholder { + color: green; + } +} diff --git a/test/integration/scss-fixtures/composes-basic/pages/index.js b/test/integration/scss-fixtures/composes-basic/pages/index.js new file mode 100644 index 0000000000000..0af8621c4649a --- /dev/null +++ b/test/integration/scss-fixtures/composes-basic/pages/index.js @@ -0,0 +1,9 @@ +import { subClass } from './index.module.scss' + +export default function Home() { + return ( +
+ This text should be yellow on blue. +
+ ) +} diff --git a/test/integration/scss-fixtures/composes-basic/pages/index.module.scss b/test/integration/scss-fixtures/composes-basic/pages/index.module.scss new file mode 100644 index 0000000000000..0999b553172d8 --- /dev/null +++ b/test/integration/scss-fixtures/composes-basic/pages/index.module.scss @@ -0,0 +1,9 @@ +.className { + background: red; + color: yellow; +} + +.subClass { + composes: className; + background: blue; +} diff --git a/test/integration/scss-fixtures/composes-external/pages/index.js b/test/integration/scss-fixtures/composes-external/pages/index.js new file mode 100644 index 0000000000000..0af8621c4649a --- /dev/null +++ b/test/integration/scss-fixtures/composes-external/pages/index.js @@ -0,0 +1,9 @@ +import { subClass } from './index.module.scss' + +export default function Home() { + return ( +
+ This text should be yellow on blue. +
+ ) +} diff --git a/test/integration/scss-fixtures/composes-external/pages/index.module.scss b/test/integration/scss-fixtures/composes-external/pages/index.module.scss new file mode 100644 index 0000000000000..373385ec2f693 --- /dev/null +++ b/test/integration/scss-fixtures/composes-external/pages/index.module.scss @@ -0,0 +1,4 @@ +.subClass { + composes: className from './other.scss'; + background: blue; +} diff --git a/test/integration/scss-fixtures/composes-external/pages/other.scss b/test/integration/scss-fixtures/composes-external/pages/other.scss new file mode 100644 index 0000000000000..6c6bc72eae403 --- /dev/null +++ b/test/integration/scss-fixtures/composes-external/pages/other.scss @@ -0,0 +1,4 @@ +.className { + background: red; + color: yellow; +} diff --git a/test/integration/scss-fixtures/custom-configuration-arr/.postcssrc.json b/test/integration/scss-fixtures/custom-configuration-arr/.postcssrc.json new file mode 100644 index 0000000000000..def6136b4cdc8 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-arr/.postcssrc.json @@ -0,0 +1,16 @@ +{ + // Use comments to test JSON5 support + "plugins": [ + "pixrem", + ["postcss-pseudoelements", true], + // Test a non-standard feature that wouldn't be normally enabled + [ + "postcss-short-size", + { + // Add a prefix to test that configuration is passed + "prefix": "xyz" + } + ], + ["postcss-trolling", false] + ] +} diff --git a/test/integration/scss-fixtures/custom-configuration-arr/pages/_app.js b/test/integration/scss-fixtures/custom-configuration-arr/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-arr/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/custom-configuration-arr/pages/index.js b/test/integration/scss-fixtures/custom-configuration-arr/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-arr/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/custom-configuration-arr/styles/global.scss b/test/integration/scss-fixtures/custom-configuration-arr/styles/global.scss new file mode 100644 index 0000000000000..78d27f7edd8e4 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-arr/styles/global.scss @@ -0,0 +1,14 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + a::before { + content: ''; + } + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400rem 300rem; +} diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/next.config.js b/test/integration/scss-fixtures/custom-configuration-legacy/next.config.js new file mode 100644 index 0000000000000..93bc6a48f6b17 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-legacy/next.config.js @@ -0,0 +1,15 @@ +const withCSS = require('@zeit/next-css') + +module.exports = withCSS({ + onDemandEntries: { + // Make sure entries are not getting disposed. + maxInactiveAge: 1000 * 60 * 60, + }, + experimental: { + css: true, + }, + webpack(cfg) { + cfg.devtool = 'source-map' + return cfg + }, +}) diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/pages/_app.js b/test/integration/scss-fixtures/custom-configuration-legacy/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-legacy/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/pages/index.js b/test/integration/scss-fixtures/custom-configuration-legacy/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-legacy/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/postcss.config.js b/test/integration/scss-fixtures/custom-configuration-legacy/postcss.config.js new file mode 100644 index 0000000000000..c7b7fde03c78c --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-legacy/postcss.config.js @@ -0,0 +1,10 @@ +module.exports = { + // Use comments to test JSON5 support + plugins: [ + // Test a non-standard feature that wouldn't be normally enabled + require('postcss-short-size')({ + // Add a prefix to test that configuration is passed + prefix: 'xyz', + }), + ], +} diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/styles/global.scss b/test/integration/scss-fixtures/custom-configuration-legacy/styles/global.scss new file mode 100644 index 0000000000000..f942036ad16ef --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration-legacy/styles/global.scss @@ -0,0 +1,11 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400px 300px; +} diff --git a/test/integration/scss-fixtures/custom-configuration/.postcssrc.json b/test/integration/scss-fixtures/custom-configuration/.postcssrc.json new file mode 100644 index 0000000000000..21cd2f23012bd --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration/.postcssrc.json @@ -0,0 +1,11 @@ +{ + // Use comments to test JSON5 support + "plugins": { + // Test a non-standard feature that wouldn't be normally enabled + "postcss-short-size": { + // Add a prefix to test that configuration is passed + "prefix": "xyz" + }, + "postcss-trolling": false + } +} diff --git a/test/integration/scss-fixtures/custom-configuration/pages/_app.js b/test/integration/scss-fixtures/custom-configuration/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/custom-configuration/pages/index.js b/test/integration/scss-fixtures/custom-configuration/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/custom-configuration/styles/global.scss b/test/integration/scss-fixtures/custom-configuration/styles/global.scss new file mode 100644 index 0000000000000..f942036ad16ef --- /dev/null +++ b/test/integration/scss-fixtures/custom-configuration/styles/global.scss @@ -0,0 +1,11 @@ +/* this should pass through untransformed */ +@media (480px <= width < 768px) { + ::placeholder { + color: green; + } +} + +/* this should be transformed to width/height */ +.video { + -xyz-max-size: 400px 300px; +} diff --git a/test/integration/scss-fixtures/dev-module/pages/index.js b/test/integration/scss-fixtures/dev-module/pages/index.js new file mode 100644 index 0000000000000..7b42859a67e32 --- /dev/null +++ b/test/integration/scss-fixtures/dev-module/pages/index.js @@ -0,0 +1,9 @@ +import { redText } from './index.module.scss' + +export default function Home() { + return ( +
+ This text should be red. +
+ ) +} diff --git a/test/integration/scss-fixtures/dev-module/pages/index.module.scss b/test/integration/scss-fixtures/dev-module/pages/index.module.scss new file mode 100644 index 0000000000000..08a38e09ef8ea --- /dev/null +++ b/test/integration/scss-fixtures/dev-module/pages/index.module.scss @@ -0,0 +1,3 @@ +.redText { + color: red; +} diff --git a/test/integration/scss-fixtures/hmr-module/pages/index.js b/test/integration/scss-fixtures/hmr-module/pages/index.js new file mode 100644 index 0000000000000..18a31282f756c --- /dev/null +++ b/test/integration/scss-fixtures/hmr-module/pages/index.js @@ -0,0 +1,15 @@ +import { redText } from './index.module.scss' + +function Home() { + return ( + <> +
+ This text should be red. +
+
+ + + ) +} + +export default Home diff --git a/test/integration/scss-fixtures/hmr-module/pages/index.module.scss b/test/integration/scss-fixtures/hmr-module/pages/index.module.scss new file mode 100644 index 0000000000000..08a38e09ef8ea --- /dev/null +++ b/test/integration/scss-fixtures/hmr-module/pages/index.module.scss @@ -0,0 +1,3 @@ +.redText { + color: red; +} diff --git a/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.js b/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.js new file mode 100644 index 0000000000000..4a5b22813be5a --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.js @@ -0,0 +1 @@ +require('./index.scss') diff --git a/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.mjs b/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.mjs new file mode 100644 index 0000000000000..63810a6819f33 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.mjs @@ -0,0 +1 @@ +import './index.scss' diff --git a/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.scss b/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.scss new file mode 100644 index 0000000000000..f77fe0ef0bdbe --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global-module/node_modules/example/index.scss @@ -0,0 +1,3 @@ +.redText { + color: 'red'; +} diff --git a/test/integration/scss-fixtures/invalid-global-module/node_modules/example/package.json b/test/integration/scss-fixtures/invalid-global-module/node_modules/example/package.json new file mode 100644 index 0000000000000..ab5f2cd4a1cf7 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global-module/node_modules/example/package.json @@ -0,0 +1,4 @@ +{ + "name": "example", + "main": "index" +} diff --git a/test/integration/scss-fixtures/invalid-global-module/pages/index.js b/test/integration/scss-fixtures/invalid-global-module/pages/index.js new file mode 100644 index 0000000000000..9a79166027dd7 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global-module/pages/index.js @@ -0,0 +1,7 @@ +import 'example' + +function Home() { + return
This should fail at build time.
+} + +export default Home diff --git a/test/integration/scss-fixtures/invalid-global-with-app/pages/_app.js b/test/integration/scss-fixtures/invalid-global-with-app/pages/_app.js new file mode 100644 index 0000000000000..68b8ee24d7fd5 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global-with-app/pages/_app.js @@ -0,0 +1,11 @@ +import React from 'react' +import App from 'next/app' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/invalid-global-with-app/pages/index.js b/test/integration/scss-fixtures/invalid-global-with-app/pages/index.js new file mode 100644 index 0000000000000..38d46eb2a45eb --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global-with-app/pages/index.js @@ -0,0 +1,5 @@ +import '../styles/global.scss' + +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/invalid-global-with-app/styles/global.scss b/test/integration/scss-fixtures/invalid-global-with-app/styles/global.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global-with-app/styles/global.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/invalid-global/pages/index.js b/test/integration/scss-fixtures/invalid-global/pages/index.js new file mode 100644 index 0000000000000..38d46eb2a45eb --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global/pages/index.js @@ -0,0 +1,5 @@ +import '../styles/global.scss' + +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/invalid-global/styles/global.scss b/test/integration/scss-fixtures/invalid-global/styles/global.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-global/styles/global.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/invalid-module-document/pages/_document.js b/test/integration/scss-fixtures/invalid-module-document/pages/_document.js new file mode 100644 index 0000000000000..a14aca67a844d --- /dev/null +++ b/test/integration/scss-fixtures/invalid-module-document/pages/_document.js @@ -0,0 +1,23 @@ +import Document, { Head, Html, Main, NextScript } from 'next/document' +import styles from '../styles.module.scss' + +class MyDocument extends Document { + static async getInitialProps(ctx) { + const initialProps = await Document.getInitialProps(ctx) + return { ...initialProps } + } + + render() { + return ( + + + +
+ + + + ) + } +} + +export default MyDocument diff --git a/test/integration/scss-fixtures/invalid-module-document/pages/index.js b/test/integration/scss-fixtures/invalid-module-document/pages/index.js new file mode 100644 index 0000000000000..08fe48e9b56c8 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-module-document/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
Hello
+} diff --git a/test/integration/scss-fixtures/invalid-module-document/styles.module.scss b/test/integration/scss-fixtures/invalid-module-document/styles.module.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-module-document/styles.module.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/invalid-module/node_modules/example/index.js b/test/integration/scss-fixtures/invalid-module/node_modules/example/index.js new file mode 100644 index 0000000000000..a8023d4c7c1bf --- /dev/null +++ b/test/integration/scss-fixtures/invalid-module/node_modules/example/index.js @@ -0,0 +1 @@ +module.exports = require('./index.module.scss') diff --git a/test/integration/scss-fixtures/invalid-module/node_modules/example/index.mjs b/test/integration/scss-fixtures/invalid-module/node_modules/example/index.mjs new file mode 100644 index 0000000000000..f72c6d4acfbe2 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-module/node_modules/example/index.mjs @@ -0,0 +1 @@ +export * from './index.module.scss' diff --git a/test/integration/scss-fixtures/invalid-module/node_modules/example/index.module.scss b/test/integration/scss-fixtures/invalid-module/node_modules/example/index.module.scss new file mode 100644 index 0000000000000..f77fe0ef0bdbe --- /dev/null +++ b/test/integration/scss-fixtures/invalid-module/node_modules/example/index.module.scss @@ -0,0 +1,3 @@ +.redText { + color: 'red'; +} diff --git a/test/integration/scss-fixtures/invalid-module/node_modules/example/package.json b/test/integration/scss-fixtures/invalid-module/node_modules/example/package.json new file mode 100644 index 0000000000000..ab5f2cd4a1cf7 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-module/node_modules/example/package.json @@ -0,0 +1,4 @@ +{ + "name": "example", + "main": "index" +} diff --git a/test/integration/scss-fixtures/invalid-module/pages/index.js b/test/integration/scss-fixtures/invalid-module/pages/index.js new file mode 100644 index 0000000000000..83fa4e1381b64 --- /dev/null +++ b/test/integration/scss-fixtures/invalid-module/pages/index.js @@ -0,0 +1,7 @@ +import * as classes from 'example' + +function Home() { + return
This should fail at build time {JSON.stringify(classes)}.
+} + +export default Home diff --git a/test/integration/scss-fixtures/multi-global-reversed/pages/_app.js b/test/integration/scss-fixtures/multi-global-reversed/pages/_app.js new file mode 100644 index 0000000000000..dc344a9bd9d27 --- /dev/null +++ b/test/integration/scss-fixtures/multi-global-reversed/pages/_app.js @@ -0,0 +1,13 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global2.scss' +import '../styles/global1.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/multi-global-reversed/pages/index.js b/test/integration/scss-fixtures/multi-global-reversed/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/multi-global-reversed/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/multi-global-reversed/styles/global1.scss b/test/integration/scss-fixtures/multi-global-reversed/styles/global1.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/multi-global-reversed/styles/global1.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/multi-global-reversed/styles/global2.scss b/test/integration/scss-fixtures/multi-global-reversed/styles/global2.scss new file mode 100644 index 0000000000000..9d1af6c0f6db1 --- /dev/null +++ b/test/integration/scss-fixtures/multi-global-reversed/styles/global2.scss @@ -0,0 +1,3 @@ +.blue-text { + color: blue; +} diff --git a/test/integration/scss-fixtures/multi-global/pages/_app.js b/test/integration/scss-fixtures/multi-global/pages/_app.js new file mode 100644 index 0000000000000..29beb9fdb3cc5 --- /dev/null +++ b/test/integration/scss-fixtures/multi-global/pages/_app.js @@ -0,0 +1,13 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global1.scss' +import '../styles/global2.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/multi-global/pages/index.js b/test/integration/scss-fixtures/multi-global/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/multi-global/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/multi-global/styles/global1.scss b/test/integration/scss-fixtures/multi-global/styles/global1.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/multi-global/styles/global1.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/multi-global/styles/global2.scss b/test/integration/scss-fixtures/multi-global/styles/global2.scss new file mode 100644 index 0000000000000..9d1af6c0f6db1 --- /dev/null +++ b/test/integration/scss-fixtures/multi-global/styles/global2.scss @@ -0,0 +1,3 @@ +.blue-text { + color: blue; +} diff --git a/test/integration/scss-fixtures/multi-module/pages/blue.js b/test/integration/scss-fixtures/multi-module/pages/blue.js new file mode 100644 index 0000000000000..1c45c34e41a84 --- /dev/null +++ b/test/integration/scss-fixtures/multi-module/pages/blue.js @@ -0,0 +1,20 @@ +import Link from 'next/link' +import { blueText } from './blue.module.scss' + +export default function Blue() { + return ( + <> +
+ This text should be blue. +
+
+ + Red + +
+ + None + + + ) +} diff --git a/test/integration/scss-fixtures/multi-module/pages/blue.module.scss b/test/integration/scss-fixtures/multi-module/pages/blue.module.scss new file mode 100644 index 0000000000000..4c5ac28ce4ef8 --- /dev/null +++ b/test/integration/scss-fixtures/multi-module/pages/blue.module.scss @@ -0,0 +1,3 @@ +.blueText { + color: blue; +} diff --git a/test/integration/scss-fixtures/multi-module/pages/none.js b/test/integration/scss-fixtures/multi-module/pages/none.js new file mode 100644 index 0000000000000..f26c2d80b3ae0 --- /dev/null +++ b/test/integration/scss-fixtures/multi-module/pages/none.js @@ -0,0 +1,19 @@ +import Link from 'next/link' + +export default function None() { + return ( + <> +
+ This text should be black. +
+
+ + Red + +
+ + Blue + + + ) +} diff --git a/test/integration/scss-fixtures/multi-module/pages/red.js b/test/integration/scss-fixtures/multi-module/pages/red.js new file mode 100644 index 0000000000000..af8b699159986 --- /dev/null +++ b/test/integration/scss-fixtures/multi-module/pages/red.js @@ -0,0 +1,20 @@ +import Link from 'next/link' +import { redText } from './red.module.scss' + +export default function Red() { + return ( + <> +
+ This text should be red. +
+
+ + Blue + +
+ + None + + + ) +} diff --git a/test/integration/scss-fixtures/multi-module/pages/red.module.scss b/test/integration/scss-fixtures/multi-module/pages/red.module.scss new file mode 100644 index 0000000000000..08a38e09ef8ea --- /dev/null +++ b/test/integration/scss-fixtures/multi-module/pages/red.module.scss @@ -0,0 +1,3 @@ +.redText { + color: red; +} diff --git a/test/integration/scss-fixtures/multi-page/pages/_app.js b/test/integration/scss-fixtures/multi-page/pages/_app.js new file mode 100644 index 0000000000000..29beb9fdb3cc5 --- /dev/null +++ b/test/integration/scss-fixtures/multi-page/pages/_app.js @@ -0,0 +1,13 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global1.scss' +import '../styles/global2.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/multi-page/pages/page1.js b/test/integration/scss-fixtures/multi-page/pages/page1.js new file mode 100644 index 0000000000000..94b9d0f24ca37 --- /dev/null +++ b/test/integration/scss-fixtures/multi-page/pages/page1.js @@ -0,0 +1,14 @@ +import Link from 'next/link' +export default function Page1() { + return ( + <> +
This text should be red.
+
+ +
+ + Switch page + + + ) +} diff --git a/test/integration/scss-fixtures/multi-page/pages/page2.js b/test/integration/scss-fixtures/multi-page/pages/page2.js new file mode 100644 index 0000000000000..e8e49a87514dc --- /dev/null +++ b/test/integration/scss-fixtures/multi-page/pages/page2.js @@ -0,0 +1,14 @@ +import Link from 'next/link' +export default function Page2() { + return ( + <> +
This text should be blue.
+
+ +
+ + Switch page + + + ) +} diff --git a/test/integration/scss-fixtures/multi-page/styles/global1.css b/test/integration/scss-fixtures/multi-page/styles/global1.css new file mode 100644 index 0000000000000..ec747fa47ddb8 --- /dev/null +++ b/test/integration/scss-fixtures/multi-page/styles/global1.css @@ -0,0 +1 @@ +null \ No newline at end of file diff --git a/test/integration/scss-fixtures/multi-page/styles/global1.scss b/test/integration/scss-fixtures/multi-page/styles/global1.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/multi-page/styles/global1.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/multi-page/styles/global2.scss b/test/integration/scss-fixtures/multi-page/styles/global2.scss new file mode 100644 index 0000000000000..9d1af6c0f6db1 --- /dev/null +++ b/test/integration/scss-fixtures/multi-page/styles/global2.scss @@ -0,0 +1,3 @@ +.blue-text { + color: blue; +} diff --git a/test/integration/scss-fixtures/nested-global/pages/_app.js b/test/integration/scss-fixtures/nested-global/pages/_app.js new file mode 100644 index 0000000000000..29beb9fdb3cc5 --- /dev/null +++ b/test/integration/scss-fixtures/nested-global/pages/_app.js @@ -0,0 +1,13 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global1.scss' +import '../styles/global2.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/nested-global/pages/index.js b/test/integration/scss-fixtures/nested-global/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/nested-global/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/nested-global/styles/global1.scss b/test/integration/scss-fixtures/nested-global/styles/global1.scss new file mode 100644 index 0000000000000..c6abef272702d --- /dev/null +++ b/test/integration/scss-fixtures/nested-global/styles/global1.scss @@ -0,0 +1,5 @@ +@import './global1b.scss'; + +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/nested-global/styles/global1b.scss b/test/integration/scss-fixtures/nested-global/styles/global1b.scss new file mode 100644 index 0000000000000..3902bc9032e31 --- /dev/null +++ b/test/integration/scss-fixtures/nested-global/styles/global1b.scss @@ -0,0 +1,4 @@ +.red-text { + color: purple; + font-weight: bolder; +} diff --git a/test/integration/scss-fixtures/nested-global/styles/global2.scss b/test/integration/scss-fixtures/nested-global/styles/global2.scss new file mode 100644 index 0000000000000..37e7107172397 --- /dev/null +++ b/test/integration/scss-fixtures/nested-global/styles/global2.scss @@ -0,0 +1,5 @@ +@import './global2b.scss'; + +.blue-text { + color: blue; +} diff --git a/test/integration/scss-fixtures/nested-global/styles/global2b.scss b/test/integration/scss-fixtures/nested-global/styles/global2b.scss new file mode 100644 index 0000000000000..56bea0235b8ac --- /dev/null +++ b/test/integration/scss-fixtures/nested-global/styles/global2b.scss @@ -0,0 +1,4 @@ +.blue-text { + color: orange; + font-weight: bolder; +} diff --git a/test/integration/scss-fixtures/next.config.js b/test/integration/scss-fixtures/next.config.js new file mode 100644 index 0000000000000..2a0ee47afec3c --- /dev/null +++ b/test/integration/scss-fixtures/next.config.js @@ -0,0 +1,10 @@ +module.exports = { + onDemandEntries: { + // Make sure entries are not getting disposed. + maxInactiveAge: 1000 * 60 * 60, + }, + webpack(cfg) { + cfg.devtool = 'source-map' + return cfg + }, +} diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.js b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.js new file mode 100644 index 0000000000000..7d1fdcb8879d9 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.js @@ -0,0 +1,3 @@ +const message = 'Why hello there' + +module.exports = { message } diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.mjs b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.mjs new file mode 100644 index 0000000000000..a81498ed3ad53 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.mjs @@ -0,0 +1 @@ +export const message = 'Why hello there' diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss new file mode 100644 index 0000000000000..aed5852ba6873 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss @@ -0,0 +1,6 @@ +@import 'other2.scss'; + +.subClass { + composes: className from './other.scss'; + background: blue; +} diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss new file mode 100644 index 0000000000000..d8eb83346a6ea --- /dev/null +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss @@ -0,0 +1,6 @@ +@import 'other3.scss'; + +.className { + background: red; + color: yellow; +} diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss new file mode 100644 index 0000000000000..3edf8b085d62b --- /dev/null +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss @@ -0,0 +1,3 @@ +.other2 { + color: red; +} diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss new file mode 100644 index 0000000000000..3bff2788064f9 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss @@ -0,0 +1,3 @@ +.other3 { + color: violet; +} diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/package.json b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/package.json new file mode 100644 index 0000000000000..ab5f2cd4a1cf7 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/package.json @@ -0,0 +1,4 @@ +{ + "name": "example", + "main": "index" +} diff --git a/test/integration/scss-fixtures/nm-module-nested/pages/index.js b/test/integration/scss-fixtures/nm-module-nested/pages/index.js new file mode 100644 index 0000000000000..897696bd01572 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module-nested/pages/index.js @@ -0,0 +1,12 @@ +import * as data from 'example' +import * as classes from 'example/index.module.scss' + +function Home() { + return ( +
+ {JSON.stringify(data)} {JSON.stringify(classes)} +
+ ) +} + +export default Home diff --git a/test/integration/scss-fixtures/nm-module/node_modules/example/index.js b/test/integration/scss-fixtures/nm-module/node_modules/example/index.js new file mode 100644 index 0000000000000..7d1fdcb8879d9 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module/node_modules/example/index.js @@ -0,0 +1,3 @@ +const message = 'Why hello there' + +module.exports = { message } diff --git a/test/integration/scss-fixtures/nm-module/node_modules/example/index.mjs b/test/integration/scss-fixtures/nm-module/node_modules/example/index.mjs new file mode 100644 index 0000000000000..a81498ed3ad53 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module/node_modules/example/index.mjs @@ -0,0 +1 @@ +export const message = 'Why hello there' diff --git a/test/integration/scss-fixtures/nm-module/node_modules/example/index.module.scss b/test/integration/scss-fixtures/nm-module/node_modules/example/index.module.scss new file mode 100644 index 0000000000000..f77fe0ef0bdbe --- /dev/null +++ b/test/integration/scss-fixtures/nm-module/node_modules/example/index.module.scss @@ -0,0 +1,3 @@ +.redText { + color: 'red'; +} diff --git a/test/integration/scss-fixtures/nm-module/node_modules/example/package.json b/test/integration/scss-fixtures/nm-module/node_modules/example/package.json new file mode 100644 index 0000000000000..ab5f2cd4a1cf7 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module/node_modules/example/package.json @@ -0,0 +1,4 @@ +{ + "name": "example", + "main": "index" +} diff --git a/test/integration/scss-fixtures/nm-module/pages/index.js b/test/integration/scss-fixtures/nm-module/pages/index.js new file mode 100644 index 0000000000000..897696bd01572 --- /dev/null +++ b/test/integration/scss-fixtures/nm-module/pages/index.js @@ -0,0 +1,12 @@ +import * as data from 'example' +import * as classes from 'example/index.module.scss' + +function Home() { + return ( +
+ {JSON.stringify(data)} {JSON.stringify(classes)} +
+ ) +} + +export default Home diff --git a/test/integration/scss-fixtures/npm-import-bad/pages/_app.js b/test/integration/scss-fixtures/npm-import-bad/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-bad/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/npm-import-bad/pages/index.js b/test/integration/scss-fixtures/npm-import-bad/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-bad/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/npm-import-bad/styles/global.scss b/test/integration/scss-fixtures/npm-import-bad/styles/global.scss new file mode 100644 index 0000000000000..8e799fdddaeec --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-bad/styles/global.scss @@ -0,0 +1 @@ +@import 'nprogress/nprogress.scss'; diff --git a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/index.js b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/index.js new file mode 100644 index 0000000000000..7d1fdcb8879d9 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/index.js @@ -0,0 +1,3 @@ +const message = 'Why hello there' + +module.exports = { message } diff --git a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/index.mjs b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/index.mjs new file mode 100644 index 0000000000000..a81498ed3ad53 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/index.mjs @@ -0,0 +1 @@ +export const message = 'Why hello there' diff --git a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/other.scss b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/other.scss new file mode 100644 index 0000000000000..eefdaa510cfa8 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/other.scss @@ -0,0 +1,3 @@ +.other { + color: blue; +} diff --git a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/package.json b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/package.json new file mode 100644 index 0000000000000..ab5f2cd4a1cf7 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/package.json @@ -0,0 +1,4 @@ +{ + "name": "example", + "main": "index" +} diff --git a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss new file mode 100644 index 0000000000000..57ac6959e15d3 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss @@ -0,0 +1,5 @@ +@import url('other.scss'); + +.test { + color: red; +} diff --git a/test/integration/scss-fixtures/npm-import-nested/pages/_app.js b/test/integration/scss-fixtures/npm-import-nested/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-nested/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/npm-import-nested/pages/index.js b/test/integration/scss-fixtures/npm-import-nested/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-nested/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/npm-import-nested/styles/global.scss b/test/integration/scss-fixtures/npm-import-nested/styles/global.scss new file mode 100644 index 0000000000000..fb61b329db5f7 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import-nested/styles/global.scss @@ -0,0 +1 @@ +@import '~example/test.scss'; diff --git a/test/integration/scss-fixtures/npm-import/pages/_app.js b/test/integration/scss-fixtures/npm-import/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/npm-import/pages/index.js b/test/integration/scss-fixtures/npm-import/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/npm-import/styles/global.scss b/test/integration/scss-fixtures/npm-import/styles/global.scss new file mode 100644 index 0000000000000..a3bfbdf7d6700 --- /dev/null +++ b/test/integration/scss-fixtures/npm-import/styles/global.scss @@ -0,0 +1 @@ +@import '~nprogress/nprogress.scss'; diff --git a/test/integration/scss-fixtures/prod-module/pages/index.js b/test/integration/scss-fixtures/prod-module/pages/index.js new file mode 100644 index 0000000000000..7b42859a67e32 --- /dev/null +++ b/test/integration/scss-fixtures/prod-module/pages/index.js @@ -0,0 +1,9 @@ +import { redText } from './index.module.scss' + +export default function Home() { + return ( +
+ This text should be red. +
+ ) +} diff --git a/test/integration/scss-fixtures/prod-module/pages/index.module.scss b/test/integration/scss-fixtures/prod-module/pages/index.module.scss new file mode 100644 index 0000000000000..08a38e09ef8ea --- /dev/null +++ b/test/integration/scss-fixtures/prod-module/pages/index.module.scss @@ -0,0 +1,3 @@ +.redText { + color: red; +} diff --git a/test/integration/scss-fixtures/single-global-src/src/pages/_app.js b/test/integration/scss-fixtures/single-global-src/src/pages/_app.js new file mode 100644 index 0000000000000..13558a96f8e8a --- /dev/null +++ b/test/integration/scss-fixtures/single-global-src/src/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/single-global-src/src/pages/index.js b/test/integration/scss-fixtures/single-global-src/src/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/single-global-src/src/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/single-global-src/styles/global.scss b/test/integration/scss-fixtures/single-global-src/styles/global.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/single-global-src/styles/global.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/single-global/pages/_app.js b/test/integration/scss-fixtures/single-global/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/single-global/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/single-global/pages/index.js b/test/integration/scss-fixtures/single-global/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/single-global/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/single-global/styles/global.scss b/test/integration/scss-fixtures/single-global/styles/global.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/single-global/styles/global.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/unused/pages/index.js b/test/integration/scss-fixtures/unused/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/unused/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/assets/light.svg b/test/integration/scss-fixtures/url-global-asset-prefix-1/assets/light.svg new file mode 100644 index 0000000000000..0194cbce06561 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/assets/light.svg @@ -0,0 +1,17 @@ + + + + Logotype - White + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/next.config.js b/test/integration/scss-fixtures/url-global-asset-prefix-1/next.config.js new file mode 100644 index 0000000000000..177a5d7903f16 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/next.config.js @@ -0,0 +1,5 @@ +const config = require('../next.config.js') +module.exports = { + ...config, + assetPrefix: '/foo/', +} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/pages/_app.js b/test/integration/scss-fixtures/url-global-asset-prefix-1/pages/_app.js new file mode 100644 index 0000000000000..29beb9fdb3cc5 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/pages/_app.js @@ -0,0 +1,13 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global1.scss' +import '../styles/global2.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/pages/index.js b/test/integration/scss-fixtures/url-global-asset-prefix-1/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/dark.svg b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/dark.svg new file mode 100644 index 0000000000000..bdae3d6587872 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/dark.svg @@ -0,0 +1,17 @@ + + + + Logotype - Black + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/dark2.svg b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/dark2.svg new file mode 100644 index 0000000000000..bdae3d6587872 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/dark2.svg @@ -0,0 +1,17 @@ + + + + Logotype - Black + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global1.scss b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global1.scss new file mode 100644 index 0000000000000..fdaf9c9476f9c --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global1.scss @@ -0,0 +1,4 @@ +.red-text { + color: red; + background-image: url('./dark.svg') url(dark2.svg); +} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2.scss b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2.scss new file mode 100644 index 0000000000000..37e7107172397 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2.scss @@ -0,0 +1,5 @@ +@import './global2b.scss'; + +.blue-text { + color: blue; +} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2b.scss b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2b.scss new file mode 100644 index 0000000000000..41c015298e5fd --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2b.scss @@ -0,0 +1,5 @@ +.blue-text { + color: orange; + font-weight: bolder; + background-image: url(../assets/light.svg); +} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/assets/light.svg b/test/integration/scss-fixtures/url-global-asset-prefix-2/assets/light.svg new file mode 100644 index 0000000000000..0194cbce06561 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/assets/light.svg @@ -0,0 +1,17 @@ + + + + Logotype - White + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/next.config.js b/test/integration/scss-fixtures/url-global-asset-prefix-2/next.config.js new file mode 100644 index 0000000000000..72ff6da7d9adf --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/next.config.js @@ -0,0 +1,5 @@ +const config = require('../next.config.js') +module.exports = { + ...config, + assetPrefix: '/foo', +} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/pages/_app.js b/test/integration/scss-fixtures/url-global-asset-prefix-2/pages/_app.js new file mode 100644 index 0000000000000..29beb9fdb3cc5 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/pages/_app.js @@ -0,0 +1,13 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global1.scss' +import '../styles/global2.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/pages/index.js b/test/integration/scss-fixtures/url-global-asset-prefix-2/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/dark.svg b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/dark.svg new file mode 100644 index 0000000000000..bdae3d6587872 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/dark.svg @@ -0,0 +1,17 @@ + + + + Logotype - Black + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/dark2.svg b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/dark2.svg new file mode 100644 index 0000000000000..bdae3d6587872 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/dark2.svg @@ -0,0 +1,17 @@ + + + + Logotype - Black + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global1.scss b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global1.scss new file mode 100644 index 0000000000000..fdaf9c9476f9c --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global1.scss @@ -0,0 +1,4 @@ +.red-text { + color: red; + background-image: url('./dark.svg') url(dark2.svg); +} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2.scss b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2.scss new file mode 100644 index 0000000000000..37e7107172397 --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2.scss @@ -0,0 +1,5 @@ +@import './global2b.scss'; + +.blue-text { + color: blue; +} diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2b.scss b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2b.scss new file mode 100644 index 0000000000000..41c015298e5fd --- /dev/null +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2b.scss @@ -0,0 +1,5 @@ +.blue-text { + color: orange; + font-weight: bolder; + background-image: url(../assets/light.svg); +} diff --git a/test/integration/scss-fixtures/url-global/assets/light.svg b/test/integration/scss-fixtures/url-global/assets/light.svg new file mode 100644 index 0000000000000..0194cbce06561 --- /dev/null +++ b/test/integration/scss-fixtures/url-global/assets/light.svg @@ -0,0 +1,17 @@ + + + + Logotype - White + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global/pages/_app.js b/test/integration/scss-fixtures/url-global/pages/_app.js new file mode 100644 index 0000000000000..29beb9fdb3cc5 --- /dev/null +++ b/test/integration/scss-fixtures/url-global/pages/_app.js @@ -0,0 +1,13 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global1.scss' +import '../styles/global2.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/url-global/pages/index.js b/test/integration/scss-fixtures/url-global/pages/index.js new file mode 100644 index 0000000000000..5cbac8a153d77 --- /dev/null +++ b/test/integration/scss-fixtures/url-global/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/url-global/styles/dark.svg b/test/integration/scss-fixtures/url-global/styles/dark.svg new file mode 100644 index 0000000000000..bdae3d6587872 --- /dev/null +++ b/test/integration/scss-fixtures/url-global/styles/dark.svg @@ -0,0 +1,17 @@ + + + + Logotype - Black + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global/styles/dark2.svg b/test/integration/scss-fixtures/url-global/styles/dark2.svg new file mode 100644 index 0000000000000..bdae3d6587872 --- /dev/null +++ b/test/integration/scss-fixtures/url-global/styles/dark2.svg @@ -0,0 +1,17 @@ + + + + Logotype - Black + Created with Sketch. + + + + + + + + + + + + diff --git a/test/integration/scss-fixtures/url-global/styles/global1.scss b/test/integration/scss-fixtures/url-global/styles/global1.scss new file mode 100644 index 0000000000000..fdaf9c9476f9c --- /dev/null +++ b/test/integration/scss-fixtures/url-global/styles/global1.scss @@ -0,0 +1,4 @@ +.red-text { + color: red; + background-image: url('./dark.svg') url(dark2.svg); +} diff --git a/test/integration/scss-fixtures/url-global/styles/global2.scss b/test/integration/scss-fixtures/url-global/styles/global2.scss new file mode 100644 index 0000000000000..37e7107172397 --- /dev/null +++ b/test/integration/scss-fixtures/url-global/styles/global2.scss @@ -0,0 +1,5 @@ +@import './global2b.scss'; + +.blue-text { + color: blue; +} diff --git a/test/integration/scss-fixtures/url-global/styles/global2b.scss b/test/integration/scss-fixtures/url-global/styles/global2b.scss new file mode 100644 index 0000000000000..41c015298e5fd --- /dev/null +++ b/test/integration/scss-fixtures/url-global/styles/global2b.scss @@ -0,0 +1,5 @@ +.blue-text { + color: orange; + font-weight: bolder; + background-image: url(../assets/light.svg); +} diff --git a/test/integration/scss-fixtures/valid-and-invalid-global/pages/_app.js b/test/integration/scss-fixtures/valid-and-invalid-global/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/valid-and-invalid-global/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/valid-and-invalid-global/pages/index.js b/test/integration/scss-fixtures/valid-and-invalid-global/pages/index.js new file mode 100644 index 0000000000000..38d46eb2a45eb --- /dev/null +++ b/test/integration/scss-fixtures/valid-and-invalid-global/pages/index.js @@ -0,0 +1,5 @@ +import '../styles/global.scss' + +export default function Home() { + return
This text should be red.
+} diff --git a/test/integration/scss-fixtures/valid-and-invalid-global/styles/global.scss b/test/integration/scss-fixtures/valid-and-invalid-global/styles/global.scss new file mode 100644 index 0000000000000..8e1524022baf8 --- /dev/null +++ b/test/integration/scss-fixtures/valid-and-invalid-global/styles/global.scss @@ -0,0 +1,3 @@ +.red-text { + color: red; +} diff --git a/test/integration/scss-fixtures/with-styled-jsx/pages/_app.js b/test/integration/scss-fixtures/with-styled-jsx/pages/_app.js new file mode 100644 index 0000000000000..b89fe16feb731 --- /dev/null +++ b/test/integration/scss-fixtures/with-styled-jsx/pages/_app.js @@ -0,0 +1,12 @@ +import React from 'react' +import App from 'next/app' +import '../styles/global.scss' + +class MyApp extends App { + render() { + const { Component, pageProps } = this.props + return + } +} + +export default MyApp diff --git a/test/integration/scss-fixtures/with-styled-jsx/pages/index.js b/test/integration/scss-fixtures/with-styled-jsx/pages/index.js new file mode 100644 index 0000000000000..ed9aa0621925e --- /dev/null +++ b/test/integration/scss-fixtures/with-styled-jsx/pages/index.js @@ -0,0 +1,12 @@ +export default function Home() { + return ( + <> +
This text should be green.
+ + + ) +} diff --git a/test/integration/scss-fixtures/with-styled-jsx/styles/global.scss b/test/integration/scss-fixtures/with-styled-jsx/styles/global.scss new file mode 100644 index 0000000000000..167caa35ea86e --- /dev/null +++ b/test/integration/scss-fixtures/with-styled-jsx/styles/global.scss @@ -0,0 +1,3 @@ +.my-text { + color: red; +} diff --git a/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/pages/_app.js b/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/pages/_app.js new file mode 100644 index 0000000000000..0e40312aad8ac --- /dev/null +++ b/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/pages/_app.js @@ -0,0 +1,5 @@ +import '../styles/global.scss' + +export default function MyApp({ Component, pageProps }) { + return +} diff --git a/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/pages/index.js b/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/pages/index.js new file mode 100644 index 0000000000000..ee6a89480a706 --- /dev/null +++ b/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/pages/index.js @@ -0,0 +1,38 @@ +import Link from 'next/link' + +const links = [ + { href: 'https://github.com/zeit/next.js', label: 'GitHub' }, + { href: 'https://nextjs.org/docs', label: 'Docs' }, +] + +function Nav() { + return ( + + ) +} + +export default () => ( +
+
+) diff --git a/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/postcss.config.js b/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/postcss.config.js new file mode 100644 index 0000000000000..b39d3d7ff9d14 --- /dev/null +++ b/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/postcss.config.js @@ -0,0 +1,13 @@ +const path = require('path') +module.exports = { + plugins: [ + 'tailwindcss', + [ + '@fullhuman/postcss-purgecss', + { + content: [path.join(__dirname, './pages/**/*.{js,jsx,ts,tsx}')], + defaultExtractor: content => content.match(/[A-Za-z0-9-_:/]+/g) || [], + }, + ], + ], +} diff --git a/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/styles/global.scss b/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/styles/global.scss new file mode 100644 index 0000000000000..b5c61c956711f --- /dev/null +++ b/test/integration/scss-fixtures/with-tailwindcss-and-purgecss/styles/global.scss @@ -0,0 +1,3 @@ +@tailwind base; +@tailwind components; +@tailwind utilities; diff --git a/test/integration/scss-fixtures/with-tailwindcss/package.json b/test/integration/scss-fixtures/with-tailwindcss/package.json new file mode 100644 index 0000000000000..50375a78eb20b --- /dev/null +++ b/test/integration/scss-fixtures/with-tailwindcss/package.json @@ -0,0 +1,7 @@ +{ + "postcss": { + "plugins": { + "tailwindcss": {} + } + } +} diff --git a/test/integration/scss-fixtures/with-tailwindcss/pages/_app.js b/test/integration/scss-fixtures/with-tailwindcss/pages/_app.js new file mode 100644 index 0000000000000..0e40312aad8ac --- /dev/null +++ b/test/integration/scss-fixtures/with-tailwindcss/pages/_app.js @@ -0,0 +1,5 @@ +import '../styles/global.scss' + +export default function MyApp({ Component, pageProps }) { + return +} diff --git a/test/integration/scss-fixtures/with-tailwindcss/pages/index.js b/test/integration/scss-fixtures/with-tailwindcss/pages/index.js new file mode 100644 index 0000000000000..b3ba78da2d5e1 --- /dev/null +++ b/test/integration/scss-fixtures/with-tailwindcss/pages/index.js @@ -0,0 +1,3 @@ +export default function Home() { + return
+} diff --git a/test/integration/scss-fixtures/with-tailwindcss/styles/global.scss b/test/integration/scss-fixtures/with-tailwindcss/styles/global.scss new file mode 100644 index 0000000000000..b5c61c956711f --- /dev/null +++ b/test/integration/scss-fixtures/with-tailwindcss/styles/global.scss @@ -0,0 +1,3 @@ +@tailwind base; +@tailwind components; +@tailwind utilities; diff --git a/test/integration/scss/test/index.test.js b/test/integration/scss/test/index.test.js new file mode 100644 index 0000000000000..59c698114427c --- /dev/null +++ b/test/integration/scss/test/index.test.js @@ -0,0 +1,815 @@ +/* eslint-env jest */ +/* global jasmine */ +import 'flat-map-polyfill' +import { join } from 'path' +import { readdir, readFile, remove } from 'fs-extra' +import { + findPort, + nextBuild, + nextStart, + launchApp, + killApp, + File, + waitFor, + renderViaHTTP, +} from 'next-test-utils' +import webdriver from 'next-webdriver' +import cheerio from 'cheerio' + +jasmine.DEFAULT_TIMEOUT_INTERVAL = 1000 * 60 * 2 + +const fixturesDir = join(__dirname, '../..', 'scss-fixtures') + +describe('SCSS Support', () => { + describe('Basic Global Support', () => { + const appDir = join(fixturesDir, 'single-global') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + expect(await readFile(join(cssFolder, cssFiles[0]), 'utf8')).toContain( + 'color:red' + ) + }) + }) + + describe('Basic Global Support with src/ dir', () => { + const appDir = join(fixturesDir, 'single-global-src') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + expect(await readFile(join(cssFolder, cssFiles[0]), 'utf8')).toContain( + 'color:red' + ) + }) + }) + + describe('Multi Global Support', () => { + const appDir = join(fixturesDir, 'multi-global') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot(`".red-text{color:red}.blue-text{color:#00f}"`) + }) + }) + + describe('Nested @import() Global Support', () => { + const appDir = join(fixturesDir, 'nested-global') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot( + `".red-text{color:purple;font-weight:bolder;color:red}.blue-text{color:orange;font-weight:bolder;color:#00f}"` + ) + }) + }) + + describe('CSS Compilation and Prefixing', () => { + const appDir = join(fixturesDir, 'compilation-and-prefixing') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've compiled and prefixed`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot( + `"@media (min-width:480px) and (max-width:767px){::-webkit-input-placeholder{color:green}::-moz-placeholder{color:green}:-ms-input-placeholder{color:green}::-ms-input-placeholder{color:green}::placeholder{color:green}}"` + ) + + // Contains a source map + expect(cssContent).toMatch(/\/\*#\s*sourceMappingURL=(.+\.map)\s*\*\//) + }) + + it(`should've emitted a source map`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssMapFiles = files.filter(f => /\.css\.map$/.test(f)) + + expect(cssMapFiles.length).toBe(1) + const cssMapContent = ( + await readFile(join(cssFolder, cssMapFiles[0]), 'utf8') + ).trim() + + const { version, mappings, sourcesContent } = JSON.parse(cssMapContent) + expect({ version, mappings, sourcesContent }).toMatchInlineSnapshot(` + Object { + "mappings": "AAAA,+CACE,4BACE,WACF,CAFA,mBACE,WACF,CAFA,uBACE,WACF,CAFA,wBACE,WACF,CAFA,cACE,WACF,CACF", + "sourcesContent": Array [ + "@media (480px <= width < 768px) { + ::placeholder { + color: green; + } + } + ", + ], + "version": 3, + } + `) + }) + }) + + // Tests css ordering + describe('Multi Global Support (reversed)', () => { + const appDir = join(fixturesDir, 'multi-global-reversed') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot(`".blue-text{color:#00f}.red-text{color:red}"`) + }) + }) + + describe('Invalid CSS in _document', () => { + const appDir = join(fixturesDir, 'invalid-module-document') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should fail to build', async () => { + const { stderr } = await nextBuild(appDir, [], { + stderr: true, + }) + expect(stderr).toContain('Failed to compile') + expect(stderr).toContain('styles.module.css') + expect(stderr).toMatch( + /CSS.*cannot.*be imported within.*pages[\\/]_document\.js/ + ) + expect(stderr).toMatch(/Location:.*pages[\\/]_document\.js/) + }) + }) + + describe('Invalid Global CSS', () => { + const appDir = join(fixturesDir, 'invalid-global') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should fail to build', async () => { + const { stderr } = await nextBuild(appDir, [], { + stderr: true, + }) + expect(stderr).toContain('Failed to compile') + expect(stderr).toContain('styles/global.css') + expect(stderr).toMatch( + /Please move all global CSS imports.*?pages(\/|\\)_app/ + ) + expect(stderr).toMatch(/Location:.*pages[\\/]index\.js/) + }) + }) + + describe('Invalid Global CSS with Custom App', () => { + const appDir = join(fixturesDir, 'invalid-global-with-app') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should fail to build', async () => { + const { stderr } = await nextBuild(appDir, [], { + stderr: true, + }) + expect(stderr).toContain('Failed to compile') + expect(stderr).toContain('styles/global.css') + expect(stderr).toMatch( + /Please move all global CSS imports.*?pages(\/|\\)_app/ + ) + expect(stderr).toMatch(/Location:.*pages[\\/]index\.js/) + }) + }) + + describe('Valid and Invalid Global CSS with Custom App', () => { + const appDir = join(fixturesDir, 'valid-and-invalid-global') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should fail to build', async () => { + const { stderr } = await nextBuild(appDir, [], { + stderr: true, + }) + expect(stderr).toContain('Failed to compile') + expect(stderr).toContain('styles/global.css') + expect(stderr).toContain('Please move all global CSS imports') + expect(stderr).toMatch(/Location:.*pages[\\/]index\.js/) + }) + }) + + describe('Can hot reload CSS without losing state', () => { + const appDir = join(fixturesDir, 'multi-page') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + let appPort + let app + beforeAll(async () => { + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should update CSS color without remounting ', async () => { + let browser + try { + browser = await webdriver(appPort, '/page1') + await waitFor(2000) // ensure application hydrates + + const desiredText = 'hello world' + await browser.elementById('text-input').type(desiredText) + expect(await browser.elementById('text-input').getValue()).toBe( + desiredText + ) + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('.red-text')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) + + const cssFile = new File(join(appDir, 'styles/global1.css')) + try { + cssFile.replace('color: red', 'color: purple') + await waitFor(2000) // wait for HMR + + const refreshedColor = await browser.eval( + `window.getComputedStyle(document.querySelector('.red-text')).color` + ) + expect(refreshedColor).toMatchInlineSnapshot(`"rgb(128, 0, 128)"`) + + // ensure text remained + expect(await browser.elementById('text-input').getValue()).toBe( + desiredText + ) + } finally { + cssFile.restore() + } + } finally { + if (browser) { + await browser.close() + } + } + }) + }) + + describe('Has CSS in computed styles in Development', () => { + const appDir = join(fixturesDir, 'multi-page') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + let appPort + let app + beforeAll(async () => { + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should have CSS for page', async () => { + let browser + try { + browser = await webdriver(appPort, '/page2') + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('.blue-text')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(0, 0, 255)"`) + } finally { + if (browser) { + await browser.close() + } + } + }) + }) + + describe('Body is not hidden when unused in Development', () => { + const appDir = join(fixturesDir, 'unused') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + let appPort + let app + beforeAll(async () => { + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should have body visible', async () => { + let browser + try { + browser = await webdriver(appPort, '/') + const currentDisplay = await browser.eval( + `window.getComputedStyle(document.querySelector('body')).display` + ) + expect(currentDisplay).toBe('block') + } finally { + if (browser) { + await browser.close() + } + } + }) + }) + + describe('Body is not hidden when broken in Development', () => { + const appDir = join(fixturesDir, 'unused') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should have body visible', async () => { + const pageFile = new File(join(appDir, 'pages/index.js')) + let browser + try { + pageFile.replace('
', '
') + await waitFor(2000) // wait for recompile + + browser = await webdriver(appPort, '/') + const currentDisplay = await browser.eval( + `window.getComputedStyle(document.querySelector('body')).display` + ) + expect(currentDisplay).toBe('block') + } finally { + pageFile.restore() + if (browser) { + await browser.close() + } + } + }) + }) + + describe('Has CSS in computed styles in Production', () => { + const appDir = join(fixturesDir, 'multi-page') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should have CSS for page', async () => { + const browser = await webdriver(appPort, '/page2') + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('.blue-text')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(0, 0, 255)"`) + }) + + it(`should've preloaded the CSS file and injected it in `, async () => { + const content = await renderViaHTTP(appPort, '/page2') + const $ = cheerio.load(content) + + const cssPreload = $('link[rel="preload"][as="style"]') + expect(cssPreload.length).toBe(1) + expect(cssPreload.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + + const cssSheet = $('link[rel="stylesheet"]') + expect(cssSheet.length).toBe(1) + expect(cssSheet.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + + /* ensure CSS preloaded first */ + const allPreloads = [].slice.call($('link[rel="preload"]')) + const styleIndexes = allPreloads.flatMap((p, i) => + p.attribs.as === 'style' ? i : [] + ) + expect(styleIndexes).toEqual([0]) + }) + }) + + describe('CSS URL via `file-loader`', () => { + const appDir = join(fixturesDir, 'url-global') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted expected files`, async () => { + const cssFolder = join(appDir, '.next/static/css') + const mediaFolder = join(appDir, '.next/static/media') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatch( + /^\.red-text\{color:red;background-image:url\(\/_next\/static\/media\/dark\.[a-z0-9]{32}\.svg\) url\(\/_next\/static\/media\/dark2\.[a-z0-9]{32}\.svg\)\}\.blue-text\{color:orange;font-weight:bolder;background-image:url\(\/_next\/static\/media\/light\.[a-z0-9]{32}\.svg\);color:#00f\}$/ + ) + + const mediaFiles = await readdir(mediaFolder) + expect(mediaFiles.length).toBe(3) + expect( + mediaFiles + .map(fileName => + /^(.+?)\..{32}\.(.+?)$/ + .exec(fileName) + .slice(1) + .join('.') + ) + .sort() + ).toMatchInlineSnapshot(` + Array [ + "dark.svg", + "dark2.svg", + "light.svg", + ] + `) + }) + }) + + describe('CSS URL via `file-loader` and asset prefix (1)', () => { + const appDir = join(fixturesDir, 'url-global-asset-prefix-1') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted expected files`, async () => { + const cssFolder = join(appDir, '.next/static/css') + const mediaFolder = join(appDir, '.next/static/media') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatch( + /^\.red-text\{color:red;background-image:url\(\/foo\/_next\/static\/media\/dark\.[a-z0-9]{32}\.svg\) url\(\/foo\/_next\/static\/media\/dark2\.[a-z0-9]{32}\.svg\)\}\.blue-text\{color:orange;font-weight:bolder;background-image:url\(\/foo\/_next\/static\/media\/light\.[a-z0-9]{32}\.svg\);color:#00f\}$/ + ) + + const mediaFiles = await readdir(mediaFolder) + expect(mediaFiles.length).toBe(3) + expect( + mediaFiles + .map(fileName => + /^(.+?)\..{32}\.(.+?)$/ + .exec(fileName) + .slice(1) + .join('.') + ) + .sort() + ).toMatchInlineSnapshot(` + Array [ + "dark.svg", + "dark2.svg", + "light.svg", + ] + `) + }) + }) + + describe('CSS URL via `file-loader` and asset prefix (2)', () => { + const appDir = join(fixturesDir, 'url-global-asset-prefix-2') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted expected files`, async () => { + const cssFolder = join(appDir, '.next/static/css') + const mediaFolder = join(appDir, '.next/static/media') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatch( + /^\.red-text\{color:red;background-image:url\(\/foo\/_next\/static\/media\/dark\.[a-z0-9]{32}\.svg\) url\(\/foo\/_next\/static\/media\/dark2\.[a-z0-9]{32}\.svg\)\}\.blue-text\{color:orange;font-weight:bolder;background-image:url\(\/foo\/_next\/static\/media\/light\.[a-z0-9]{32}\.svg\);color:#00f\}$/ + ) + + const mediaFiles = await readdir(mediaFolder) + expect(mediaFiles.length).toBe(3) + expect( + mediaFiles + .map(fileName => + /^(.+?)\..{32}\.(.+?)$/ + .exec(fileName) + .slice(1) + .join('.') + ) + .sort() + ).toMatchInlineSnapshot(` + Array [ + "dark.svg", + "dark2.svg", + "light.svg", + ] + `) + }) + }) + + describe('Good CSS Import from node_modules', () => { + const appDir = join(fixturesDir, 'npm-import') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatch(/nprogress/) + }) + }) + + describe('Good Nested CSS Import from node_modules', () => { + const appDir = join(fixturesDir, 'npm-import-nested') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot(`".other{color:#00f}.test{color:red}"`) + }) + }) + + describe('Bad CSS Import from node_modules', () => { + const appDir = join(fixturesDir, 'npm-import-bad') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should fail the build', async () => { + const { stderr } = await nextBuild(appDir, [], { stderr: true }) + + expect(stderr).toMatch(/Can't resolve '[^']*?nprogress[^']*?'/) + expect(stderr).toMatch(/Build error occurred/) + }) + }) + + describe('Ordering with styled-jsx (dev)', () => { + const appDir = join(fixturesDir, 'with-styled-jsx') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should have the correct color (css ordering)', async () => { + const browser = await webdriver(appPort, '/') + await waitFor(2000) // ensure application hydrates + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('.my-text')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(0, 128, 0)"`) + }) + }) + + describe('Ordering with styled-jsx (prod)', () => { + const appDir = join(fixturesDir, 'with-styled-jsx') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should have the correct color (css ordering)', async () => { + const browser = await webdriver(appPort, '/') + await waitFor(2000) // ensure application hydrates + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('.my-text')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(0, 128, 0)"`) + }) + }) + + describe('Basic Tailwind CSS', () => { + const appDir = join(fixturesDir, 'with-tailwindcss') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've compiled and prefixed`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + + expect(cssContent).toMatch(/object-right-bottom/) // look for tailwind's CSS + expect(cssContent).not.toMatch(/tailwind/) // ensure @tailwind was removed + + // Contains a source map + expect(cssContent).toMatch(/\/\*#\s*sourceMappingURL=(.+\.map)\s*\*\//) + }) + + it(`should've emitted a source map`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssMapFiles = files.filter(f => /\.css\.map$/.test(f)) + + expect(cssMapFiles.length).toBe(1) + }) + }) + + describe('Tailwind and Purge CSS', () => { + const appDir = join(fixturesDir, 'with-tailwindcss-and-purgecss') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should build successfully', async () => { + await nextBuild(appDir) + }) + + it(`should've compiled and prefixed`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + + expect(cssContent).not.toMatch(/object-right-bottom/) // this was unused and should be gone + expect(cssContent).toMatch(/text-blue-500/) // this was used + expect(cssContent).not.toMatch(/tailwind/) // ensure @tailwind was removed + + // Contains a source map + expect(cssContent).toMatch(/\/\*#\s*sourceMappingURL=(.+\.map)\s*\*\//) + }) + + it(`should've emitted a source map`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssMapFiles = files.filter(f => /\.css\.map$/.test(f)) + + expect(cssMapFiles.length).toBe(1) + }) + }) +}) diff --git a/yarn.lock b/yarn.lock index dd3fd79329695..bc8d6031f55ee 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4433,6 +4433,15 @@ clone-deep@^0.3.0: kind-of "^3.2.2" shallow-clone "^0.1.2" +clone-deep@^4.0.1: + version "4.0.1" + resolved "https://registry.yarnpkg.com/clone-deep/-/clone-deep-4.0.1.tgz#c19fd9bdbbf85942b4fd979c84dcf7d5f07c2387" + integrity sha512-neHB9xuzh/wk0dIHweyAXv2aPGZIVk3pLMe+/RNzINf17fe0OG96QroktYAUm7SM1PBnzTabaLboqqxDyMU+SQ== + dependencies: + is-plain-object "^2.0.4" + kind-of "^6.0.2" + shallow-clone "^3.0.0" + clone-response@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/clone-response/-/clone-response-1.0.2.tgz#d1dc973920314df67fbeb94223b4ee350239e96b" @@ -13252,6 +13261,17 @@ sass-loader@6.0.6: lodash.tail "^4.1.1" pify "^3.0.0" +sass-loader@8.0.2: + version "8.0.2" + resolved "https://registry.yarnpkg.com/sass-loader/-/sass-loader-8.0.2.tgz#debecd8c3ce243c76454f2e8290482150380090d" + integrity sha512-7o4dbSK8/Ol2KflEmSco4jTjQoV988bM82P9CZdmo9hR3RLnvNc0ufMNdMrB0caq38JQ/FgF4/7RcbcfKzxoFQ== + dependencies: + clone-deep "^4.0.1" + loader-utils "^1.2.3" + neo-async "^2.6.1" + schema-utils "^2.6.1" + semver "^6.3.0" + sax@>=0.6.0, sax@^1.2.4, sax@~1.2.4: version "1.2.4" resolved "https://registry.yarnpkg.com/sax/-/sax-1.2.4.tgz#2816234e2378bddc4e5354fab5caa895df7100d9" @@ -13282,6 +13302,14 @@ schema-utils@^2.0.0, schema-utils@^2.0.1, schema-utils@^2.6.0: ajv "^6.10.2" ajv-keywords "^3.4.1" +schema-utils@^2.6.1: + version "2.6.4" + resolved "https://registry.yarnpkg.com/schema-utils/-/schema-utils-2.6.4.tgz#a27efbf6e4e78689d91872ee3ccfa57d7bdd0f53" + integrity sha512-VNjcaUxVnEeun6B2fiiUDjXXBtD4ZSH7pdbfIu1pOFwgptDPLMo/z9jr4sUfsjFVPqDCEin/F7IYlq7/E6yDbQ== + dependencies: + ajv "^6.10.2" + ajv-keywords "^3.4.1" + scss-tokenizer@^0.2.3: version "0.2.3" resolved "https://registry.yarnpkg.com/scss-tokenizer/-/scss-tokenizer-0.2.3.tgz#8eb06db9a9723333824d3f5530641149847ce5d1" @@ -13439,6 +13467,13 @@ shallow-clone@^0.1.2: lazy-cache "^0.2.3" mixin-object "^2.0.1" +shallow-clone@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/shallow-clone/-/shallow-clone-3.0.1.tgz#8f2981ad92531f55035b01fb230769a40e02efa3" + integrity sha512-/6KqX+GVUdqPuPPd2LxDDxzX6CAbjJehAAOKlNpqqUpAqPM6HeL8f+o3a+JsyGjn2lv0WY8UsTgUJjU9Ok55NA== + dependencies: + kind-of "^6.0.2" + shebang-command@^1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/shebang-command/-/shebang-command-1.2.0.tgz#44aac65b695b03398968c39f363fee5deafdf1ea" From 6877b9945395dda4e1bbb1597841043abe4f2af7 Mon Sep 17 00:00:00 2001 From: Tim Neutkens Date: Sun, 19 Jan 2020 12:53:33 +0100 Subject: [PATCH 03/34] Fix failing tests --- test/integration/scss/test/index.test.js | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/test/integration/scss/test/index.test.js b/test/integration/scss/test/index.test.js index 59c698114427c..cf6ef28ce989f 100644 --- a/test/integration/scss/test/index.test.js +++ b/test/integration/scss/test/index.test.js @@ -217,7 +217,7 @@ describe('SCSS Support', () => { stderr: true, }) expect(stderr).toContain('Failed to compile') - expect(stderr).toContain('styles.module.css') + expect(stderr).toContain('styles.module.scss') expect(stderr).toMatch( /CSS.*cannot.*be imported within.*pages[\\/]_document\.js/ ) @@ -237,7 +237,7 @@ describe('SCSS Support', () => { stderr: true, }) expect(stderr).toContain('Failed to compile') - expect(stderr).toContain('styles/global.css') + expect(stderr).toContain('styles/global.scss') expect(stderr).toMatch( /Please move all global CSS imports.*?pages(\/|\\)_app/ ) @@ -257,7 +257,7 @@ describe('SCSS Support', () => { stderr: true, }) expect(stderr).toContain('Failed to compile') - expect(stderr).toContain('styles/global.css') + expect(stderr).toContain('styles/global.scss') expect(stderr).toMatch( /Please move all global CSS imports.*?pages(\/|\\)_app/ ) @@ -277,7 +277,7 @@ describe('SCSS Support', () => { stderr: true, }) expect(stderr).toContain('Failed to compile') - expect(stderr).toContain('styles/global.css') + expect(stderr).toContain('styles/global.scss') expect(stderr).toContain('Please move all global CSS imports') expect(stderr).toMatch(/Location:.*pages[\\/]index\.js/) }) @@ -317,7 +317,7 @@ describe('SCSS Support', () => { ) expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) - const cssFile = new File(join(appDir, 'styles/global1.css')) + const cssFile = new File(join(appDir, 'styles/global1.scss')) try { cssFile.replace('color: red', 'color: purple') await waitFor(2000) // wait for HMR From 7302fed0047cc1d3d441fccef5dcc9708675370b Mon Sep 17 00:00:00 2001 From: Tim Neutkens Date: Sun, 19 Jan 2020 13:09:30 +0100 Subject: [PATCH 04/34] Fix url-loader tests --- packages/next/build/webpack/config/blocks/css/index.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index 8f050419cc704..72d55ca12cce2 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -427,7 +427,7 @@ export const css = curry(async function css( oneOf: [ { // This should only be applied to CSS files - issuer: { test: /\.css$/ }, + issuer: { test: /\.(css|scss|sass)$/ }, // Exclude extensions that webpack handles by default exclude: [/\.(js|mjs|jsx|ts|tsx)$/, /\.html$/, /\.json$/], use: { From 11ce9033d12ce23a375f3f31f8f79712917f138e Mon Sep 17 00:00:00 2001 From: Tim Neutkens Date: Sun, 19 Jan 2020 13:14:28 +0100 Subject: [PATCH 05/34] Remove css file generated by tests --- test/integration/scss-fixtures/multi-page/styles/global1.css | 1 - 1 file changed, 1 deletion(-) delete mode 100644 test/integration/scss-fixtures/multi-page/styles/global1.css diff --git a/test/integration/scss-fixtures/multi-page/styles/global1.css b/test/integration/scss-fixtures/multi-page/styles/global1.css deleted file mode 100644 index ec747fa47ddb8..0000000000000 --- a/test/integration/scss-fixtures/multi-page/styles/global1.css +++ /dev/null @@ -1 +0,0 @@ -null \ No newline at end of file From 952aba6d98978055ef315b3aeb1f083787d5604d Mon Sep 17 00:00:00 2001 From: Tim Neutkens Date: Sun, 19 Jan 2020 16:05:10 +0100 Subject: [PATCH 06/34] Fix nprogress import for css file --- test/integration/scss-fixtures/npm-import/styles/global.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/integration/scss-fixtures/npm-import/styles/global.scss b/test/integration/scss-fixtures/npm-import/styles/global.scss index a3bfbdf7d6700..a369dafd92cc4 100644 --- a/test/integration/scss-fixtures/npm-import/styles/global.scss +++ b/test/integration/scss-fixtures/npm-import/styles/global.scss @@ -1 +1 @@ -@import '~nprogress/nprogress.scss'; +@import '~nprogress/nprogress.css'; From cd23277fd9ae3a3a455a27d7942bdecd26ca8707 Mon Sep 17 00:00:00 2001 From: Tim Neutkens Date: Sun, 19 Jan 2020 16:44:34 +0100 Subject: [PATCH 07/34] Fix SCSS modules (still 2 tests that need investigating) --- .../blocks/css/getCssModuleLocalIdent.ts | 8 +- .../scss-modules/test/index.test.js | 400 ++++++++++++++++++ 2 files changed, 406 insertions(+), 2 deletions(-) create mode 100644 test/integration/scss-modules/test/index.test.js diff --git a/packages/next/build/webpack/config/blocks/css/getCssModuleLocalIdent.ts b/packages/next/build/webpack/config/blocks/css/getCssModuleLocalIdent.ts index e85e9f93957c1..e2a91edd1050c 100644 --- a/packages/next/build/webpack/config/blocks/css/getCssModuleLocalIdent.ts +++ b/packages/next/build/webpack/config/blocks/css/getCssModuleLocalIdent.ts @@ -15,8 +15,12 @@ export function getCssModuleLocalIdent( // Generate a more meaningful name (parent folder) when the user names the // file `index.module.css`. const fileNameOrFolder = - relativePath.endsWith('index.module.css') && - relativePath !== 'pages/index.module.css' + (relativePath.endsWith('index.module.css') || + relativePath.endsWith('index.module.scss') || + relativePath.endsWith('index.module.sass')) && + relativePath !== 'pages/index.module.css' && + relativePath !== 'pages/index.module.scss' && + relativePath !== 'pages/index.module.sass' ? '[folder]' : '[name]' diff --git a/test/integration/scss-modules/test/index.test.js b/test/integration/scss-modules/test/index.test.js new file mode 100644 index 0000000000000..242d4eb38762e --- /dev/null +++ b/test/integration/scss-modules/test/index.test.js @@ -0,0 +1,400 @@ +/* eslint-env jest */ +/* global jasmine */ +import { join } from 'path' +import { remove, readFile, readdir } from 'fs-extra' +import { + nextBuild, + nextStart, + findPort, + killApp, + launchApp, + waitFor, + renderViaHTTP, +} from 'next-test-utils' +import cheerio from 'cheerio' +import webdriver from 'next-webdriver' + +jasmine.DEFAULT_TIMEOUT_INTERVAL = 1000 * 60 * 1 + +const fixturesDir = join(__dirname, '../../scss-fixtures') + +describe('SCSS modules', () => { + describe('Basic CSS Module Support', () => { + const appDir = join(fixturesDir, 'basic-module') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot(`".index_redText__2VIiM{color:red}"`) + }) + + it(`should've injected the CSS on server render`, async () => { + const content = await renderViaHTTP(appPort, '/') + const $ = cheerio.load(content) + + const cssPreload = $('link[rel="preload"][as="style"]') + expect(cssPreload.length).toBe(1) + expect(cssPreload.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + + const cssSheet = $('link[rel="stylesheet"]') + expect(cssSheet.length).toBe(1) + expect(cssSheet.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + + expect($('#verify-red').attr('class')).toMatchInlineSnapshot( + `"index_redText__2VIiM"` + ) + }) + }) + + describe('3rd Party CSS Module Support', () => { + const appDir = join(fixturesDir, '3rd-party-module') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot( + `".index_foo__9_fxH{position:relative}.index_foo__9_fxH .bar,.index_foo__9_fxH .baz{height:100%;overflow:hidden}.index_foo__9_fxH .lol,.index_foo__9_fxH>.lel{width:80%}"` + ) + }) + + it(`should've injected the CSS on server render`, async () => { + const content = await renderViaHTTP(appPort, '/') + const $ = cheerio.load(content) + + const cssPreload = $('link[rel="preload"][as="style"]') + expect(cssPreload.length).toBe(1) + expect(cssPreload.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + + const cssSheet = $('link[rel="stylesheet"]') + expect(cssSheet.length).toBe(1) + expect(cssSheet.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + + expect($('#verify-div').attr('class')).toMatchInlineSnapshot( + `"index_foo__9_fxH"` + ) + }) + }) + + describe('Has CSS Module in computed styles in Development', () => { + const appDir = join(fixturesDir, 'dev-module') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should have CSS for page', async () => { + const browser = await webdriver(appPort, '/') + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('#verify-red')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) + }) + }) + + describe('Has CSS Module in computed styles in Production', () => { + const appDir = join(fixturesDir, 'prod-module') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it('should have CSS for page', async () => { + const browser = await webdriver(appPort, '/') + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('#verify-red')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) + }) + }) + + xdescribe('Can hot reload CSS Module without losing state', () => { + const appDir = join(fixturesDir, 'hmr-module') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + // FIXME: this is broken + it('should update CSS color without remounting ', async () => { + const browser = await webdriver(appPort, '/') + await waitFor(2000) // ensure application hydrates + + const desiredText = 'hello world' + await browser.elementById('text-input').type(desiredText) + expect(await browser.elementById('text-input').getValue()).toBe( + desiredText + ) + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('#verify-red')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) + + const cssFile = new File(join(appDir, 'pages/index.module.scss')) + try { + cssFile.replace('color: red', 'color: purple') + await waitFor(2000) // wait for HMR + + const refreshedColor = await browser.eval( + `window.getComputedStyle(document.querySelector('#verify-red')).color` + ) + expect(refreshedColor).toMatchInlineSnapshot(`"rgb(128, 0, 128)"`) + + // ensure text remained + expect(await browser.elementById('text-input').getValue()).toBe( + desiredText + ) + } finally { + cssFile.restore() + } + }) + }) + + describe('Invalid CSS Module Usage in node_modules', () => { + const appDir = join(fixturesDir, 'invalid-module') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should fail to build', async () => { + const { stderr } = await nextBuild(appDir, [], { + stderr: true, + }) + expect(stderr).toContain('Failed to compile') + expect(stderr).toContain('node_modules/example/index.module.scss') + expect(stderr).toMatch( + /CSS Modules.*cannot.*be imported from within.*node_modules/ + ) + expect(stderr).toMatch( + /Location:.*node_modules[\\/]example[\\/]index\.mjs/ + ) + }) + }) + + describe('Invalid CSS Module Usage in node_modules', () => { + const appDir = join(fixturesDir, 'invalid-global-module') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + it('should fail to build', async () => { + const { stderr } = await nextBuild(appDir, [], { + stderr: true, + }) + expect(stderr).toContain('Failed to compile') + expect(stderr).toContain('node_modules/example/index.scss') + expect(stderr).toMatch( + /Global CSS.*cannot.*be imported from within.*node_modules/ + ) + expect(stderr).toMatch( + /Location:.*node_modules[\\/]example[\\/]index\.mjs/ + ) + }) + }) + + describe('Valid CSS Module Usage from within node_modules', () => { + const appDir = join(fixturesDir, 'nm-module') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + let appPort + let app + beforeAll(async () => { + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it(`should've prerendered with relevant data`, async () => { + const content = await renderViaHTTP(appPort, '/') + const $ = cheerio.load(content) + + const cssPreload = $('#nm-div') + expect(cssPreload.text()).toMatchInlineSnapshot( + `"{\\"message\\":\\"Why hello there\\"} {\\"redText\\":\\"example_redText__1hNNA\\"}"` + ) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot(`".example_redText__1hNNA{color:\\"red\\"}"`) + }) + }) + + describe('Valid Nested CSS Module Usage from within node_modules', () => { + const appDir = join(fixturesDir, 'nm-module-nested') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) + + let appPort + let app + beforeAll(async () => { + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) + + it(`should've prerendered with relevant data`, async () => { + const content = await renderViaHTTP(appPort, '/') + const $ = cheerio.load(content) + + const cssPreload = $('#nm-div') + expect(cssPreload.text()).toMatchInlineSnapshot( + `"{\\"message\\":\\"Why hello there\\"} {\\"subClass\\":\\"example_subClass__2YUgj other_className__bt_-E\\"}"` + ) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot( + `".other3_other3__1f9h7{color:violet}.other_className__bt_-E{background:red;color:#ff0}.other2_other2__2PUfY{color:red}.example_subClass__2YUgj{background:#00f}"` + ) + }) + }) + + describe('CSS Module Composes Usage (Basic)', () => { + // This is a very bad feature. Do not use it. + const appDir = join(fixturesDir, 'composes-basic') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot( + `".index_className__2O8Wt{background:red;color:#ff0}.index_subClass__3e6Re{background:#00f}"` + ) + }) + }) + + describe('CSS Module Composes Usage (External)', () => { + // This is a very bad feature. Do not use it. + const appDir = join(fixturesDir, 'composes-external') + + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + }) + + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') + + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) + + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + + expect( + cssContent.replace(/\/\*.*?\*\//g, '').trim() + ).toMatchInlineSnapshot( + `".other_className__2VTl4{background:red;color:#ff0}.index_subClass__3e6Re{background:#00f}"` + ) + }) + }) +}) From 81a6a800afd95f83befdbab5f7c55a56d6fd3681 Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Sun, 19 Jan 2020 11:20:09 -0700 Subject: [PATCH 08/34] Update documentation for Sass support --- docs/basic-features/built-in-css-support.md | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/docs/basic-features/built-in-css-support.md b/docs/basic-features/built-in-css-support.md index 1bc6a1274659c..4b8f562df384a 100644 --- a/docs/basic-features/built-in-css-support.md +++ b/docs/basic-features/built-in-css-support.md @@ -157,10 +157,19 @@ export default HelloWorld Please see the [styled-jsx documentation](https://github.com/zeit/styled-jsx) for more examples. -## Sass, Less, and Stylus Support +## Sass Support -To support importing `.scss`, `.less` or `.styl` files you can use the following plugins: +To enable importing global `.scss` or `.sass` within `pages/_app.js` and component-level CSS Modules with `.module.scss` or `.module.sass` install `node-sass` as a dependency to your project: + +```bash +npm install node-sass +``` + +Sass support has the same benefits and restrictions as the built-in CSS support detailed above. + +## Less and Stylus Support + +To support importing `.less` or `.styl` files you can use the following plugins: -- [@zeit/next-sass](https://github.com/zeit/next-plugins/tree/master/packages/next-sass) - [@zeit/next-less](https://github.com/zeit/next-plugins/tree/master/packages/next-less) - [@zeit/next-stylus](https://github.com/zeit/next-plugins/tree/master/packages/next-stylus) From 380319d9d0c4bfb19e28c210262ccd82d19f3556 Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Sun, 19 Jan 2020 16:27:47 -0700 Subject: [PATCH 09/34] Fix plain CSS import test --- .../nm-module-nested/node_modules/example/index.module.scss | 2 +- .../nm-module-nested/node_modules/example/other.scss | 2 +- .../node_modules/example/{other2.scss => other2.css} | 0 .../node_modules/example/{other3.scss => other3.css} | 0 test/integration/scss-modules/test/index.test.js | 4 ++-- 5 files changed, 4 insertions(+), 4 deletions(-) rename test/integration/scss-fixtures/nm-module-nested/node_modules/example/{other2.scss => other2.css} (100%) rename test/integration/scss-fixtures/nm-module-nested/node_modules/example/{other3.scss => other3.css} (100%) diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss index aed5852ba6873..095246f28de48 100644 --- a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss @@ -1,4 +1,4 @@ -@import 'other2.scss'; +@import 'other2.css'; .subClass { composes: className from './other.scss'; diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss index d8eb83346a6ea..8882484b2304d 100644 --- a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss @@ -1,4 +1,4 @@ -@import 'other3.scss'; +@import 'other3.css'; .className { background: red; diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.css similarity index 100% rename from test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss rename to test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.css diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.css similarity index 100% rename from test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss rename to test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.css diff --git a/test/integration/scss-modules/test/index.test.js b/test/integration/scss-modules/test/index.test.js index 242d4eb38762e..94645c769bace 100644 --- a/test/integration/scss-modules/test/index.test.js +++ b/test/integration/scss-modules/test/index.test.js @@ -325,7 +325,7 @@ describe('SCSS modules', () => { const cssPreload = $('#nm-div') expect(cssPreload.text()).toMatchInlineSnapshot( - `"{\\"message\\":\\"Why hello there\\"} {\\"subClass\\":\\"example_subClass__2YUgj other_className__bt_-E\\"}"` + `"{\\"message\\":\\"Why hello there\\"} {\\"subClass\\":\\"example_subClass__2EbKX other_className__E6nd8\\"}"` ) }) @@ -341,7 +341,7 @@ describe('SCSS modules', () => { expect( cssContent.replace(/\/\*.*?\*\//g, '').trim() ).toMatchInlineSnapshot( - `".other3_other3__1f9h7{color:violet}.other_className__bt_-E{background:red;color:#ff0}.other2_other2__2PUfY{color:red}.example_subClass__2YUgj{background:#00f}"` + `".other3_other3__1f9h7{color:violet}.other_className__E6nd8{background:red;color:#ff0}.other2_other2__2PUfY{color:red}.example_subClass__2EbKX{background:#00f}"` ) }) }) From ac9288d0fd5ec663ede4a10af361d14ba0eec6cf Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Sun, 19 Jan 2020 16:42:28 -0700 Subject: [PATCH 10/34] Fix formatting with prettier fix --- .../build/webpack/config/blocks/css/getCssModuleLocalIdent.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/getCssModuleLocalIdent.ts b/packages/next/build/webpack/config/blocks/css/getCssModuleLocalIdent.ts index e2a91edd1050c..615710b70a09f 100644 --- a/packages/next/build/webpack/config/blocks/css/getCssModuleLocalIdent.ts +++ b/packages/next/build/webpack/config/blocks/css/getCssModuleLocalIdent.ts @@ -19,8 +19,8 @@ export function getCssModuleLocalIdent( relativePath.endsWith('index.module.scss') || relativePath.endsWith('index.module.sass')) && relativePath !== 'pages/index.module.css' && - relativePath !== 'pages/index.module.scss' && - relativePath !== 'pages/index.module.sass' + relativePath !== 'pages/index.module.scss' && + relativePath !== 'pages/index.module.sass' ? '[folder]' : '[name]' From 7095ed581e59290cf435efae9d8b8c1b9b90a989 Mon Sep 17 00:00:00 2001 From: Tim Neutkens Date: Mon, 20 Jan 2020 13:22:18 +0100 Subject: [PATCH 11/34] Update test output to reflect scss usage --- test/integration/scss-modules/test/index.test.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/integration/scss-modules/test/index.test.js b/test/integration/scss-modules/test/index.test.js index 242d4eb38762e..5432b55a8f6ec 100644 --- a/test/integration/scss-modules/test/index.test.js +++ b/test/integration/scss-modules/test/index.test.js @@ -325,7 +325,7 @@ describe('SCSS modules', () => { const cssPreload = $('#nm-div') expect(cssPreload.text()).toMatchInlineSnapshot( - `"{\\"message\\":\\"Why hello there\\"} {\\"subClass\\":\\"example_subClass__2YUgj other_className__bt_-E\\"}"` + `"{\\"message\\":\\"Why hello there\\"} {\\"other2\\":\\"example_other2__1pnJV\\",\\"subClass\\":\\"example_subClass__2EbKX other_className__E6nd8\\"}"` ) }) @@ -341,7 +341,7 @@ describe('SCSS modules', () => { expect( cssContent.replace(/\/\*.*?\*\//g, '').trim() ).toMatchInlineSnapshot( - `".other3_other3__1f9h7{color:violet}.other_className__bt_-E{background:red;color:#ff0}.other2_other2__2PUfY{color:red}.example_subClass__2YUgj{background:#00f}"` + `".other_other3__ZPN-Y{color:violet}.other_className__E6nd8{background:red;color:#ff0}.example_other2__1pnJV{color:red}.example_subClass__2EbKX{background:#00f}"` ) }) }) From bd25e8ebb7b61ccd09fe15c4ed6a1a8c0fe9c451 Mon Sep 17 00:00:00 2001 From: Tim Neutkens Date: Mon, 20 Jan 2020 13:24:16 +0100 Subject: [PATCH 12/34] Revert "Fix plain CSS import test" This reverts commit 380319d9d0c4bfb19e28c210262ccd82d19f3556. # Conflicts: # test/integration/scss-modules/test/index.test.js --- .../nm-module-nested/node_modules/example/index.module.scss | 2 +- .../nm-module-nested/node_modules/example/other.scss | 2 +- .../node_modules/example/{other2.css => other2.scss} | 0 .../node_modules/example/{other3.css => other3.scss} | 0 4 files changed, 2 insertions(+), 2 deletions(-) rename test/integration/scss-fixtures/nm-module-nested/node_modules/example/{other2.css => other2.scss} (100%) rename test/integration/scss-fixtures/nm-module-nested/node_modules/example/{other3.css => other3.scss} (100%) diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss index 095246f28de48..aed5852ba6873 100644 --- a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss @@ -1,4 +1,4 @@ -@import 'other2.css'; +@import 'other2.scss'; .subClass { composes: className from './other.scss'; diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss index 8882484b2304d..d8eb83346a6ea 100644 --- a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss @@ -1,4 +1,4 @@ -@import 'other3.css'; +@import 'other3.scss'; .className { background: red; diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.css b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss similarity index 100% rename from test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.css rename to test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.css b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss similarity index 100% rename from test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.css rename to test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss From c2715716d48d7ef18d0cbc6dd4cbde1c9bcd58ac Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Mon, 20 Jan 2020 14:18:50 -0700 Subject: [PATCH 13/34] Update loader structure * Resolve loaders before passing to compile function * Remove dead filter code * Arrange loaders in order and push to array --- .../build/webpack/config/blocks/css/index.ts | 45 ++++++++++--------- 1 file changed, 24 insertions(+), 21 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index 72d55ca12cce2..837d2267d14c3 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -136,27 +136,11 @@ export const css = curry(async function css( cssOptions: webpack.ParserOptions, preProcessor: string ) { - const loaders: webpack.RuleSetUseItem[] = [ - // Resolve CSS `@import`s and `url()`s - { - loader: require.resolve('css-loader'), - options: cssOptions, - }, - - // Compile CSS - { - loader: require.resolve('postcss-loader'), - options: { - ident: '__nextjs_postcss', - plugins: postCssPlugins, - sourceMap: true, - }, - }, - ].filter(Boolean) + const loaders: webpack.RuleSetUseItem[] = [] // Add appropriate development mode or production mode style loader first if (ctx.isClient) { - loaders.unshift( + loaders.push( getClientStyleLoader({ isDevelopment: ctx.isDevelopment, assetPrefix: ctx.assetPrefix, @@ -167,13 +151,32 @@ export const css = curry(async function css( // Add preprocessor loader if (preProcessor) { loaders.push({ - loader: require.resolve(preProcessor), + loader: preProcessor, options: { sourceMap: true, }, }) } + // Add remaining loaders + loaders.push( + // Resolve CSS `@import`s and `url()`s + { + loader: require.resolve('css-loader'), + options: cssOptions, + }, + + // Compile CSS + { + loader: require.resolve('postcss-loader'), + options: { + ident: '__nextjs_postcss', + plugins: postCssPlugins, + sourceMap: true, + }, + } + ) + return loaders } @@ -235,7 +238,7 @@ export const css = curry(async function css( getLocalIdent: getCssModuleLocalIdent, }, }, - 'sass-loader' + require.resolve('sass-loader') ), }, // Opt-in support for SASS (using .scss or .sass extensions). @@ -272,7 +275,7 @@ export const css = curry(async function css( getLocalIdent: getCssModuleLocalIdent, }, }, - 'sass-loader' + require.resolve('sass-loader') ), }, ], From 5bc4e720483deaf12caef8a67cf004bf2fc095de Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Mon, 20 Jan 2020 14:38:07 -0700 Subject: [PATCH 14/34] Fix loader order bug --- .../build/webpack/config/blocks/css/index.ts | 22 +++++++++---------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index 837d2267d14c3..f764e9b5cc54e 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -148,17 +148,7 @@ export const css = curry(async function css( ) } - // Add preprocessor loader - if (preProcessor) { - loaders.push({ - loader: preProcessor, - options: { - sourceMap: true, - }, - }) - } - - // Add remaining loaders + // Add main loaders loaders.push( // Resolve CSS `@import`s and `url()`s { @@ -177,6 +167,16 @@ export const css = curry(async function css( } ) + // Add preprocessor loader + if (preProcessor) { + loaders.push({ + loader: preProcessor, + options: { + sourceMap: true, + }, + }) + } + return loaders } From 0fa30aca8b379826318ac0e2328073a92f966ad4 Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Mon, 20 Jan 2020 18:39:29 -0700 Subject: [PATCH 15/34] Fix global Sass loader and make module prepocessor optional --- .../build/webpack/config/blocks/css/index.ts | 45 ++++++++++--------- 1 file changed, 25 insertions(+), 20 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index f764e9b5cc54e..2eb8df548aed5 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -134,7 +134,7 @@ export const css = curry(async function css( function getModuleStyleLoader( cssOptions: webpack.ParserOptions, - preProcessor: string + preProcessor?: string ) { const loaders: webpack.RuleSetUseItem[] = [] @@ -221,25 +221,22 @@ export const css = curry(async function css( exclude: /node_modules/, }, - use: getModuleStyleLoader( - { - importLoaders: 1, - sourceMap: true, - onlyLocals: ctx.isServer, - modules: { - // Disallow global style exports so we can code-split CSS and - // not worry about loading order. - mode: 'pure', - // Generate a friendly production-ready name so it's - // reasonably understandable. The same name is used for - // development. - // TODO: Consider making production reduce this to a single - // character? - getLocalIdent: getCssModuleLocalIdent, - }, + use: getModuleStyleLoader({ + importLoaders: 1, + sourceMap: true, + onlyLocals: ctx.isServer, + modules: { + // Disallow global style exports so we can code-split CSS and + // not worry about loading order. + mode: 'pure', + // Generate a friendly production-ready name so it's + // reasonably understandable. The same name is used for + // development. + // TODO: Consider making production reduce this to a single + // character? + getLocalIdent: getCssModuleLocalIdent, }, - require.resolve('sass-loader') - ), + }), }, // Opt-in support for SASS (using .scss or .sass extensions). // By default we support SASS Modules with the @@ -365,7 +362,7 @@ export const css = curry(async function css( // Resolve CSS `@import`s and `url()`s { loader: require.resolve('css-loader'), - options: { importLoaders: 1, sourceMap: true }, + options: { importLoaders: 2, sourceMap: true }, }, // Compile CSS @@ -377,6 +374,14 @@ export const css = curry(async function css( sourceMap: true, }, }, + + // Preprocess Sass + { + loader: require.resolve('sass-loader'), + options: { + sourceMap: true, + }, + }, ], }, ], From c0fb9368fc07f8ccc2c7dc372da9b0f65d1c2b5e Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 11:16:52 -0500 Subject: [PATCH 16/34] Adjust Sass Modules Implementation --- .../build/webpack/config/blocks/css/index.ts | 132 +++++---------- .../config/blocks/css/loaders/modules.ts | 11 +- packages/next/package.json | 1 + yarn.lock | 151 +++++++++++++++++- 4 files changed, 191 insertions(+), 104 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index 5c7ec76a6addd..eed4184cb483d 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -1,12 +1,11 @@ import curry from 'lodash.curry' import path from 'path' -import webpack, { Configuration } from 'webpack' +import { Configuration } from 'webpack' import MiniCssExtractPlugin from '../../../plugins/mini-css-extract-plugin' import { loader, plugin } from '../../helpers' import { ConfigurationContext, ConfigurationFn, pipe } from '../../utils' -import { getGlobalCssLoader } from './loaders' +import { getCssModuleLoader, getGlobalCssLoader } from './loaders' import { getClientStyleLoader } from './loaders/client' -import { getCssModuleLocalIdent } from './loaders/getCssModuleLocalIdent' import { getCustomDocumentError, getGlobalImportError, @@ -15,11 +14,14 @@ import { } from './messages' import { getPostCssPlugins } from './plugins' -// RegExps for Stylesheets +// RegExps for Style Sheets // const regexCssAll = /\.css$/ const regexCssGlobal = /(? Date: Wed, 22 Jan 2020 11:18:53 -0500 Subject: [PATCH 17/34] Fix typo --- packages/next/build/webpack/config/blocks/css/index.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index eed4184cb483d..4b57f68a2d91f 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -53,7 +53,7 @@ export const css = curry(async function css( true ) - // CSS cannot be imported in _document. This comes before everything b ecause + // CSS cannot be imported in _document. This comes before everything because // global CSS nor CSS modules work in said file. fns.push( loader({ From 4cb6e9bffd34cfc44702a1d09be6303599a914aa Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 11:20:51 -0500 Subject: [PATCH 18/34] Adjust regexps --- packages/next/build/webpack/config/blocks/css/index.ts | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index 4b57f68a2d91f..d57c8282d1c6b 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -14,13 +14,15 @@ import { } from './messages' import { getPostCssPlugins } from './plugins' +// RegExps for all Style Sheet variants +const regexLikeCss = /\.(css|scss|sass)$/ + // RegExps for Style Sheets -// const regexCssAll = /\.css$/ const regexCssGlobal = /(? Date: Wed, 22 Jan 2020 11:24:22 -0500 Subject: [PATCH 19/34] Use regexes --- packages/next/build/webpack/config/blocks/css/index.ts | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index d57c8282d1c6b..8b42ff8a237e4 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -22,6 +22,7 @@ const regexCssGlobal = /(? Date: Wed, 22 Jan 2020 11:27:55 -0500 Subject: [PATCH 20/34] Simplify global setup --- .../build/webpack/config/blocks/css/index.ts | 89 ++++++------------- .../config/blocks/css/loaders/global.ts | 11 ++- 2 files changed, 38 insertions(+), 62 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index 8b42ff8a237e4..7ca81d268b697 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -1,11 +1,10 @@ import curry from 'lodash.curry' import path from 'path' -import { Configuration } from 'webpack' +import webpack, { Configuration } from 'webpack' import MiniCssExtractPlugin from '../../../plugins/mini-css-extract-plugin' import { loader, plugin } from '../../helpers' import { ConfigurationContext, ConfigurationFn, pipe } from '../../utils' import { getCssModuleLoader, getGlobalCssLoader } from './loaders' -import { getClientStyleLoader } from './loaders/client' import { getCustomDocumentError, getGlobalImportError, @@ -34,6 +33,29 @@ export const css = curry(async function css( return config } + const sassPreprocessors: webpack.RuleSetUseItem[] = [ + { + loader: require.resolve('sass-loader'), + options: { + // Source maps are required so that `resolve-url-loader` can + // locate files original to their source directory. + sourceMap: true, + }, + }, + // `sass-loader` will pass-through CSS imports as-is instead of + // inlining them. Once inlined, the paths are no longer correct. + // To fix this, we use `resolve-url-loader` to rewrite the CSS + // imports to real file paths. + { + loader: require.resolve('resolve-url-loader'), + options: { + // Source maps are not required here, but we may as well emit + // them. + sourceMap: true, + }, + }, + ] + const fns: ConfigurationFn[] = [ loader({ oneOf: [ @@ -114,28 +136,7 @@ export const css = curry(async function css( include: [ctx.rootDirectory], exclude: /node_modules/, }, - use: getCssModuleLoader(ctx, postCssPlugins, [ - { - loader: require.resolve('sass-loader'), - options: { - // Source maps are required so that `resolve-url-loader` can - // locate files original to their source directory. - sourceMap: true, - }, - }, - // `sass-loader` will pass-through CSS imports as-is instead of - // inlining them. Once inlined, the paths are no longer correct. - // To fix this, we use `resolve-url-loader` to rewrite the CSS - // imports to real file paths. - { - loader: require.resolve('resolve-url-loader'), - options: { - // Source maps are not required here, but we may as well emit - // them. - sourceMap: true, - }, - }, - ]), + use: getCssModuleLoader(ctx, postCssPlugins, sassPreprocessors), }, ], }) @@ -181,46 +182,14 @@ export const css = curry(async function css( use: getGlobalCssLoader(ctx, postCssPlugins), }, { - // A global CSS import always has side effects. Webpack will tree - // shake the CSS without this option if the issuer claims to have + // A global Sass import always has side effects. Webpack will tree + // shake the Sass without this option if the issuer claims to have // no side-effects. // See https://github.com/webpack/webpack/issues/6571 sideEffects: true, - test: /\.(scss|sass)$/, + test: regexSassGlobal, issuer: { include: ctx.customAppFile }, - - use: [ - // Add appropriate development more or production mode style - // loader - getClientStyleLoader({ - isDevelopment: ctx.isDevelopment, - assetPrefix: ctx.assetPrefix, - }), - - // Resolve CSS `@import`s and `url()`s - { - loader: require.resolve('css-loader'), - options: { importLoaders: 2, sourceMap: true }, - }, - - // Compile CSS - { - loader: require.resolve('postcss-loader'), - options: { - ident: '__nextjs_postcss', - plugins: postCssPlugins, - sourceMap: true, - }, - }, - - // Preprocess Sass - { - loader: require.resolve('sass-loader'), - options: { - sourceMap: true, - }, - }, - ], + use: getGlobalCssLoader(ctx, postCssPlugins, sassPreprocessors), }, ], }) diff --git a/packages/next/build/webpack/config/blocks/css/loaders/global.ts b/packages/next/build/webpack/config/blocks/css/loaders/global.ts index 133ea5e68120a..a5dcf146ff130 100644 --- a/packages/next/build/webpack/config/blocks/css/loaders/global.ts +++ b/packages/next/build/webpack/config/blocks/css/loaders/global.ts @@ -5,7 +5,8 @@ import { getClientStyleLoader } from './client' export function getGlobalCssLoader( ctx: ConfigurationContext, - postCssPlugins: postcss.AcceptedPlugin[] + postCssPlugins: postcss.AcceptedPlugin[], + preProcessors: webpack.RuleSetUseItem[] = [] ): webpack.RuleSetUseItem[] { const loaders: webpack.RuleSetUseItem[] = [] @@ -23,7 +24,7 @@ export function getGlobalCssLoader( // Resolve CSS `@import`s and `url()`s loaders.push({ loader: require.resolve('css-loader'), - options: { importLoaders: 1, sourceMap: true }, + options: { importLoaders: 1 + preProcessors.length, sourceMap: true }, }) // Compile CSS @@ -36,5 +37,11 @@ export function getGlobalCssLoader( }, }) + loaders.push( + // Webpack loaders run like a stack, so we need to reverse the natural + // order of preprocessors. + ...preProcessors.reverse() + ) + return loaders } From ba5e73f5627c87cf26b32d1afbbaa130f099fb57 Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 11:30:21 -0500 Subject: [PATCH 21/34] Adjust comments --- .../next/build/webpack/config/blocks/css/index.ts | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index 7ca81d268b697..a02dc5a7a9bd5 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -34,16 +34,19 @@ export const css = curry(async function css( } const sassPreprocessors: webpack.RuleSetUseItem[] = [ + // First, process files with `sass-loader`: this inlines content, and + // compiles away the proprietary syntax. { loader: require.resolve('sass-loader'), options: { - // Source maps are required so that `resolve-url-loader` can - // locate files original to their source directory. + // Source maps are required so that `resolve-url-loader` can locate + // files original to their source directory. sourceMap: true, }, }, - // `sass-loader` will pass-through CSS imports as-is instead of - // inlining them. Once inlined, the paths are no longer correct. + // Then, `sass-loader` will have passed-through CSS imports as-is instead + // of inlining them. Because they were inlined, the paths are no longer + // correct. // To fix this, we use `resolve-url-loader` to rewrite the CSS // imports to real file paths. { From 711837bdae0082b73c0af207a6dfe5f14945cce1 Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 11:46:21 -0500 Subject: [PATCH 22/34] fix regex --- packages/next/build/webpack/config/blocks/css/index.ts | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index a02dc5a7a9bd5..aa866c1d71b6d 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -166,7 +166,10 @@ export const css = curry(async function css( fns.push( loader({ oneOf: [ - { test: /\.(css|scss|sass)$/, use: require.resolve('ignore-loader') }, + { + test: [regexCssGlobal, regexSassGlobal], + use: require.resolve('ignore-loader'), + }, ], }) ) From dca6b50c735356e2d48cd526f7c6fe903bd206e4 Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 13:27:53 -0500 Subject: [PATCH 23/34] Simplify identifier file --- .../blocks/css/loaders/getCssModuleLocalIdent.ts | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/packages/next/build/webpack/config/blocks/css/loaders/getCssModuleLocalIdent.ts b/packages/next/build/webpack/config/blocks/css/loaders/getCssModuleLocalIdent.ts index 615710b70a09f..168574bab0575 100644 --- a/packages/next/build/webpack/config/blocks/css/loaders/getCssModuleLocalIdent.ts +++ b/packages/next/build/webpack/config/blocks/css/loaders/getCssModuleLocalIdent.ts @@ -2,6 +2,8 @@ import loaderUtils from 'loader-utils' import path from 'path' import webpack from 'webpack' +const regexLikeIndexModule = /(? Date: Wed, 22 Jan 2020 13:32:57 -0500 Subject: [PATCH 24/34] Update Sass Instructions --- docs/basic-features/built-in-css-support.md | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/docs/basic-features/built-in-css-support.md b/docs/basic-features/built-in-css-support.md index 4b8f562df384a..62425b01e4919 100644 --- a/docs/basic-features/built-in-css-support.md +++ b/docs/basic-features/built-in-css-support.md @@ -159,10 +159,13 @@ Please see the [styled-jsx documentation](https://github.com/zeit/styled-jsx) fo ## Sass Support -To enable importing global `.scss` or `.sass` within `pages/_app.js` and component-level CSS Modules with `.module.scss` or `.module.sass` install `node-sass` as a dependency to your project: +Next.js allows you to import Sass using both the `.scss` and `.sass` extensions. +You can use component-level Sass via CSS Modules and the `.module.scss` or `.module.sass` extension. + +Before you can use Next.js' built-in Sass support, be sure to install [`sass`](https://github.com/sass/sass): ```bash -npm install node-sass +npm install sass ``` Sass support has the same benefits and restrictions as the built-in CSS support detailed above. From 251d5f82dd77db8a69265d4587c76bb879559636 Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 13:52:01 -0500 Subject: [PATCH 25/34] Remove unneeded fixtures --- .../.postcssrc.json | 3 --- .../bad-custom-configuration-arr-1/pages/_app.js | 12 ------------ .../pages/index.js | 3 --- .../styles/global.scss | 14 -------------- .../.postcssrc.json | 3 --- .../bad-custom-configuration-arr-2/pages/_app.js | 12 ------------ .../pages/index.js | 3 --- .../styles/global.scss | 14 -------------- .../.postcssrc.json | 3 --- .../bad-custom-configuration-arr-3/pages/_app.js | 12 ------------ .../pages/index.js | 3 --- .../styles/global.scss | 14 -------------- .../.postcssrc.json | 3 --- .../bad-custom-configuration-arr-4/pages/_app.js | 12 ------------ .../pages/index.js | 3 --- .../styles/global.scss | 14 -------------- .../.postcssrc.json | 3 --- .../bad-custom-configuration-arr-5/pages/_app.js | 12 ------------ .../pages/index.js | 3 --- .../styles/global.scss | 14 -------------- .../.postcssrc.json | 1 - .../bad-custom-configuration-arr-6/pages/_app.js | 12 ------------ .../pages/index.js | 3 --- .../styles/global.scss | 14 -------------- .../.postcssrc.json | 3 --- .../bad-custom-configuration-arr-7/pages/_app.js | 12 ------------ .../pages/index.js | 3 --- .../styles/global.scss | 14 -------------- .../bad-custom-configuration-arr-8/pages/_app.js | 12 ------------ .../pages/index.js | 3 --- .../postcss.config.js | 3 --- .../styles/global.scss | 14 -------------- .../bad-custom-configuration-func/pages/_app.js | 12 ------------ .../bad-custom-configuration-func/pages/index.js | 3 --- .../postcss.config.js | 3 --- .../styles/global.scss | 4 ---- .../bad-custom-configuration/.postcssrc.json | 13 ------------- .../bad-custom-configuration/pages/_app.js | 12 ------------ .../bad-custom-configuration/pages/index.js | 3 --- .../bad-custom-configuration/styles/global.scss | 4 ---- .../custom-configuration-arr/.postcssrc.json | 16 ---------------- .../custom-configuration-arr/pages/_app.js | 12 ------------ .../custom-configuration-arr/pages/index.js | 3 --- .../custom-configuration-arr/styles/global.scss | 14 -------------- .../custom-configuration-legacy/next.config.js | 15 --------------- .../custom-configuration-legacy/pages/_app.js | 12 ------------ .../custom-configuration-legacy/pages/index.js | 3 --- .../postcss.config.js | 10 ---------- .../styles/global.scss | 11 ----------- .../custom-configuration/.postcssrc.json | 11 ----------- .../custom-configuration/pages/_app.js | 12 ------------ .../custom-configuration/pages/index.js | 3 --- .../custom-configuration/styles/global.scss | 11 ----------- 53 files changed, 441 deletions(-) delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-1/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-1/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-2/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-2/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-3/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-3/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-4/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-4/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-5/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-5/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-6/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-6/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-7/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-7/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-8/postcss.config.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-arr-8/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-func/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-func/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-func/postcss.config.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration-func/styles/global.scss delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration/pages/_app.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration/pages/index.js delete mode 100644 test/integration/scss-fixtures/bad-custom-configuration/styles/global.scss delete mode 100644 test/integration/scss-fixtures/custom-configuration-arr/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/custom-configuration-arr/pages/_app.js delete mode 100644 test/integration/scss-fixtures/custom-configuration-arr/pages/index.js delete mode 100644 test/integration/scss-fixtures/custom-configuration-arr/styles/global.scss delete mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/next.config.js delete mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/pages/_app.js delete mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/pages/index.js delete mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/postcss.config.js delete mode 100644 test/integration/scss-fixtures/custom-configuration-legacy/styles/global.scss delete mode 100644 test/integration/scss-fixtures/custom-configuration/.postcssrc.json delete mode 100644 test/integration/scss-fixtures/custom-configuration/pages/_app.js delete mode 100644 test/integration/scss-fixtures/custom-configuration/pages/index.js delete mode 100644 test/integration/scss-fixtures/custom-configuration/styles/global.scss diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/.postcssrc.json deleted file mode 100644 index ab27508fd95ca..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/.postcssrc.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "plugins": [["postcss-trolling"]] -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-1/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-1/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/.postcssrc.json deleted file mode 100644 index c6df57bdda0fa..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/.postcssrc.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "plugins": [["postcss-trolling", null]] -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-2/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-2/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/.postcssrc.json deleted file mode 100644 index e886576085efd..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/.postcssrc.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "plugins": [[5, null]] -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-3/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-3/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/.postcssrc.json deleted file mode 100644 index 05e159725dc23..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/.postcssrc.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "plugins": [5] -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-4/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-4/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/.postcssrc.json deleted file mode 100644 index 1e02e994a48d5..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/.postcssrc.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "plugins": null -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-5/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-5/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/.postcssrc.json deleted file mode 100644 index 0967ef424bce6..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/.postcssrc.json +++ /dev/null @@ -1 +0,0 @@ -{} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-6/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-6/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/.postcssrc.json deleted file mode 100644 index 561d0cb76ddf9..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/.postcssrc.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "plugins": [["postcss-trolling", 5]] -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-7/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-7/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/postcss.config.js b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/postcss.config.js deleted file mode 100644 index 5f1f2140125eb..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/postcss.config.js +++ /dev/null @@ -1,3 +0,0 @@ -module.exports = { - plugins: [require('postcss-trolling')], -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-arr-8/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-arr-8/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-func/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration-func/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-func/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration-func/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration-func/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-func/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-func/postcss.config.js b/test/integration/scss-fixtures/bad-custom-configuration-func/postcss.config.js deleted file mode 100644 index 9bf5d079edf9b..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-func/postcss.config.js +++ /dev/null @@ -1,3 +0,0 @@ -module.exports = function() { - return { plugins: [] } -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration-func/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration-func/styles/global.scss deleted file mode 100644 index e535e1983057d..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration-func/styles/global.scss +++ /dev/null @@ -1,4 +0,0 @@ -/* this should be transformed to width/height */ -.video { - max-size: 400px 300px; -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration/.postcssrc.json b/test/integration/scss-fixtures/bad-custom-configuration/.postcssrc.json deleted file mode 100644 index 8c058dc78d1e0..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration/.postcssrc.json +++ /dev/null @@ -1,13 +0,0 @@ -{ - "sourceMap": false, - "plugins": { - "postcss-modules-extract-imports": {}, - "postcss-modules-local-by-default": {}, - "postcss-modules-scope": {}, - "postcss-modules-values": {}, - "postcss-modules": {}, - - // Test a non-standard feature that wouldn't be normally enabled - "postcss-short-size": {} - } -} diff --git a/test/integration/scss-fixtures/bad-custom-configuration/pages/_app.js b/test/integration/scss-fixtures/bad-custom-configuration/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/bad-custom-configuration/pages/index.js b/test/integration/scss-fixtures/bad-custom-configuration/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/bad-custom-configuration/styles/global.scss b/test/integration/scss-fixtures/bad-custom-configuration/styles/global.scss deleted file mode 100644 index e535e1983057d..0000000000000 --- a/test/integration/scss-fixtures/bad-custom-configuration/styles/global.scss +++ /dev/null @@ -1,4 +0,0 @@ -/* this should be transformed to width/height */ -.video { - max-size: 400px 300px; -} diff --git a/test/integration/scss-fixtures/custom-configuration-arr/.postcssrc.json b/test/integration/scss-fixtures/custom-configuration-arr/.postcssrc.json deleted file mode 100644 index def6136b4cdc8..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-arr/.postcssrc.json +++ /dev/null @@ -1,16 +0,0 @@ -{ - // Use comments to test JSON5 support - "plugins": [ - "pixrem", - ["postcss-pseudoelements", true], - // Test a non-standard feature that wouldn't be normally enabled - [ - "postcss-short-size", - { - // Add a prefix to test that configuration is passed - "prefix": "xyz" - } - ], - ["postcss-trolling", false] - ] -} diff --git a/test/integration/scss-fixtures/custom-configuration-arr/pages/_app.js b/test/integration/scss-fixtures/custom-configuration-arr/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-arr/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/custom-configuration-arr/pages/index.js b/test/integration/scss-fixtures/custom-configuration-arr/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-arr/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/custom-configuration-arr/styles/global.scss b/test/integration/scss-fixtures/custom-configuration-arr/styles/global.scss deleted file mode 100644 index 78d27f7edd8e4..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-arr/styles/global.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - a::before { - content: ''; - } - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400rem 300rem; -} diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/next.config.js b/test/integration/scss-fixtures/custom-configuration-legacy/next.config.js deleted file mode 100644 index 93bc6a48f6b17..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-legacy/next.config.js +++ /dev/null @@ -1,15 +0,0 @@ -const withCSS = require('@zeit/next-css') - -module.exports = withCSS({ - onDemandEntries: { - // Make sure entries are not getting disposed. - maxInactiveAge: 1000 * 60 * 60, - }, - experimental: { - css: true, - }, - webpack(cfg) { - cfg.devtool = 'source-map' - return cfg - }, -}) diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/pages/_app.js b/test/integration/scss-fixtures/custom-configuration-legacy/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-legacy/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/pages/index.js b/test/integration/scss-fixtures/custom-configuration-legacy/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-legacy/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/postcss.config.js b/test/integration/scss-fixtures/custom-configuration-legacy/postcss.config.js deleted file mode 100644 index c7b7fde03c78c..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-legacy/postcss.config.js +++ /dev/null @@ -1,10 +0,0 @@ -module.exports = { - // Use comments to test JSON5 support - plugins: [ - // Test a non-standard feature that wouldn't be normally enabled - require('postcss-short-size')({ - // Add a prefix to test that configuration is passed - prefix: 'xyz', - }), - ], -} diff --git a/test/integration/scss-fixtures/custom-configuration-legacy/styles/global.scss b/test/integration/scss-fixtures/custom-configuration-legacy/styles/global.scss deleted file mode 100644 index f942036ad16ef..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration-legacy/styles/global.scss +++ /dev/null @@ -1,11 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400px 300px; -} diff --git a/test/integration/scss-fixtures/custom-configuration/.postcssrc.json b/test/integration/scss-fixtures/custom-configuration/.postcssrc.json deleted file mode 100644 index 21cd2f23012bd..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration/.postcssrc.json +++ /dev/null @@ -1,11 +0,0 @@ -{ - // Use comments to test JSON5 support - "plugins": { - // Test a non-standard feature that wouldn't be normally enabled - "postcss-short-size": { - // Add a prefix to test that configuration is passed - "prefix": "xyz" - }, - "postcss-trolling": false - } -} diff --git a/test/integration/scss-fixtures/custom-configuration/pages/_app.js b/test/integration/scss-fixtures/custom-configuration/pages/_app.js deleted file mode 100644 index b89fe16feb731..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration/pages/_app.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import App from 'next/app' -import '../styles/global.scss' - -class MyApp extends App { - render() { - const { Component, pageProps } = this.props - return - } -} - -export default MyApp diff --git a/test/integration/scss-fixtures/custom-configuration/pages/index.js b/test/integration/scss-fixtures/custom-configuration/pages/index.js deleted file mode 100644 index b3ba78da2d5e1..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration/pages/index.js +++ /dev/null @@ -1,3 +0,0 @@ -export default function Home() { - return
-} diff --git a/test/integration/scss-fixtures/custom-configuration/styles/global.scss b/test/integration/scss-fixtures/custom-configuration/styles/global.scss deleted file mode 100644 index f942036ad16ef..0000000000000 --- a/test/integration/scss-fixtures/custom-configuration/styles/global.scss +++ /dev/null @@ -1,11 +0,0 @@ -/* this should pass through untransformed */ -@media (480px <= width < 768px) { - ::placeholder { - color: green; - } -} - -/* this should be transformed to width/height */ -.video { - -xyz-max-size: 400px 300px; -} From c14c7f0dc41c5bf8206bfff724e4d4b79314beb5 Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 14:03:52 -0500 Subject: [PATCH 26/34] Adjust global tests --- .../compilation-and-prefixing/styles/global.scss | 5 +++-- .../scss-fixtures/npm-import-bad/styles/global.scss | 2 +- .../npm-import-nested/node_modules/example/test.scss | 2 +- test/integration/scss-modules/test/index.test.js | 3 +-- test/integration/scss/test/index.test.js | 5 +---- 5 files changed, 7 insertions(+), 10 deletions(-) diff --git a/test/integration/scss-fixtures/compilation-and-prefixing/styles/global.scss b/test/integration/scss-fixtures/compilation-and-prefixing/styles/global.scss index 19e8290b4cd41..2cc5c559f728a 100644 --- a/test/integration/scss-fixtures/compilation-and-prefixing/styles/global.scss +++ b/test/integration/scss-fixtures/compilation-and-prefixing/styles/global.scss @@ -1,5 +1,6 @@ -@media (480px <= width < 768px) { +$var: red; +.redText { ::placeholder { - color: green; + color: $var; } } diff --git a/test/integration/scss-fixtures/npm-import-bad/styles/global.scss b/test/integration/scss-fixtures/npm-import-bad/styles/global.scss index 8e799fdddaeec..bc9b10bfd0877 100644 --- a/test/integration/scss-fixtures/npm-import-bad/styles/global.scss +++ b/test/integration/scss-fixtures/npm-import-bad/styles/global.scss @@ -1 +1 @@ -@import 'nprogress/nprogress.scss'; +@import 'nprogress/nprogress.css'; diff --git a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss index 57ac6959e15d3..2d3c0c63b9749 100644 --- a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss +++ b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss @@ -1,4 +1,4 @@ -@import url('other.scss'); +@import 'other.scss'; .test { color: red; diff --git a/test/integration/scss-modules/test/index.test.js b/test/integration/scss-modules/test/index.test.js index 5432b55a8f6ec..93e793260e399 100644 --- a/test/integration/scss-modules/test/index.test.js +++ b/test/integration/scss-modules/test/index.test.js @@ -19,7 +19,7 @@ jasmine.DEFAULT_TIMEOUT_INTERVAL = 1000 * 60 * 1 const fixturesDir = join(__dirname, '../../scss-fixtures') describe('SCSS modules', () => { - describe('Basic CSS Module Support', () => { + describe('Basic SCSS Module Support', () => { const appDir = join(fixturesDir, 'basic-module') let appPort @@ -181,7 +181,6 @@ describe('SCSS modules', () => { // FIXME: this is broken it('should update CSS color without remounting ', async () => { const browser = await webdriver(appPort, '/') - await waitFor(2000) // ensure application hydrates const desiredText = 'hello world' await browser.elementById('text-input').type(desiredText) diff --git a/test/integration/scss/test/index.test.js b/test/integration/scss/test/index.test.js index cf6ef28ce989f..7a2cbc971f0bc 100644 --- a/test/integration/scss/test/index.test.js +++ b/test/integration/scss/test/index.test.js @@ -143,7 +143,7 @@ describe('SCSS Support', () => { expect( cssContent.replace(/\/\*.*?\*\//g, '').trim() ).toMatchInlineSnapshot( - `"@media (min-width:480px) and (max-width:767px){::-webkit-input-placeholder{color:green}::-moz-placeholder{color:green}:-ms-input-placeholder{color:green}::-ms-input-placeholder{color:green}::placeholder{color:green}}"` + `".redText ::-webkit-input-placeholder{color:red}.redText ::-moz-placeholder{color:red}.redText :-ms-input-placeholder{color:red}.redText ::-ms-input-placeholder{color:red}.redText ::placeholder{color:red}"` ) // Contains a source map @@ -304,7 +304,6 @@ describe('SCSS Support', () => { let browser try { browser = await webdriver(appPort, '/page1') - await waitFor(2000) // ensure application hydrates const desiredText = 'hello world' await browser.elementById('text-input').type(desiredText) @@ -703,7 +702,6 @@ describe('SCSS Support', () => { it('should have the correct color (css ordering)', async () => { const browser = await webdriver(appPort, '/') - await waitFor(2000) // ensure application hydrates const currentColor = await browser.eval( `window.getComputedStyle(document.querySelector('.my-text')).color` @@ -729,7 +727,6 @@ describe('SCSS Support', () => { it('should have the correct color (css ordering)', async () => { const browser = await webdriver(appPort, '/') - await waitFor(2000) // ensure application hydrates const currentColor = await browser.eval( `window.getComputedStyle(document.querySelector('.my-text')).color` From e5f3931ee3d137c566e243b48ab3fd5de0e4f66e Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 14:17:52 -0500 Subject: [PATCH 27/34] Remove wrapper --- .../scss-modules/test/index.test.js | 576 +++++++++--------- 1 file changed, 280 insertions(+), 296 deletions(-) diff --git a/test/integration/scss-modules/test/index.test.js b/test/integration/scss-modules/test/index.test.js index 93e793260e399..d73f290d379f3 100644 --- a/test/integration/scss-modules/test/index.test.js +++ b/test/integration/scss-modules/test/index.test.js @@ -18,382 +18,366 @@ jasmine.DEFAULT_TIMEOUT_INTERVAL = 1000 * 60 * 1 const fixturesDir = join(__dirname, '../../scss-fixtures') -describe('SCSS modules', () => { - describe('Basic SCSS Module Support', () => { - const appDir = join(fixturesDir, 'basic-module') - - let appPort - let app - beforeAll(async () => { - await remove(join(appDir, '.next')) - await nextBuild(appDir) - appPort = await findPort() - app = await nextStart(appDir, appPort) - }) - afterAll(async () => { - await killApp(app) - }) +describe('Basic SCSS Module Support', () => { + const appDir = join(fixturesDir, 'basic-module') + + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) - it(`should've emitted a single CSS file`, async () => { - const cssFolder = join(appDir, '.next/static/css') + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') - const files = await readdir(cssFolder) - const cssFiles = files.filter(f => /\.css$/.test(f)) + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) - expect(cssFiles.length).toBe(1) - const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') - expect( - cssContent.replace(/\/\*.*?\*\//g, '').trim() - ).toMatchInlineSnapshot(`".index_redText__2VIiM{color:red}"`) - }) + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatchInlineSnapshot( + `".index_redText__2VIiM{color:red}"` + ) + }) - it(`should've injected the CSS on server render`, async () => { - const content = await renderViaHTTP(appPort, '/') - const $ = cheerio.load(content) + it(`should've injected the CSS on server render`, async () => { + const content = await renderViaHTTP(appPort, '/') + const $ = cheerio.load(content) - const cssPreload = $('link[rel="preload"][as="style"]') - expect(cssPreload.length).toBe(1) - expect(cssPreload.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + const cssPreload = $('link[rel="preload"][as="style"]') + expect(cssPreload.length).toBe(1) + expect(cssPreload.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) - const cssSheet = $('link[rel="stylesheet"]') - expect(cssSheet.length).toBe(1) - expect(cssSheet.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + const cssSheet = $('link[rel="stylesheet"]') + expect(cssSheet.length).toBe(1) + expect(cssSheet.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) - expect($('#verify-red').attr('class')).toMatchInlineSnapshot( - `"index_redText__2VIiM"` - ) - }) + expect($('#verify-red').attr('class')).toMatchInlineSnapshot( + `"index_redText__2VIiM"` + ) }) +}) - describe('3rd Party CSS Module Support', () => { - const appDir = join(fixturesDir, '3rd-party-module') +describe('3rd Party CSS Module Support', () => { + const appDir = join(fixturesDir, '3rd-party-module') - let appPort - let app - beforeAll(async () => { - await remove(join(appDir, '.next')) - await nextBuild(appDir) - appPort = await findPort() - app = await nextStart(appDir, appPort) - }) - afterAll(async () => { - await killApp(app) - }) + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) - it(`should've emitted a single CSS file`, async () => { - const cssFolder = join(appDir, '.next/static/css') + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') - const files = await readdir(cssFolder) - const cssFiles = files.filter(f => /\.css$/.test(f)) + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) - expect(cssFiles.length).toBe(1) - const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') - expect( - cssContent.replace(/\/\*.*?\*\//g, '').trim() - ).toMatchInlineSnapshot( - `".index_foo__9_fxH{position:relative}.index_foo__9_fxH .bar,.index_foo__9_fxH .baz{height:100%;overflow:hidden}.index_foo__9_fxH .lol,.index_foo__9_fxH>.lel{width:80%}"` - ) - }) + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatchInlineSnapshot( + `".index_foo__9_fxH{position:relative}.index_foo__9_fxH .bar,.index_foo__9_fxH .baz{height:100%;overflow:hidden}.index_foo__9_fxH .lol,.index_foo__9_fxH>.lel{width:80%}"` + ) + }) - it(`should've injected the CSS on server render`, async () => { - const content = await renderViaHTTP(appPort, '/') - const $ = cheerio.load(content) + it(`should've injected the CSS on server render`, async () => { + const content = await renderViaHTTP(appPort, '/') + const $ = cheerio.load(content) - const cssPreload = $('link[rel="preload"][as="style"]') - expect(cssPreload.length).toBe(1) - expect(cssPreload.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + const cssPreload = $('link[rel="preload"][as="style"]') + expect(cssPreload.length).toBe(1) + expect(cssPreload.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) - const cssSheet = $('link[rel="stylesheet"]') - expect(cssSheet.length).toBe(1) - expect(cssSheet.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) + const cssSheet = $('link[rel="stylesheet"]') + expect(cssSheet.length).toBe(1) + expect(cssSheet.attr('href')).toMatch(/^\/_next\/static\/css\/.*\.css$/) - expect($('#verify-div').attr('class')).toMatchInlineSnapshot( - `"index_foo__9_fxH"` - ) - }) + expect($('#verify-div').attr('class')).toMatchInlineSnapshot( + `"index_foo__9_fxH"` + ) }) +}) - describe('Has CSS Module in computed styles in Development', () => { - const appDir = join(fixturesDir, 'dev-module') +describe('Has CSS Module in computed styles in Development', () => { + const appDir = join(fixturesDir, 'dev-module') - let appPort - let app - beforeAll(async () => { - await remove(join(appDir, '.next')) - appPort = await findPort() - app = await launchApp(appDir, appPort) - }) - afterAll(async () => { - await killApp(app) - }) + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) - it('should have CSS for page', async () => { - const browser = await webdriver(appPort, '/') + it('should have CSS for page', async () => { + const browser = await webdriver(appPort, '/') - const currentColor = await browser.eval( - `window.getComputedStyle(document.querySelector('#verify-red')).color` - ) - expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) - }) + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('#verify-red')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) }) +}) - describe('Has CSS Module in computed styles in Production', () => { - const appDir = join(fixturesDir, 'prod-module') +describe('Has CSS Module in computed styles in Production', () => { + const appDir = join(fixturesDir, 'prod-module') - let appPort - let app - beforeAll(async () => { - await remove(join(appDir, '.next')) - await nextBuild(appDir) - appPort = await findPort() - app = await nextStart(appDir, appPort) - }) - afterAll(async () => { - await killApp(app) - }) + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) - it('should have CSS for page', async () => { - const browser = await webdriver(appPort, '/') + it('should have CSS for page', async () => { + const browser = await webdriver(appPort, '/') - const currentColor = await browser.eval( - `window.getComputedStyle(document.querySelector('#verify-red')).color` - ) - expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) - }) + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('#verify-red')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) }) +}) - xdescribe('Can hot reload CSS Module without losing state', () => { - const appDir = join(fixturesDir, 'hmr-module') +xdescribe('Can hot reload CSS Module without losing state', () => { + const appDir = join(fixturesDir, 'hmr-module') - let appPort - let app - beforeAll(async () => { - await remove(join(appDir, '.next')) - appPort = await findPort() - app = await launchApp(appDir, appPort) - }) - afterAll(async () => { - await killApp(app) - }) + let appPort + let app + beforeAll(async () => { + await remove(join(appDir, '.next')) + appPort = await findPort() + app = await launchApp(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) - // FIXME: this is broken - it('should update CSS color without remounting ', async () => { - const browser = await webdriver(appPort, '/') + // FIXME: this is broken + it('should update CSS color without remounting ', async () => { + const browser = await webdriver(appPort, '/') - const desiredText = 'hello world' - await browser.elementById('text-input').type(desiredText) - expect(await browser.elementById('text-input').getValue()).toBe( - desiredText - ) + const desiredText = 'hello world' + await browser.elementById('text-input').type(desiredText) + expect(await browser.elementById('text-input').getValue()).toBe(desiredText) + + const currentColor = await browser.eval( + `window.getComputedStyle(document.querySelector('#verify-red')).color` + ) + expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) + + const cssFile = new File(join(appDir, 'pages/index.module.scss')) + try { + cssFile.replace('color: red', 'color: purple') + await waitFor(2000) // wait for HMR - const currentColor = await browser.eval( + const refreshedColor = await browser.eval( `window.getComputedStyle(document.querySelector('#verify-red')).color` ) - expect(currentColor).toMatchInlineSnapshot(`"rgb(255, 0, 0)"`) - - const cssFile = new File(join(appDir, 'pages/index.module.scss')) - try { - cssFile.replace('color: red', 'color: purple') - await waitFor(2000) // wait for HMR - - const refreshedColor = await browser.eval( - `window.getComputedStyle(document.querySelector('#verify-red')).color` - ) - expect(refreshedColor).toMatchInlineSnapshot(`"rgb(128, 0, 128)"`) - - // ensure text remained - expect(await browser.elementById('text-input').getValue()).toBe( - desiredText - ) - } finally { - cssFile.restore() - } - }) + expect(refreshedColor).toMatchInlineSnapshot(`"rgb(128, 0, 128)"`) + + // ensure text remained + expect(await browser.elementById('text-input').getValue()).toBe( + desiredText + ) + } finally { + cssFile.restore() + } }) +}) - describe('Invalid CSS Module Usage in node_modules', () => { - const appDir = join(fixturesDir, 'invalid-module') +describe('Invalid CSS Module Usage in node_modules', () => { + const appDir = join(fixturesDir, 'invalid-module') - beforeAll(async () => { - await remove(join(appDir, '.next')) - }) + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) - it('should fail to build', async () => { - const { stderr } = await nextBuild(appDir, [], { - stderr: true, - }) - expect(stderr).toContain('Failed to compile') - expect(stderr).toContain('node_modules/example/index.module.scss') - expect(stderr).toMatch( - /CSS Modules.*cannot.*be imported from within.*node_modules/ - ) - expect(stderr).toMatch( - /Location:.*node_modules[\\/]example[\\/]index\.mjs/ - ) + it('should fail to build', async () => { + const { stderr } = await nextBuild(appDir, [], { + stderr: true, }) + expect(stderr).toContain('Failed to compile') + expect(stderr).toContain('node_modules/example/index.module.scss') + expect(stderr).toMatch( + /CSS Modules.*cannot.*be imported from within.*node_modules/ + ) + expect(stderr).toMatch(/Location:.*node_modules[\\/]example[\\/]index\.mjs/) }) +}) - describe('Invalid CSS Module Usage in node_modules', () => { - const appDir = join(fixturesDir, 'invalid-global-module') +describe('Invalid CSS Module Usage in node_modules', () => { + const appDir = join(fixturesDir, 'invalid-global-module') - beforeAll(async () => { - await remove(join(appDir, '.next')) - }) + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) - it('should fail to build', async () => { - const { stderr } = await nextBuild(appDir, [], { - stderr: true, - }) - expect(stderr).toContain('Failed to compile') - expect(stderr).toContain('node_modules/example/index.scss') - expect(stderr).toMatch( - /Global CSS.*cannot.*be imported from within.*node_modules/ - ) - expect(stderr).toMatch( - /Location:.*node_modules[\\/]example[\\/]index\.mjs/ - ) + it('should fail to build', async () => { + const { stderr } = await nextBuild(appDir, [], { + stderr: true, }) + expect(stderr).toContain('Failed to compile') + expect(stderr).toContain('node_modules/example/index.scss') + expect(stderr).toMatch( + /Global CSS.*cannot.*be imported from within.*node_modules/ + ) + expect(stderr).toMatch(/Location:.*node_modules[\\/]example[\\/]index\.mjs/) }) +}) - describe('Valid CSS Module Usage from within node_modules', () => { - const appDir = join(fixturesDir, 'nm-module') +describe('Valid CSS Module Usage from within node_modules', () => { + const appDir = join(fixturesDir, 'nm-module') - beforeAll(async () => { - await remove(join(appDir, '.next')) - }) + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) - let appPort - let app - beforeAll(async () => { - await nextBuild(appDir) - appPort = await findPort() - app = await nextStart(appDir, appPort) - }) - afterAll(async () => { - await killApp(app) - }) + let appPort + let app + beforeAll(async () => { + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) - it(`should've prerendered with relevant data`, async () => { - const content = await renderViaHTTP(appPort, '/') - const $ = cheerio.load(content) + it(`should've prerendered with relevant data`, async () => { + const content = await renderViaHTTP(appPort, '/') + const $ = cheerio.load(content) - const cssPreload = $('#nm-div') - expect(cssPreload.text()).toMatchInlineSnapshot( - `"{\\"message\\":\\"Why hello there\\"} {\\"redText\\":\\"example_redText__1hNNA\\"}"` - ) - }) + const cssPreload = $('#nm-div') + expect(cssPreload.text()).toMatchInlineSnapshot( + `"{\\"message\\":\\"Why hello there\\"} {\\"redText\\":\\"example_redText__1hNNA\\"}"` + ) + }) - it(`should've emitted a single CSS file`, async () => { - const cssFolder = join(appDir, '.next/static/css') + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') - const files = await readdir(cssFolder) - const cssFiles = files.filter(f => /\.css$/.test(f)) + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) - expect(cssFiles.length).toBe(1) - const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') - expect( - cssContent.replace(/\/\*.*?\*\//g, '').trim() - ).toMatchInlineSnapshot(`".example_redText__1hNNA{color:\\"red\\"}"`) - }) + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatchInlineSnapshot( + `".example_redText__1hNNA{color:\\"red\\"}"` + ) }) +}) - describe('Valid Nested CSS Module Usage from within node_modules', () => { - const appDir = join(fixturesDir, 'nm-module-nested') +describe('Valid Nested CSS Module Usage from within node_modules', () => { + const appDir = join(fixturesDir, 'nm-module-nested') - beforeAll(async () => { - await remove(join(appDir, '.next')) - }) + beforeAll(async () => { + await remove(join(appDir, '.next')) + }) - let appPort - let app - beforeAll(async () => { - await nextBuild(appDir) - appPort = await findPort() - app = await nextStart(appDir, appPort) - }) - afterAll(async () => { - await killApp(app) - }) + let appPort + let app + beforeAll(async () => { + await nextBuild(appDir) + appPort = await findPort() + app = await nextStart(appDir, appPort) + }) + afterAll(async () => { + await killApp(app) + }) - it(`should've prerendered with relevant data`, async () => { - const content = await renderViaHTTP(appPort, '/') - const $ = cheerio.load(content) + it(`should've prerendered with relevant data`, async () => { + const content = await renderViaHTTP(appPort, '/') + const $ = cheerio.load(content) - const cssPreload = $('#nm-div') - expect(cssPreload.text()).toMatchInlineSnapshot( - `"{\\"message\\":\\"Why hello there\\"} {\\"other2\\":\\"example_other2__1pnJV\\",\\"subClass\\":\\"example_subClass__2EbKX other_className__E6nd8\\"}"` - ) - }) + const cssPreload = $('#nm-div') + expect(cssPreload.text()).toMatchInlineSnapshot( + `"{\\"message\\":\\"Why hello there\\"} {\\"other2\\":\\"example_other2__1pnJV\\",\\"subClass\\":\\"example_subClass__2EbKX other_className__E6nd8\\"}"` + ) + }) - it(`should've emitted a single CSS file`, async () => { - const cssFolder = join(appDir, '.next/static/css') + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') - const files = await readdir(cssFolder) - const cssFiles = files.filter(f => /\.css$/.test(f)) + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) - expect(cssFiles.length).toBe(1) - const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') - expect( - cssContent.replace(/\/\*.*?\*\//g, '').trim() - ).toMatchInlineSnapshot( - `".other_other3__ZPN-Y{color:violet}.other_className__E6nd8{background:red;color:#ff0}.example_other2__1pnJV{color:red}.example_subClass__2EbKX{background:#00f}"` - ) - }) + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatchInlineSnapshot( + `".other_other3__ZPN-Y{color:violet}.other_className__E6nd8{background:red;color:#ff0}.example_other2__1pnJV{color:red}.example_subClass__2EbKX{background:#00f}"` + ) }) +}) - describe('CSS Module Composes Usage (Basic)', () => { - // This is a very bad feature. Do not use it. - const appDir = join(fixturesDir, 'composes-basic') +describe('CSS Module Composes Usage (Basic)', () => { + // This is a very bad feature. Do not use it. + const appDir = join(fixturesDir, 'composes-basic') - beforeAll(async () => { - await remove(join(appDir, '.next')) - await nextBuild(appDir) - }) + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + }) - it(`should've emitted a single CSS file`, async () => { - const cssFolder = join(appDir, '.next/static/css') + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') - const files = await readdir(cssFolder) - const cssFiles = files.filter(f => /\.css$/.test(f)) + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) - expect(cssFiles.length).toBe(1) - const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') - expect( - cssContent.replace(/\/\*.*?\*\//g, '').trim() - ).toMatchInlineSnapshot( - `".index_className__2O8Wt{background:red;color:#ff0}.index_subClass__3e6Re{background:#00f}"` - ) - }) + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatchInlineSnapshot( + `".index_className__2O8Wt{background:red;color:#ff0}.index_subClass__3e6Re{background:#00f}"` + ) }) +}) - describe('CSS Module Composes Usage (External)', () => { - // This is a very bad feature. Do not use it. - const appDir = join(fixturesDir, 'composes-external') +describe('CSS Module Composes Usage (External)', () => { + // This is a very bad feature. Do not use it. + const appDir = join(fixturesDir, 'composes-external') - beforeAll(async () => { - await remove(join(appDir, '.next')) - await nextBuild(appDir) - }) + beforeAll(async () => { + await remove(join(appDir, '.next')) + await nextBuild(appDir) + }) - it(`should've emitted a single CSS file`, async () => { - const cssFolder = join(appDir, '.next/static/css') + it(`should've emitted a single CSS file`, async () => { + const cssFolder = join(appDir, '.next/static/css') - const files = await readdir(cssFolder) - const cssFiles = files.filter(f => /\.css$/.test(f)) + const files = await readdir(cssFolder) + const cssFiles = files.filter(f => /\.css$/.test(f)) - expect(cssFiles.length).toBe(1) - const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') + expect(cssFiles.length).toBe(1) + const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') - expect( - cssContent.replace(/\/\*.*?\*\//g, '').trim() - ).toMatchInlineSnapshot( - `".other_className__2VTl4{background:red;color:#ff0}.index_subClass__3e6Re{background:#00f}"` - ) - }) + expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatchInlineSnapshot( + `".other_className__2VTl4{background:red;color:#ff0}.index_subClass__3e6Re{background:#00f}"` + ) }) }) From 6196d9acb90a53f23f6cb422ea2655001a33357f Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 14:34:36 -0500 Subject: [PATCH 28/34] Update source maps --- test/integration/scss/test/index.test.js | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/test/integration/scss/test/index.test.js b/test/integration/scss/test/index.test.js index 7a2cbc971f0bc..7696ca5648d1b 100644 --- a/test/integration/scss/test/index.test.js +++ b/test/integration/scss/test/index.test.js @@ -164,11 +164,12 @@ describe('SCSS Support', () => { const { version, mappings, sourcesContent } = JSON.parse(cssMapContent) expect({ version, mappings, sourcesContent }).toMatchInlineSnapshot(` Object { - "mappings": "AAAA,+CACE,4BACE,WACF,CAFA,mBACE,WACF,CAFA,uBACE,WACF,CAFA,wBACE,WACF,CAFA,cACE,WACF,CACF", + "mappings": "AACA,qCAEI,SAHK,CACT,4BAEI,SAHK,CACT,gCAEI,SAHK,CACT,iCAEI,SAHK,CACT,uBAEI,SAHK", "sourcesContent": Array [ - "@media (480px <= width < 768px) { + "$var: red; + .redText { ::placeholder { - color: green; + color: $var; } } ", From 34500ace1bd4bec0319bb10ca93a3907e771f217 Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 14:41:29 -0500 Subject: [PATCH 29/34] Flag scss behavior --- packages/next/build/webpack-config.ts | 1 + .../build/webpack/config/blocks/css/index.ts | 92 ++++++++++++------- packages/next/build/webpack/config/index.ts | 4 +- packages/next/next-server/server/config.ts | 1 + 4 files changed, 65 insertions(+), 33 deletions(-) diff --git a/packages/next/build/webpack-config.ts b/packages/next/build/webpack-config.ts index 777213d13dc68..ab38642e45bf4 100644 --- a/packages/next/build/webpack-config.ts +++ b/packages/next/build/webpack-config.ts @@ -834,6 +834,7 @@ export default async function getBaseWebpackConfig( isDevelopment: dev, isServer, hasSupportCss: !!config.experimental.css, + hasSupportScss: !!config.experimental.scss, assetPrefix: config.assetPrefix || '', }) diff --git a/packages/next/build/webpack/config/blocks/css/index.ts b/packages/next/build/webpack/config/blocks/css/index.ts index aa866c1d71b6d..0ba6ec7051db3 100644 --- a/packages/next/build/webpack/config/blocks/css/index.ts +++ b/packages/next/build/webpack/config/blocks/css/index.ts @@ -26,6 +26,7 @@ const regexSassModules = /\.module\.(scss|sass)$/ export const css = curry(async function css( enabled: boolean, + scssEnabled: boolean, ctx: ConfigurationContext, config: Configuration ) { @@ -123,34 +124,44 @@ export const css = curry(async function css( }, use: getCssModuleLoader(ctx, postCssPlugins), }, - - // Opt-in support for Sass (using .scss or .sass extensions). - { - // Sass Modules should never have side effects. This setting will - // allow unused Sass to be removed from the production build. - // We ensure this by disallowing `:global()` Sass at the top-level - // via the `pure` mode in `css-loader`. - sideEffects: false, - // Sass Modules are activated via this specific extension. - test: regexSassModules, - // Sass Modules are only supported in the user's application. We're - // not yet allowing Sass imports _within_ `node_modules`. - issuer: { - include: [ctx.rootDirectory], - exclude: /node_modules/, - }, - use: getCssModuleLoader(ctx, postCssPlugins, sassPreprocessors), - }, ], }) ) + if (scssEnabled) { + fns.push( + loader({ + oneOf: [ + // Opt-in support for Sass (using .scss or .sass extensions). + { + // Sass Modules should never have side effects. This setting will + // allow unused Sass to be removed from the production build. + // We ensure this by disallowing `:global()` Sass at the top-level + // via the `pure` mode in `css-loader`. + sideEffects: false, + // Sass Modules are activated via this specific extension. + test: regexSassModules, + // Sass Modules are only supported in the user's application. We're + // not yet allowing Sass imports _within_ `node_modules`. + issuer: { + include: [ctx.rootDirectory], + exclude: /node_modules/, + }, + use: getCssModuleLoader(ctx, postCssPlugins, sassPreprocessors), + }, + ], + }) + ) + } // Throw an error for CSS Modules used outside their supported scope fns.push( loader({ oneOf: [ { - test: [regexCssModules, regexSassModules], + test: [ + regexCssModules, + (scssEnabled && regexSassModules) as RegExp, + ].filter(Boolean), use: { loader: 'error-loader', options: { @@ -167,7 +178,10 @@ export const css = curry(async function css( loader({ oneOf: [ { - test: [regexCssGlobal, regexSassGlobal], + test: [ + regexCssGlobal, + (scssEnabled && regexSassGlobal) as RegExp, + ].filter(Boolean), use: require.resolve('ignore-loader'), }, ], @@ -187,19 +201,27 @@ export const css = curry(async function css( issuer: { include: ctx.customAppFile }, use: getGlobalCssLoader(ctx, postCssPlugins), }, - { - // A global Sass import always has side effects. Webpack will tree - // shake the Sass without this option if the issuer claims to have - // no side-effects. - // See https://github.com/webpack/webpack/issues/6571 - sideEffects: true, - test: regexSassGlobal, - issuer: { include: ctx.customAppFile }, - use: getGlobalCssLoader(ctx, postCssPlugins, sassPreprocessors), - }, ], }) ) + if (scssEnabled) { + fns.push( + loader({ + oneOf: [ + { + // A global Sass import always has side effects. Webpack will tree + // shake the Sass without this option if the issuer claims to have + // no side-effects. + // See https://github.com/webpack/webpack/issues/6571 + sideEffects: true, + test: regexSassGlobal, + issuer: { include: ctx.customAppFile }, + use: getGlobalCssLoader(ctx, postCssPlugins, sassPreprocessors), + }, + ], + }) + ) + } } // Throw an error for Global CSS used inside of `node_modules` @@ -207,7 +229,10 @@ export const css = curry(async function css( loader({ oneOf: [ { - test: [regexCssGlobal, regexSassGlobal], + test: [ + regexCssGlobal, + (scssEnabled && regexSassGlobal) as RegExp, + ].filter(Boolean), issuer: { include: [/node_modules/] }, use: { loader: 'error-loader', @@ -225,7 +250,10 @@ export const css = curry(async function css( loader({ oneOf: [ { - test: [regexCssGlobal, regexSassGlobal], + test: [ + regexCssGlobal, + (scssEnabled && regexSassGlobal) as RegExp, + ].filter(Boolean), use: { loader: 'error-loader', options: { diff --git a/packages/next/build/webpack/config/index.ts b/packages/next/build/webpack/config/index.ts index 3d60123601e49..8df1fffe08efa 100644 --- a/packages/next/build/webpack/config/index.ts +++ b/packages/next/build/webpack/config/index.ts @@ -11,6 +11,7 @@ export async function build( isDevelopment, isServer, hasSupportCss, + hasSupportScss, assetPrefix, }: { rootDirectory: string @@ -18,6 +19,7 @@ export async function build( isDevelopment: boolean isServer: boolean hasSupportCss: boolean + hasSupportScss: boolean assetPrefix: string } ): Promise { @@ -35,6 +37,6 @@ export async function build( : '', } - const fn = pipe(base(ctx), css(hasSupportCss, ctx)) + const fn = pipe(base(ctx), css(hasSupportCss, hasSupportScss, ctx)) return fn(config) } diff --git a/packages/next/next-server/server/config.ts b/packages/next/next-server/server/config.ts index 57a50d0df8b0b..564742f40bf6c 100644 --- a/packages/next/next-server/server/config.ts +++ b/packages/next/next-server/server/config.ts @@ -42,6 +42,7 @@ const defaultConfig: { [key: string]: any } = { (os.cpus() || { length: 1 }).length) - 1 ), css: true, + scss: false, documentMiddleware: false, granularChunks: true, modern: false, From 703b7adaa61eb8db90a1171785c1ce118390027a Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Wed, 22 Jan 2020 12:11:02 -0700 Subject: [PATCH 30/34] Fix css property value --- .../nm-module/node_modules/example/index.module.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/integration/css-fixtures/nm-module/node_modules/example/index.module.css b/test/integration/css-fixtures/nm-module/node_modules/example/index.module.css index f77fe0ef0bdbe..08a38e09ef8ea 100644 --- a/test/integration/css-fixtures/nm-module/node_modules/example/index.module.css +++ b/test/integration/css-fixtures/nm-module/node_modules/example/index.module.css @@ -1,3 +1,3 @@ .redText { - color: 'red'; + color: red; } From cf6834f8d1fe0e4b27de6c9355b785c47b198043 Mon Sep 17 00:00:00 2001 From: alejalapeno Date: Wed, 22 Jan 2020 12:21:58 -0700 Subject: [PATCH 31/34] Update fixtures with Sass vars --- .../scss-fixtures/basic-module/pages/index.module.scss | 3 ++- .../scss-fixtures/composes-basic/pages/index.module.scss | 3 ++- .../scss-fixtures/composes-external/pages/index.module.scss | 3 ++- .../scss-fixtures/composes-external/pages/other.scss | 3 ++- .../scss-fixtures/dev-module/pages/index.module.scss | 3 ++- .../scss-fixtures/hmr-module/pages/index.module.scss | 3 ++- .../scss-fixtures/multi-global-reversed/styles/global1.scss | 3 ++- .../scss-fixtures/multi-global-reversed/styles/global2.scss | 3 ++- .../integration/scss-fixtures/multi-global/styles/global1.scss | 3 ++- .../integration/scss-fixtures/multi-global/styles/global2.scss | 3 ++- .../scss-fixtures/multi-module/pages/blue.module.scss | 3 ++- .../scss-fixtures/multi-module/pages/red.module.scss | 3 ++- test/integration/scss-fixtures/multi-page/styles/global1.scss | 3 ++- test/integration/scss-fixtures/multi-page/styles/global2.scss | 3 ++- .../scss-fixtures/nested-global/styles/global1.scss | 3 ++- .../scss-fixtures/nested-global/styles/global1b.scss | 3 ++- .../scss-fixtures/nested-global/styles/global2.scss | 3 ++- .../scss-fixtures/nested-global/styles/global2b.scss | 3 ++- .../nm-module-nested/node_modules/example/index.module.scss | 3 ++- .../nm-module-nested/node_modules/example/other.scss | 3 ++- .../nm-module-nested/node_modules/example/other2.scss | 3 ++- .../nm-module-nested/node_modules/example/other3.scss | 3 ++- .../nm-module/node_modules/example/index.module.scss | 3 ++- .../npm-import-nested/node_modules/example/other.scss | 3 ++- .../npm-import-nested/node_modules/example/test.scss | 3 ++- .../scss-fixtures/prod-module/pages/index.module.scss | 3 ++- .../scss-fixtures/single-global-src/styles/global.scss | 3 ++- .../integration/scss-fixtures/single-global/styles/global.scss | 3 ++- .../url-global-asset-prefix-1/styles/global1.scss | 3 ++- .../url-global-asset-prefix-1/styles/global2.scss | 3 ++- .../url-global-asset-prefix-1/styles/global2b.scss | 3 ++- .../url-global-asset-prefix-2/styles/global1.scss | 3 ++- .../url-global-asset-prefix-2/styles/global2.scss | 3 ++- .../url-global-asset-prefix-2/styles/global2b.scss | 3 ++- test/integration/scss-fixtures/url-global/styles/global1.scss | 3 ++- test/integration/scss-fixtures/url-global/styles/global2.scss | 3 ++- test/integration/scss-fixtures/url-global/styles/global2b.scss | 3 ++- .../scss-fixtures/valid-and-invalid-global/styles/global.scss | 3 ++- .../scss-fixtures/with-styled-jsx/styles/global.scss | 3 ++- 39 files changed, 78 insertions(+), 39 deletions(-) diff --git a/test/integration/scss-fixtures/basic-module/pages/index.module.scss b/test/integration/scss-fixtures/basic-module/pages/index.module.scss index 08a38e09ef8ea..eb8bb05c73aca 100644 --- a/test/integration/scss-fixtures/basic-module/pages/index.module.scss +++ b/test/integration/scss-fixtures/basic-module/pages/index.module.scss @@ -1,3 +1,4 @@ +$var: red; .redText { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/composes-basic/pages/index.module.scss b/test/integration/scss-fixtures/composes-basic/pages/index.module.scss index 0999b553172d8..e3c6430bd6f70 100644 --- a/test/integration/scss-fixtures/composes-basic/pages/index.module.scss +++ b/test/integration/scss-fixtures/composes-basic/pages/index.module.scss @@ -1,5 +1,6 @@ +$var: red; .className { - background: red; + background: $var; color: yellow; } diff --git a/test/integration/scss-fixtures/composes-external/pages/index.module.scss b/test/integration/scss-fixtures/composes-external/pages/index.module.scss index 373385ec2f693..196db5d888917 100644 --- a/test/integration/scss-fixtures/composes-external/pages/index.module.scss +++ b/test/integration/scss-fixtures/composes-external/pages/index.module.scss @@ -1,4 +1,5 @@ +$var: blue; .subClass { composes: className from './other.scss'; - background: blue; + background: $var; } diff --git a/test/integration/scss-fixtures/composes-external/pages/other.scss b/test/integration/scss-fixtures/composes-external/pages/other.scss index 6c6bc72eae403..382dd3097baa0 100644 --- a/test/integration/scss-fixtures/composes-external/pages/other.scss +++ b/test/integration/scss-fixtures/composes-external/pages/other.scss @@ -1,4 +1,5 @@ +$var: red; .className { - background: red; + background: $var; color: yellow; } diff --git a/test/integration/scss-fixtures/dev-module/pages/index.module.scss b/test/integration/scss-fixtures/dev-module/pages/index.module.scss index 08a38e09ef8ea..eb8bb05c73aca 100644 --- a/test/integration/scss-fixtures/dev-module/pages/index.module.scss +++ b/test/integration/scss-fixtures/dev-module/pages/index.module.scss @@ -1,3 +1,4 @@ +$var: red; .redText { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/hmr-module/pages/index.module.scss b/test/integration/scss-fixtures/hmr-module/pages/index.module.scss index 08a38e09ef8ea..eb8bb05c73aca 100644 --- a/test/integration/scss-fixtures/hmr-module/pages/index.module.scss +++ b/test/integration/scss-fixtures/hmr-module/pages/index.module.scss @@ -1,3 +1,4 @@ +$var: red; .redText { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/multi-global-reversed/styles/global1.scss b/test/integration/scss-fixtures/multi-global-reversed/styles/global1.scss index 8e1524022baf8..da7b3d1417b1b 100644 --- a/test/integration/scss-fixtures/multi-global-reversed/styles/global1.scss +++ b/test/integration/scss-fixtures/multi-global-reversed/styles/global1.scss @@ -1,3 +1,4 @@ +$var: red; .red-text { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/multi-global-reversed/styles/global2.scss b/test/integration/scss-fixtures/multi-global-reversed/styles/global2.scss index 9d1af6c0f6db1..3dd5eeaf6db92 100644 --- a/test/integration/scss-fixtures/multi-global-reversed/styles/global2.scss +++ b/test/integration/scss-fixtures/multi-global-reversed/styles/global2.scss @@ -1,3 +1,4 @@ +$var: blue; .blue-text { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/multi-global/styles/global1.scss b/test/integration/scss-fixtures/multi-global/styles/global1.scss index 8e1524022baf8..da7b3d1417b1b 100644 --- a/test/integration/scss-fixtures/multi-global/styles/global1.scss +++ b/test/integration/scss-fixtures/multi-global/styles/global1.scss @@ -1,3 +1,4 @@ +$var: red; .red-text { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/multi-global/styles/global2.scss b/test/integration/scss-fixtures/multi-global/styles/global2.scss index 9d1af6c0f6db1..3dd5eeaf6db92 100644 --- a/test/integration/scss-fixtures/multi-global/styles/global2.scss +++ b/test/integration/scss-fixtures/multi-global/styles/global2.scss @@ -1,3 +1,4 @@ +$var: blue; .blue-text { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/multi-module/pages/blue.module.scss b/test/integration/scss-fixtures/multi-module/pages/blue.module.scss index 4c5ac28ce4ef8..a227734ba1db1 100644 --- a/test/integration/scss-fixtures/multi-module/pages/blue.module.scss +++ b/test/integration/scss-fixtures/multi-module/pages/blue.module.scss @@ -1,3 +1,4 @@ +$var: blue; .blueText { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/multi-module/pages/red.module.scss b/test/integration/scss-fixtures/multi-module/pages/red.module.scss index 08a38e09ef8ea..eb8bb05c73aca 100644 --- a/test/integration/scss-fixtures/multi-module/pages/red.module.scss +++ b/test/integration/scss-fixtures/multi-module/pages/red.module.scss @@ -1,3 +1,4 @@ +$var: red; .redText { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/multi-page/styles/global1.scss b/test/integration/scss-fixtures/multi-page/styles/global1.scss index 8e1524022baf8..da7b3d1417b1b 100644 --- a/test/integration/scss-fixtures/multi-page/styles/global1.scss +++ b/test/integration/scss-fixtures/multi-page/styles/global1.scss @@ -1,3 +1,4 @@ +$var: red; .red-text { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/multi-page/styles/global2.scss b/test/integration/scss-fixtures/multi-page/styles/global2.scss index 9d1af6c0f6db1..3dd5eeaf6db92 100644 --- a/test/integration/scss-fixtures/multi-page/styles/global2.scss +++ b/test/integration/scss-fixtures/multi-page/styles/global2.scss @@ -1,3 +1,4 @@ +$var: blue; .blue-text { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/nested-global/styles/global1.scss b/test/integration/scss-fixtures/nested-global/styles/global1.scss index c6abef272702d..096036b10f2dd 100644 --- a/test/integration/scss-fixtures/nested-global/styles/global1.scss +++ b/test/integration/scss-fixtures/nested-global/styles/global1.scss @@ -1,5 +1,6 @@ @import './global1b.scss'; +$var: red; .red-text { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/nested-global/styles/global1b.scss b/test/integration/scss-fixtures/nested-global/styles/global1b.scss index 3902bc9032e31..e288c3ca0d12e 100644 --- a/test/integration/scss-fixtures/nested-global/styles/global1b.scss +++ b/test/integration/scss-fixtures/nested-global/styles/global1b.scss @@ -1,4 +1,5 @@ +$var: purple; .red-text { - color: purple; + color: $var; font-weight: bolder; } diff --git a/test/integration/scss-fixtures/nested-global/styles/global2.scss b/test/integration/scss-fixtures/nested-global/styles/global2.scss index 37e7107172397..4b659d369c561 100644 --- a/test/integration/scss-fixtures/nested-global/styles/global2.scss +++ b/test/integration/scss-fixtures/nested-global/styles/global2.scss @@ -1,5 +1,6 @@ @import './global2b.scss'; +$var: blue; .blue-text { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/nested-global/styles/global2b.scss b/test/integration/scss-fixtures/nested-global/styles/global2b.scss index 56bea0235b8ac..cc1554c3c8334 100644 --- a/test/integration/scss-fixtures/nested-global/styles/global2b.scss +++ b/test/integration/scss-fixtures/nested-global/styles/global2b.scss @@ -1,4 +1,5 @@ +$var: orange; .blue-text { - color: orange; + color: $var; font-weight: bolder; } diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss index aed5852ba6873..d2d4babe01664 100644 --- a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/index.module.scss @@ -1,6 +1,7 @@ @import 'other2.scss'; +$var: blue; .subClass { composes: className from './other.scss'; - background: blue; + background: $var; } diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss index d8eb83346a6ea..eb0f82f7aacb4 100644 --- a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other.scss @@ -1,6 +1,7 @@ @import 'other3.scss'; +$var: red; .className { - background: red; + background: $var; color: yellow; } diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss index 3edf8b085d62b..7525334516ec4 100644 --- a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other2.scss @@ -1,3 +1,4 @@ +$var: red; .other2 { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss index 3bff2788064f9..ecbdacff019d8 100644 --- a/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss +++ b/test/integration/scss-fixtures/nm-module-nested/node_modules/example/other3.scss @@ -1,3 +1,4 @@ +$var: violet; .other3 { - color: violet; + color: $var; } diff --git a/test/integration/scss-fixtures/nm-module/node_modules/example/index.module.scss b/test/integration/scss-fixtures/nm-module/node_modules/example/index.module.scss index f77fe0ef0bdbe..eb8bb05c73aca 100644 --- a/test/integration/scss-fixtures/nm-module/node_modules/example/index.module.scss +++ b/test/integration/scss-fixtures/nm-module/node_modules/example/index.module.scss @@ -1,3 +1,4 @@ +$var: red; .redText { - color: 'red'; + color: $var; } diff --git a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/other.scss b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/other.scss index eefdaa510cfa8..b2a7622386198 100644 --- a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/other.scss +++ b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/other.scss @@ -1,3 +1,4 @@ +$var: blue; .other { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss index 2d3c0c63b9749..2db9b0627d1ef 100644 --- a/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss +++ b/test/integration/scss-fixtures/npm-import-nested/node_modules/example/test.scss @@ -1,5 +1,6 @@ @import 'other.scss'; +$var: red; .test { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/prod-module/pages/index.module.scss b/test/integration/scss-fixtures/prod-module/pages/index.module.scss index 08a38e09ef8ea..eb8bb05c73aca 100644 --- a/test/integration/scss-fixtures/prod-module/pages/index.module.scss +++ b/test/integration/scss-fixtures/prod-module/pages/index.module.scss @@ -1,3 +1,4 @@ +$var: red; .redText { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/single-global-src/styles/global.scss b/test/integration/scss-fixtures/single-global-src/styles/global.scss index 8e1524022baf8..da7b3d1417b1b 100644 --- a/test/integration/scss-fixtures/single-global-src/styles/global.scss +++ b/test/integration/scss-fixtures/single-global-src/styles/global.scss @@ -1,3 +1,4 @@ +$var: red; .red-text { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/single-global/styles/global.scss b/test/integration/scss-fixtures/single-global/styles/global.scss index 8e1524022baf8..da7b3d1417b1b 100644 --- a/test/integration/scss-fixtures/single-global/styles/global.scss +++ b/test/integration/scss-fixtures/single-global/styles/global.scss @@ -1,3 +1,4 @@ +$var: red; .red-text { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global1.scss b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global1.scss index fdaf9c9476f9c..24f6145a7a6fa 100644 --- a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global1.scss +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global1.scss @@ -1,4 +1,5 @@ +$var: red; .red-text { - color: red; + color: $var; background-image: url('./dark.svg') url(dark2.svg); } diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2.scss b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2.scss index 37e7107172397..4b659d369c561 100644 --- a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2.scss +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2.scss @@ -1,5 +1,6 @@ @import './global2b.scss'; +$var: blue; .blue-text { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2b.scss b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2b.scss index 41c015298e5fd..0fe57600718f5 100644 --- a/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2b.scss +++ b/test/integration/scss-fixtures/url-global-asset-prefix-1/styles/global2b.scss @@ -1,5 +1,6 @@ +$var: orange; .blue-text { - color: orange; + color: $var; font-weight: bolder; background-image: url(../assets/light.svg); } diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global1.scss b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global1.scss index fdaf9c9476f9c..24f6145a7a6fa 100644 --- a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global1.scss +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global1.scss @@ -1,4 +1,5 @@ +$var: red; .red-text { - color: red; + color: $var; background-image: url('./dark.svg') url(dark2.svg); } diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2.scss b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2.scss index 37e7107172397..4b659d369c561 100644 --- a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2.scss +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2.scss @@ -1,5 +1,6 @@ @import './global2b.scss'; +$var: blue; .blue-text { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2b.scss b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2b.scss index 41c015298e5fd..0fe57600718f5 100644 --- a/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2b.scss +++ b/test/integration/scss-fixtures/url-global-asset-prefix-2/styles/global2b.scss @@ -1,5 +1,6 @@ +$var: orange; .blue-text { - color: orange; + color: $var; font-weight: bolder; background-image: url(../assets/light.svg); } diff --git a/test/integration/scss-fixtures/url-global/styles/global1.scss b/test/integration/scss-fixtures/url-global/styles/global1.scss index fdaf9c9476f9c..24f6145a7a6fa 100644 --- a/test/integration/scss-fixtures/url-global/styles/global1.scss +++ b/test/integration/scss-fixtures/url-global/styles/global1.scss @@ -1,4 +1,5 @@ +$var: red; .red-text { - color: red; + color: $var; background-image: url('./dark.svg') url(dark2.svg); } diff --git a/test/integration/scss-fixtures/url-global/styles/global2.scss b/test/integration/scss-fixtures/url-global/styles/global2.scss index 37e7107172397..4b659d369c561 100644 --- a/test/integration/scss-fixtures/url-global/styles/global2.scss +++ b/test/integration/scss-fixtures/url-global/styles/global2.scss @@ -1,5 +1,6 @@ @import './global2b.scss'; +$var: blue; .blue-text { - color: blue; + color: $var; } diff --git a/test/integration/scss-fixtures/url-global/styles/global2b.scss b/test/integration/scss-fixtures/url-global/styles/global2b.scss index 41c015298e5fd..0fe57600718f5 100644 --- a/test/integration/scss-fixtures/url-global/styles/global2b.scss +++ b/test/integration/scss-fixtures/url-global/styles/global2b.scss @@ -1,5 +1,6 @@ +$var: orange; .blue-text { - color: orange; + color: $var; font-weight: bolder; background-image: url(../assets/light.svg); } diff --git a/test/integration/scss-fixtures/valid-and-invalid-global/styles/global.scss b/test/integration/scss-fixtures/valid-and-invalid-global/styles/global.scss index 8e1524022baf8..da7b3d1417b1b 100644 --- a/test/integration/scss-fixtures/valid-and-invalid-global/styles/global.scss +++ b/test/integration/scss-fixtures/valid-and-invalid-global/styles/global.scss @@ -1,3 +1,4 @@ +$var: red; .red-text { - color: red; + color: $var; } diff --git a/test/integration/scss-fixtures/with-styled-jsx/styles/global.scss b/test/integration/scss-fixtures/with-styled-jsx/styles/global.scss index 167caa35ea86e..30a5d888c5011 100644 --- a/test/integration/scss-fixtures/with-styled-jsx/styles/global.scss +++ b/test/integration/scss-fixtures/with-styled-jsx/styles/global.scss @@ -1,3 +1,4 @@ +$var: red; .my-text { - color: red; + color: $var; } From 30006435b2610ee0706eb35f27c3670a3678fc58 Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 14:57:19 -0500 Subject: [PATCH 32/34] Turn on Scss support --- test/integration/scss-fixtures/next.config.js | 1 + 1 file changed, 1 insertion(+) diff --git a/test/integration/scss-fixtures/next.config.js b/test/integration/scss-fixtures/next.config.js index 2a0ee47afec3c..b97156a83b09e 100644 --- a/test/integration/scss-fixtures/next.config.js +++ b/test/integration/scss-fixtures/next.config.js @@ -3,6 +3,7 @@ module.exports = { // Make sure entries are not getting disposed. maxInactiveAge: 1000 * 60 * 60, }, + experimental: { scss: true }, webpack(cfg) { cfg.devtool = 'source-map' return cfg From 825d79039d539c9dcfcb75e659589763f04f0395 Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 14:59:16 -0500 Subject: [PATCH 33/34] fix HMR test --- test/integration/scss/test/index.test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/integration/scss/test/index.test.js b/test/integration/scss/test/index.test.js index 7696ca5648d1b..aca8a733f9951 100644 --- a/test/integration/scss/test/index.test.js +++ b/test/integration/scss/test/index.test.js @@ -319,7 +319,7 @@ describe('SCSS Support', () => { const cssFile = new File(join(appDir, 'styles/global1.scss')) try { - cssFile.replace('color: red', 'color: purple') + cssFile.replace('$var: red', '$var: purple') await waitFor(2000) // wait for HMR const refreshedColor = await browser.eval( From 7572109c23876ffec066878de00b7d432fa57ebb Mon Sep 17 00:00:00 2001 From: Joe Haddad Date: Wed, 22 Jan 2020 15:14:37 -0500 Subject: [PATCH 34/34] Fix snapshots --- test/integration/css-modules/test/index.test.js | 2 +- test/integration/scss-modules/test/index.test.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/test/integration/css-modules/test/index.test.js b/test/integration/css-modules/test/index.test.js index 3c0d865fd44dc..e990a2e04624c 100644 --- a/test/integration/css-modules/test/index.test.js +++ b/test/integration/css-modules/test/index.test.js @@ -286,7 +286,7 @@ describe('Valid CSS Module Usage from within node_modules', () => { const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatchInlineSnapshot( - `".example_redText__1rb5g{color:\\"red\\"}"` + `".example_redText__1rb5g{color:red}"` ) }) }) diff --git a/test/integration/scss-modules/test/index.test.js b/test/integration/scss-modules/test/index.test.js index d73f290d379f3..751ef2e07889c 100644 --- a/test/integration/scss-modules/test/index.test.js +++ b/test/integration/scss-modules/test/index.test.js @@ -286,7 +286,7 @@ describe('Valid CSS Module Usage from within node_modules', () => { const cssContent = await readFile(join(cssFolder, cssFiles[0]), 'utf8') expect(cssContent.replace(/\/\*.*?\*\//g, '').trim()).toMatchInlineSnapshot( - `".example_redText__1hNNA{color:\\"red\\"}"` + `".example_redText__1hNNA{color:red}"` ) }) })