Vue 2 + Webpack: Accessing Assets Folder - css

I have my assets in the /src/assets/ folder, specifically /src/assets/stylesheets/file.css but I cannot seem to bundle them. In my main.js file I've included the following
require('./assets/stylesheets/file.css')
but it does not work. I see:
Module not found: Error: Can't resolve './assets/stylesheets/codrops.css' in '/Users/USERNAME/Documents/Projects/vue/APPNAME/src'
# ./src/main.js 9:0-43
# multi ./build/dev-client ./src/main.js
I've tried using ../assets and that didn't work either.
Here's my build/webpack.base.conf.js file:
var path = require('path')
var utils = require('./utils')
var config = require('../config')
var vueLoaderConfig = require('./vue-loader.conf')
function resolve (dir) {
return path.join(__dirname, '..', dir)
}
module.exports = {
entry: {
app: './src/main.js'
},
output: {
path: config.build.assetsRoot,
filename: '[name].js',
publicPath: process.env.NODE_ENV === 'production'
? config.build.assetsPublicPath
: config.dev.assetsPublicPath
},
resolve: {
extensions: ['.js', '.vue', '.json'],
alias: {
'vue$': 'vue/dist/vue.esm.js',
'#': resolve('src')
}
},
module: {
rules: [
{
test: /\.vue$/,
loader: 'vue-loader',
options: vueLoaderConfig
},
{
test: /\.js$/,
loader: 'babel-loader',
include: [resolve('src'), resolve('test')]
},
{
test: /\.(png|jpe?g|gif|svg)(\?.*)?$/,
loader: 'url-loader',
options: {
limit: 10000,
name: utils.assetsPath('img/[name].[hash:7].[ext]')
}
},
{
test: /\.(mp4|webm|ogg|mp3|wav|flac|aac)(\?.*)?$/,
loader: 'url-loader',
options: {
limit: 10000,
name: utils.assetsPath('media/[name].[hash:7].[ext]')
}
},
{
test: /\.(woff2?|eot|ttf|otf)(\?.*)?$/,
loader: 'url-loader',
options: {
limit: 10000,
name: utils.assetsPath('fonts/[name].[hash:7].[ext]')
}
}
]
}
}
EDIT: I've updated this file to look like:
var path = require('path')
var utils = require('./utils')
var config = require('../config')
var vueLoaderConfig = require('./vue-loader.conf')
function resolve (dir) {
return path.join(__dirname, '..', dir)
}
const ExtractTextPlugin = require('extract-text-webpack-plugin')
const extractCSS = new ExtractTextPlugin({ filename: 'css.bundle.css' })
const extractSASS = new ExtractTextPlugin({ filename: 'sass.bundle.css' })
module.exports = {
entry: {
app: './src/main.js'
},
output: {
path: config.build.assetsRoot,
filename: '[name].js',
publicPath: process.env.NODE_ENV === 'production'
? config.build.assetsPublicPath
: config.dev.assetsPublicPath
},
resolve: {
extensions: ['.js', '.vue', '.json'],
alias: {
'vue$': 'vue/dist/vue.esm.js',
'#': resolve('src')
}
},
module: {
// loaders: [
// { test: /\.css$/, loader: "style-loader!css-loader" }
// ],
rules: [
{
test: /\.vue$/,
loader: 'vue-loader',
options: vueLoaderConfig
},
{
test: /\.js$/,
loader: 'babel-loader',
include: [resolve('src'), resolve('test')]
},
{
test: /\.css$/,
use: extractCSS.extract({ // Instance 1
fallback: 'style-loader!css-loader',
use: [ 'css-loader' ]
})
},
{
test: /\.scss$/,
use: extractSASS.extract({ // Instance 2
fallback: 'style-loader',
use: [ 'css-loader', 'sass-loader' ]
})
},
{
test: /\.(png|jpe?g|gif|svg)(\?.*)?$/,
loader: 'url-loader',
options: {
limit: 10000,
name: utils.assetsPath('img/[name].[hash:7].[ext]')
}
},
{
test: /\.(mp4|webm|ogg|mp3|wav|flac|aac)(\?.*)?$/,
loader: 'url-loader',
options: {
limit: 10000,
name: utils.assetsPath('media/[name].[hash:7].[ext]')
}
},
{
test: /\.(woff2?|eot|ttf|otf)(\?.*)?$/,
loader: 'url-loader',
options: {
limit: 10000,
name: utils.assetsPath('fonts/[name].[hash:7].[ext]')
}
}
]
},
plugins: [
extractCSS,
extractSASS
]
}
but when I require the .css: require("./assets/now-ui-kit.css"); I see the following:
error in ./src/assets/now-ui-kit.css
Module build failed: ModuleBuildError: Module build failed: Unknown word (5:1)
3 | // load the styles
4 | var content = require("!!../../node_modules/css-loader/index.js?{\"minimize\":false,\"sourceMap\":false}!./now-ui-kit.css");
> 5 | if(typeof content === 'string') content = [[module.id, content, '']];
| ^
6 | if(content.locals) module.exports = content.locals;
7 | // add the styles to the DOM
8 | var update = require("!../../node_modules/vue-style-loader/lib/addStylesClient.js")("94a1c16e", content, false);

