I'm trying to get grunt working to do something. My project looks like this:
/app
/assets
/components
/stylesheets
/less
/file1.less
/file2.less
/file3.less
/importAll.less
/css
I want it so that when file1, file2, or file3 are saved the importAll.less file is compiled into css and put into /css/style.css. This is as far as I got.
less: {
development: {
options: {
paths: ["./assets/stylesheets/less"],
yuicompress: true
},
files: {
"./assets/stylesheets/css/style.css": "./assets/stylesheets/less/importAll.less"
}
}
}
I'm not sure how to get the file watcher working.
I got it working with the following!
module.exports = function(grunt) {
grunt.initConfig({
less: {
development: {
options: {
paths: ["./assets/stylesheets/less"],
yuicompress: true
},
files: {
"./assets/stylesheets/css/style.css": "./assets/stylesheets/less/style.less"
}
}
},
watch: {
files: "./assets/stylesheets/less/*",
tasks: ["less"]
}
});
grunt.loadNpmTasks('grunt-contrib-less');
grunt.loadNpmTasks('grunt-contrib-watch');
};
Related
I have just created a new CRA app. In our organization we have a micro frontend framework which has certain requirements when it comes to the the asset file of each micro frontend app. CRA will by default, create a asset-manifest.json file.
https://github.com/facebook/create-react-app/blob/main/packages/react-scripts/config/webpack.config.js#L656
Now I need to change this file to assets.json and make some structural changes as well. To achieve this I use CRACO and add the WebpackManifestPlugin.
const ManifestPlugin = require('webpack-manifest-plugin');
module.exports = {
webpack: {
plugins: {
// tried removing CRA definition for ManifestPlugin.
// It worked, but had no impact on my problem
// remove: ['ManifestPlugin'],
add: [
new ManifestPlugin({
fileName: 'assets.json',
generate: (seed, files, entrypoints) => {
const js = [],
css = [];
files.forEach((file) => {
if (file.path.endsWith('.js') && file.isInitial) {
js.push({ value: file.path, type: 'entry' });
}
if (file.path.endsWith('.css') && file.isInitial) {
css.push({ value: file.path, type: 'entry' });
}
});
return { js, css };
},
})
]
}
}
};
Whenever I build the application, my new assets.json file is generated as expected.
However, I can't get CRA, or webpack-dev-server I assume, to serve this file while I run my CRA app in development mode. It only resolves to the index.html file. I have looked through CRA source code and can't really find any relevant place where asset-manifest.json is mentioned.
So how do I get webpack-dev-server to serve my assets.json file?
You need to add the ManifestPlugin to webpack.plugins.remove array to receive only the configuration from WebpackManifestPlugin:
...
webpack: {
alias: {},
plugins: {
add: [
new WebpackManifestPlugin(webpackManifestConfig)
],
remove: [
"ManifestPlugin"
],
},
configure: (webpackConfig, { env, paths }) => { return webpackConfig; }
},
...
I have a vue project and I use vue-cli-service build to build the project for production.
I noticed by default when I build the files, the resource name are having some kind of version code like
app.34fc5700.js
chunk-vendors.c7da5824.js
Is there a way to get rid of it?
I'm using vue.config.js, there's no webpack.conf.js in my project, and this is how it looks like:
module.exports = {
publicPath: process.env.VUE_APP_ROOT_PATH,
outputDir: process.env.VUE_APP_BUILD_DIR,
chainWebpack: config => {
config.resolve.symlinks(false);
config.plugin('html').init((Plugin, args) => {
const newArgs = {
...args[0],
};
newArgs.minify && (newArgs.minify.removeAttributeQuotes = false);
return new Plugin(newArgs);
});
},
css: {
loaderOptions: {
sass: {
additionalData: '#import "#/scss/_variables.scss";',
},
},
}
}
Looks like the option filenamehashing is something you need. Basically this option is enabled by default so you might need to turn it off:
// vue.config.js
module.exports = {
filenameHashing: false,
// ...
};
I'm using vue-cli 2.9.6, and created a vue project using vue init webpack <project name>.
When I call vue run build, it is creating a number of different js files (and names change each time...):
vendor.20d54e752692d648b42a.js
vendor.20d54e752692d648b42a.js.map
app.ed70f310595763347909.js
app.ed70f310595763347909.js.map
manifest.2ae2e69a05c33dfc65f8.js
manifest.2ae2e69a05c33dfc65f8.js.map
And also css files like this:
app.a670fcd1e9a699133143a2b144475068.css
app.a670fcd1e9a699133143a2b144475068.css.map
I would like the output to simply be 2 files:
build.js { for all js }
styles.css { for all css }
How can I achieve this?
for preventing creation of vendor.js and manifest.js just remove following code from webpack.prod.conf.js
// split vendor js into its own file
new webpack.optimize.CommonsChunkPlugin({
name: 'vendor',
minChunks (module) {
// any required modules inside node_modules are extracted to vendor
return (
module.resource &&
/\.js$/.test(module.resource) &&
module.resource.indexOf(
path.join(__dirname, '../node_modules')
) === 0
)
}
}),
// extract webpack runtime and module manifest to its own file in order to
// prevent vendor hash from being updated whenever app bundle is updated
new webpack.optimize.CommonsChunkPlugin({
name: 'manifest',
minChunks: Infinity
}),
To prevent sourceMaps set in config/index.js the variable productionSourceMap from true to false
Changing name of app.js to build.js can be obtained modifying the entry and outputproperties in webpack.base.conf.js this way:
entry: {
build: './src/main.js'
},
output: {
path: config.build.assetsRoot,
filename: utils.assetsPath('js/[name].js'),
chunkFilename: utils.assetsPath('js/[id].[chunkhash].js')
},
Update name of the css output file updating options of ExtractTextPluginin webpack.prod.conf.js to filename: utils.assetsPath('css/styles.css'),
// vue.config.js
module.exports = {
chainWebpack: config => {
if(config.plugins.has('extract-css')) {
const extractCSSPlugin = config.plugin('extract-css')
extractCSSPlugin && extractCSSPlugin.tap(() => [{
filename: 'styles.css',
chunkFilename: 'styles.css'
}])
}
},
configureWebpack: {
output: {
filename: 'build.js',
chunkFilename: 'build.js'
}
}
}
or
module.exports = {
configureWebpack: {
optimization: {
splitChunks: false
}
},
filenameHashing: false
}
I am new in using vue to build web app.
By default, use npm run build, it will build the following structure:
But I hope to build as follow:
Then, how can I write the vue.config.js as output like what I want?
Using this GitHub issue as an example, you should be able to achieve this by adding something like this to your configuration...
// vue.config.js
module.exports = {
chainWebpack: config => {
config.module.rule('images').use('url-loader')
.loader('file-loader') // replaces the url-loader
.tap(options => Object.assign(options, {
name: 'images/register/[name].[hash:8].[ext]'
}))
config.module.rule('svg').use('file-loader')
.tap(options => Object.assign(options, {
name: 'images/register/[name].[hash:8].[ext]'
}))
},
css: {
extract: {
filename: 'css/register/[name].[hash:8].css',
chunkFilename: 'css/register/[name].[hash:8].css'
}
},
configureWebpack: {
output: {
filename: 'js/register/[name].[hash:8].js',
chunkFilename: 'js/register/[name].[hash:8].js'
}
}
}
See https://cli.vuejs.org/config/#vue-config-js for more information and examples.
I'm having trouble using Grunt in a new Laravel project. At the moment I can't seem to configure/run grunt-contrib-watch correctly.
Directory Structure:
|-- app
|-- node_modules
|-- Gruntfile.js
|-- package.json
|-- public
|---- bower_components
|---- css
|------ dist
|------ header.css
|---- js
|------ dist
|------ app.js
And I have my Laravel project setup to find View files from the public folder in app/config/view.php:
'paths' => array(__DIR__.'/../../public'),
Laravel is installed and Apache is setup, and I'm trying to test a reload of changes using Grunt. Whenever I run grunt, it says "Running watch task" and "Waiting....", however, watch never appears to run UNLESS the file I edited was the Gruntfile itself.
Here's my Gruntfile:
module.exports = function(grunt) {
/* Config for Project */
grunt.initConfig({
pkg: grunt.file.readJSON('package.json'),
cssmin: {
dist: {
src: 'public/css/*.css',
dest: 'css/dist/main.min.css'
}
},
uglify: {
dist: {
src: ['public/js/*.js'],
dest: 'js/dist/app.min.js'
}
},
watch: {
js: {
files: ['**/*.js'],
tasks: ['uglify'],
options: {
reload: true
}
},
css: {
files: ['**/*.css'],
tasks: ['cssmin'],
options: {
reload: true
}
}
}
});
grunt.event.on('watch', function(action, filepath, target) {
grunt.log.writeln(target + ': ' + filepath + ' has ' + action);
});
grunt.loadNpmTasks('grunt-contrib-watch');
grunt.loadNpmTasks('grunt-contrib-cssmin');
grunt.loadNpmTasks('grunt-contrib-less');
grunt.loadNpmTasks('grunt-contrib-uglify');
// grunt.registerTask('buildcss', ['sass', 'cssc', 'cssmin']);
grunt.registerTask('default', ['watch',]);
};
Does anyone have an idea what I mis-configured / why watch isn't running?
your grunt:watch task is doing exactly what you are telling it to do. Here's the task commented
watch: {
// this means, whenever a .js file changes, run "grunt uglify"
js: {
files: ['**/*.js'],
tasks: ['uglify'],
options: {
reload: true
}
},
// this means, whenever a .css file changes, run "grunt cssmin"
css: {
files: ['**/*.css'],
tasks: ['cssmin'],
options: {
reload: true
}
}
}
There is no less compilation because you're not telling your grunt:watch to compile the less files when they change...
you'll need another plugin to compile your less files, check https://github.com/gruntjs/grunt-contrib-less, configure that plugin task and then add a new grunt:watch directive, that should look something like:
less: {
// this means, whenever a .less file changes, run 'grunt less'
files: ['**/*.less'],
tasks: ['less']
}
Hope this helps