It doesn't look like you have any css loader in your webpack config file. Add the following imports, rules and plugins to your file to accomplish the css bundling:
const ExtractTextPlugin = require('extract-text-webpack-plugin')
const extractCSS = new ExtractTextPlugin({ filename: 'css.bundle.css' })
const extractSASS = new ExtractTextPlugin({ filename: 'sass.bundle.css' })
const config = {
module: {
rules: [
{
test: /\.css$/,
use: extractCSS.extract({ // Instance 1
fallback: 'style-loader',
use: [ 'css-loader' ]
})
},
{
test: /\.scss$/,
use: extractSASS.extract({ // Instance 2
fallback: 'style-loader',
use: [ 'css-loader', 'sass-loader' ]
})
}
]
},
plugins: [
extractCSS // Instance 1
extractSASS // Instance 2
]
}
Here is where I took the code snippet from and here is the webpack css documentation.

Related

Bootstrap not applying CSS using Webpack

I'm using Bootstrap with webpack, but when I run my app, no Bootstrap and no CSS is applied.
This is my webpack.config.js :
const path = require('path');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const { CleanWebpackPlugin } = require('clean-webpack-plugin');
const ManifestPlugin = require('webpack-manifest-plugin');
const UglifyJsPlugin = require('uglifyjs-webpack-plugin');
var OptimizeCSSAssetsPlugin = require('optimize-css-assets-webpack-plugin');
const MiniCssExtractPlugin = require("mini-css-extract-plugin");
module.exports = {
// mode: 'production',
entry: './src/index.js',
output: {
path: path.resolve(__dirname, 'build'),
publicPath: '',
filename: 'bundle.js'
},
devServer: {
contentBase: path.join(__dirname, './build'),
compress: true,
port: 3000
},
performance: {
maxEntrypointSize: 512000,
maxAssetSize: 512000
},
module: {
rules: [
{
test: /\.s?css$/,
use: [
{
loader: "file-loader",
options: {
name: "[name].css"
}
},
{
loader: "extract-loader"
},
{
loader: "css-loader",
},
{
loader: "sass-loader"
}
]
},
{
test: /\.(js|jsx)$/,
exclude: /node_modules/,
use: {
loader: "babel-loader"
}
},
{
test: /\.(png|svg|jpg|gif)$/,
use: ["file-loader"]
},
{
test: /\.(woff(2)?|ttf|otf|eot|svg)(\?v=\d+\.\d+\.\d+)?$/,
use: [
{
loader: 'file-loader',
options: {
name: '[name].[ext]',
outputPath: 'fonts/'
}
}
]
}
]
},
//remove comments from JS files
optimization: {
minimizer: [
new UglifyJsPlugin({
uglifyOptions: {
output: {
comments: false,
},
},
}),
new OptimizeCSSAssetsPlugin({
cssProcessorPluginOptions: {
preset: ['default', { discardComments: { removeAll: true } }],
}
})
],
},
plugins: [
new MiniCssExtractPlugin({
filename: "[name].css"
}),
new ManifestPlugin(),
new CleanWebpackPlugin(),
new HtmlWebpackPlugin({
template: path.resolve('./public/index.html'),
}),
]
};
I have this kind of error in brower console :
Uncaught Error: Module build failed (from ./node_modules/mini-css-extract-plugin/dist/loader.js):
ModuleBuildError: Module build failed (from ./node_modules/css-loader/dist/cjs.js):
CssSyntaxError
(192:1) Unknown word
I don't have an idea where this error comes from.
Below two versions of dev/prod and all the code you can see here webpack-boilerplate
Dev:
{
test: /\.(css|sass|scss)$/,
use: [
'style-loader',
{
loader: 'css-loader',
options: {
importLoaders: 2,
sourceMap: true
},
},
{
loader: 'sass-loader',
options: {
sourceMap: true,
},
}
],
},
Prod:
{
test: /\.(css|sass|scss)$/,
use: [
MiniCssExtractPlugin.loader,
{
loader: 'css-loader',
options: {
sourceMap: true,
importLoaders: 2
},
},
{
loader: 'sass-loader',
options: {
sourceMap: true,
},
},
],
},

Compile sass files to hashed css using webpack

to compile my .scss files I use webpack.
What i want to achieve is to get for example
styles.b0eda78ad870282c8cb9fd58884415d7.css
instead of
styles.css
When I add to webpack option [hash] (now commented in source) - then every change in .scss files generate new .css files. For example 3 changes in .scss will generate 3 new files with different hashes:
themeA.b0eda78ad870282c8cb9fd58884415d7.css
themeA.2c0521243fe51696a6d08ae5443a6721.css
themeA.6ebd2d65f4d311fbac8441141826a9a8.css
I want only to update one css file with new hash and do not create new files.
My webpack configuration
const themeA = `${mainDirectory}/commons/themeA.scss`;
const themeB = `${mainDirectory}/commons/scss/shop/themeB.scss`;
const themeC = `${mainDirectory}/commons/themeC.scss`;
const themeD = `${mainDirectory}/commons/scss/shop/themeD.scss`;
let sassFiles;
const themeMap = new Map([
['a', themeA],
['b', themeB],
['c', themeC],
['d', themeD],
]);
if (theme === undefined) {
sassFiles = [...themeMap.values()];
} else {
sassFiles = [
`${mainDirectory}/commons/${theme}.scss`,
`${mainDirectory}/commons/scss/shop/${theme}_shop.scss`,
];
}
module.exports = {
entry: [...sassFiles],
mode: 'development',
output: {
path: path.resolve(mainDirectory, 'commons'),
filename: 'hot/sassBundle.js',
publicPath: '/',
},
module: {
rules: [
{
test: /\.scss$/,
sideEffects: true,
use: [
{
loader: 'file-loader',
options: {
minimize: true,
name: '[name].css',
// hashed css
// name: '[name].[hash].css',
outputPath: '/css',
},
},
{
loader: 'extract-loader',
},
{
loader: 'css-loader',
options: {
url: false,
sourceMap: !buildMode,
},
},
{
loader: 'postcss-loader',
options: {
sourceMap: !buildMode,
},
},
{
loader: 'sass-loader',
options: {
sourceMap: !buildMode,
convertToAbsoluteUrls: false,
},
},
],
},
{
test: /\.(png|jpg|gif|svg)$/,
loader: 'file-loader',
},
{
test: /\.(woff|woff2|eot|ttf)$/,
loader: 'url-loader?limit=100000',
},
],
},
plugins: [
new webpack.SourceMapDevToolPlugin({}),
new ReplaceInFileWebpackPlugin([
{
dir: `${mainDirectory}/commons/css/`,
test: [/\.css$/],
rules: [
{
search: /\/\*# sourceURL.+\\*/g,
replace: '',
},
],
},
]),
],
};

Webpack don't extract css to general file from vue components from node_modules

When configuring Webpack 4 to work with vue components connected from the node_modules folder, css is not going to the general "app.css" file. But at the same time of the components which I have written is going. How to change the config so that styles from all components are collected in one file?
component connection example
import vSelect from 'vue-select';
Vue.component('v-select', vSelect);
webpack.common.js
const path = require('path');
const MiniCssExtractPlugin = require("mini-css-extract-plugin");
const VueLoaderPlugin = require('vue-loader/lib/plugin');
const devMode = process.env.NODE_ENV !== 'production';
module.exports = {
entry: ['./src/js/app.js', './src/sass/app.scss'],
module: {
rules: [{
test: /\.(png|jpeg|jpg|gif|svg)$/,
loader: 'file-loader',
options: {
outputPath: 'resources',
name: '[folder]/[name].[ext]',
}
},
{
test: /\.(eot|ttf|woff|woff2)$/,
loader: 'file-loader',
options: {
outputPath: 'resources/fonts',
name: '[folder]/[name].[ext]',
}
},
{
test: /\.css$/,
use: [
devMode ? 'style-loader' : MiniCssExtractPlugin.loader,
{
loader: 'css-loader',
options: {
sourceMap: true
}
},
"postcss-loader",
],
},
{
test: /\.scss$/,
use: [
devMode ? 'style-loader' : MiniCssExtractPlugin.loader,
{
loader: 'css-loader',
options: {
sourceMap: true
}
},
"postcss-loader",
{
loader: 'sass-loader',
options: {
sourceMap: true
}
},
],
},
{
test: /\.sass$/,
use: [
devMode ? 'style-loader' : MiniCssExtractPlugin.loader,
{
loader: 'css-loader',
options: {
sourceMap: true
}
},
"postcss-loader",
{
loader: 'sass-loader',
options: {
indentedSyntax: true,
sourceMap: true
}
},
],
},
{
test: /\.vue$/,
loader: 'vue-loader',
options: {
esModule: true,
extractCss: true,
}
},
{
test: /\.js$/,
use: 'babel-loader',
exclude: /node_modules/,
}
]
},
resolve: {
alias: {
'vue$': 'vue/dist/vue.common.js',
'res': path.join(__dirname, './src/resources'),
'root': path.join(__dirname, './src/js')
},
extensions: ['*', '.js', '.vue', '.json']
},
plugins: [
new MiniCssExtractPlugin({
filename: "css/app.css",
}),
new VueLoaderPlugin()
],
}
webpack.dev.js
const path = require('path');
const merge = require('webpack-merge');
const common = require('./webpack.common.js');
module.exports = merge(common, {
output: {
path: path.resolve(__dirname, './dist'),
filename: 'js/app.js',
publicPath: '/',
chunkFilename: 'js/[name].js'
},
mode: 'development',
devtool: 'inline-source-map',
devServer: {
historyApiFallback: true,
noInfo: true,
overlay: true
},
});
webpack.prod.js
const OptimizeCSSAssetsPlugin = require("optimize-css-assets-webpack-plugin");
const UglifyJsPlugin = require('uglifyjs-webpack-plugin');
const path = require('path');
const merge = require('webpack-merge');
const common = require('./webpack.common.js');
module.exports = merge(common, {
output: {
path: path.resolve(__dirname, '.././static'),
filename: 'js/app.js',
publicPath: '/static/',
chunkFilename: 'js/[name].js'
},
mode: 'production',
devtool: 'source-map',
optimization: {
minimizer: [
new OptimizeCSSAssetsPlugin({}),
new UglifyJsPlugin({
sourceMap: true,
})
]
},
});

How to resolve #import with Webpack3

I'm trying to add semantic-ui-css to my React application. But, I'm receiving this error message:
"Invalid or unexpected token".
The traceback indicates an issue parsing the #import. Any thoughts or suggestions would be greatly appreciated.
Also, I realize many other people have had this problem, but haven't found a solution on Stack that works yet. Full source is available here: https://github.com/lgants/django-react-ssr.
frontend/webpack.client.base.config.js
var path = require('path');
var webpack = require('webpack');
var BundleTracker = require('webpack-bundle-tracker');
var CleanWebpackPlugin = require('clean-webpack-plugin');
var ExtractTextPlugin = require('extract-text-webpack-plugin');
module.exports = {
entry: './src/client/index.js',
output: {
filename: '[name]-[hash].js',
publicPath: '/static/js/',
path: path.resolve(__dirname, '../backend/app/static/js/')
},
// tells webpack to run babel on every file it runs through
resolve: {
extensions: ['.js', '.jsx', '.json']
},
module: {
rules: [
{
test: /\.(js|jsx)$/,
loader: 'babel-loader',
exclude: /node_modules/,
options: {
presets: [
'react',
'stage-0',
['env', { targets: { browsers: ['last 2 versions'] } }]
]
}
},
{
test: /\.(png|gif)$/,
loader: 'url-loader?limit=1024&name=[name]-[hash:8].[ext]!image-webpack-loader'
},
{
test: /\.jpg$/,
loader: 'file-loader'
},
{
test: /\.css$/,
use: [
'style-loader',
'css-loader'
]
},
{
test: /\.(sass|scss)$/,
loader: ExtractTextPlugin.extract({ use: 'style-loader!css-loader!sass-loader' })
},
{
test: /\.less$/,
use: [
'style-loader',
'css-loader',
'less-loader'
]
},
{
test: /\.(ttf|eot|svg|woff2?)(\?v=[0-9]\.[0-9]\.[0-9])?$/,
loader: 'file-loader'
}
]
},
plugins: [
new BundleTracker(
{
filename: './webpack-stats.client.json'
}
),
new CleanWebpackPlugin([
'backend/app/static/js/main-*.*', 'backend/app/static/js/*.hot-update.*'
],
{
dry: false,
root: path.resolve(__dirname, '..'),
watch: true
}
)
]
};
frontend/webpack.client.dev.config.js
var path = require('path');
var merge = require('webpack-merge');
var webpack = require('webpack');
var baseConfig = require('./webpack.client.base.config.js');
var CleanWebpackPlugin = require('clean-webpack-plugin');
const config = {
plugins: [
new webpack.HotModuleReplacementPlugin(),
]
};
module.exports = merge(baseConfig, config);

Getting webpack style loader to let me import css within my components

I'm currently messing around with https://github.com/sahat/megaboilerplate and trying to get it such that I can import css from within my components.
Here's my config:
const path = require('path');
const webpack = require('webpack');
var config = {
devtool: 'cheap-module-eval-source-map',
entry: [
'webpack-hot-middleware/client',
'./app/main'
],
output: {
path: path.join(__dirname, 'public', 'js'),
filename: 'bundle.js',
publicPath: '/js'
},
plugins: [
new webpack.HotModuleReplacementPlugin(),
new webpack.NoEmitOnErrorsPlugin(),
new webpack.optimize.OccurrenceOrderPlugin(),
new webpack.DefinePlugin({
'process.env.NODE_ENV': JSON.stringify(process.env.NODE_ENV)
}),
],
module: {
loaders: [
{
test: /\.css$/,
use: [
{ loader: "style-loader" },
{ loader: "css-loader" },
],
}, {
test: /\.js$/,
exclude: /node_modules/,
loader: 'babel-loader',
query: {
plugins: [
['react-transform', {
transforms: [
{
transform: 'react-transform-hmr',
imports: ['react'],
locals: ['module']
}, {
transform: 'react-transform-catch-errors',
imports: ['react', 'redbox-react']
}
]
}]
]
}
}
]
}
};
if (process.env.NODE_ENV === 'production') {
config.plugins.push(
new webpack.optimize.UglifyJsPlugin({
compressor: {
screw_ie8: true,
warnings: false
}
})
);
}
module.exports = config;
As you can see from the original config:
https://github.com/sahat/megaboilerplate/blob/master/webpack.config.js
I've added:
test: /\.css$/,
use: [
{ loader: "style-loader" },
{ loader: "css-loader" },
],
But when I run the server, I get:
/megaboiler/node_modules/spectre.css/dist/spectre.min.css:1
(function (exports, require, module, __filename, __dirname) { /*! Spectre.css | MIT License | github.com/picturepan2/spectre */html{font-family:sans-serif;line-height:1.15;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%}body{margin:0}article,aside,footer,header,nav,section{display:block}h1{font-size:2em;margin:.67em 0}figcaption,figure,main{display:block}hr{box-sizing:content-box;height:0;overflow:visible}a{background-color:transparent;-webkit-text-decoration-skip:objects}a:active,a:hover{outline-width:0}b,strong{font-weight:inherit}b,strong{font-weight:bolder}code,kbd,pre,samp{font-family:monospace,monospace;font-size:1em}dfn{font-style:italic}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}audio,video{display:inline-block}audio:not([controls]){display:none;height:0}img{border-style:none}svg:not(:root){overflow:hidden}button,input
SyntaxError: Unexpected token {
What am I missing?
Your test: /\.css$/ is now.
use: [
{ loader: "style-loader" },
{ loader: "css-loader" },
],
Seems that you may miss some loaders which can handle your files correctly, remember each loader has it's limits what it can process.
use: [
'raw-loader',
'style-loader',
'css-loader',
'postcss-loader',
'resolve-url-loader',
]

Resources