2020-01-28 08:30:39 +01:00
const fastGlob = require ( 'fast-glob' ) ;
2020-06-12 13:26:37 +02:00
const wrapAnsi = require ( 'wrap-ansi' ) ;
2020-08-22 03:23:03 +02:00
const AddAssetPlugin = require ( 'add-asset-webpack-plugin' ) ;
2020-08-12 00:30:47 +02:00
const CssMinimizerPlugin = require ( 'css-minimizer-webpack-plugin' ) ;
2020-12-27 15:24:27 +01:00
const LicenseCheckerWebpackPlugin = require ( 'license-checker-webpack-plugin' ) ;
2020-01-25 09:41:34 +01:00
const MiniCssExtractPlugin = require ( 'mini-css-extract-plugin' ) ;
2020-05-14 18:06:01 +02:00
const MonacoWebpackPlugin = require ( 'monaco-editor-webpack-plugin' ) ;
2020-01-28 08:30:39 +01:00
const TerserPlugin = require ( 'terser-webpack-plugin' ) ;
const VueLoaderPlugin = require ( 'vue-loader/lib/plugin' ) ;
2020-03-11 20:34:54 +01:00
const { statSync } = require ( 'fs' ) ;
const { resolve , parse } = require ( 'path' ) ;
const { SourceMapDevToolPlugin } = require ( 'webpack' ) ;
2020-01-28 08:30:39 +01:00
2020-03-11 20:34:54 +01:00
const glob = ( pattern ) => fastGlob . sync ( pattern , { cwd : _ _dirname , absolute : true } ) ;
2020-02-11 11:02:41 -06:00
2020-01-28 08:30:39 +01:00
const themes = { } ;
2020-02-11 11:02:41 -06:00
for ( const path of glob ( 'web_src/less/themes/*.less' ) ) {
2020-01-28 08:30:39 +01:00
themes [ parse ( path ) . name ] = [ path ] ;
}
2019-11-13 22:52:13 +08:00
2020-02-23 09:47:42 +01:00
const isProduction = process . env . NODE _ENV !== 'development' ;
2020-07-27 23:01:25 +02:00
const filterCssImport = ( url , ... args ) => {
const cssFile = args [ 1 ] || args [ 0 ] ; // resourcePath is 2nd argument for url and 3rd for import
2020-06-28 04:59:56 +02:00
const importedFile = url . replace ( /[?#].+/ , '' ) . toLowerCase ( ) ;
2020-07-06 10:56:54 +02:00
2020-06-28 04:59:56 +02:00
if ( cssFile . includes ( 'fomantic' ) ) {
if ( /brand-icons/ . test ( importedFile ) ) return false ;
2020-07-12 11:10:56 +02:00
if ( /(eot|ttf|otf|woff|svg)$/ . test ( importedFile ) ) return false ;
2020-07-06 10:56:54 +02:00
}
2020-12-27 15:24:27 +01:00
if ( cssFile . includes ( 'font-awesome' ) && /(eot|ttf|otf|woff|svg)$/ . test ( importedFile ) ) {
return false ;
2020-06-28 04:59:56 +02:00
}
2020-07-06 10:56:54 +02:00
return true ;
2020-06-28 04:59:56 +02:00
} ;
2019-11-13 22:52:13 +08:00
module . exports = {
2020-02-23 09:47:42 +01:00
mode : isProduction ? 'production' : 'development' ,
2019-11-13 22:52:13 +08:00
entry : {
2020-01-28 08:30:39 +01:00
index : [
2020-06-28 04:59:56 +02:00
resolve ( _ _dirname , 'web_src/js/jquery.js' ) ,
resolve ( _ _dirname , 'web_src/fomantic/build/semantic.js' ) ,
2020-01-28 08:30:39 +01:00
resolve ( _ _dirname , 'web_src/js/index.js' ) ,
2020-06-28 04:59:56 +02:00
resolve ( _ _dirname , 'web_src/fomantic/build/semantic.css' ) ,
2020-01-28 08:30:39 +01:00
resolve ( _ _dirname , 'web_src/less/index.less' ) ,
] ,
swagger : [
2020-02-07 18:09:30 +01:00
resolve ( _ _dirname , 'web_src/js/standalone/swagger.js' ) ,
2020-08-26 19:42:46 +02:00
resolve ( _ _dirname , 'web_src/less/standalone/swagger.less' ) ,
2020-01-28 08:30:39 +01:00
] ,
2020-05-22 03:45:34 +02:00
serviceworker : [
resolve ( _ _dirname , 'web_src/js/serviceworker.js' ) ,
] ,
2020-07-03 10:55:36 +01:00
'eventsource.sharedworker' : [
resolve ( _ _dirname , 'web_src/js/features/eventsource.sharedworker.js' ) ,
] ,
2020-11-10 19:16:30 +00:00
'easymde' : [
resolve ( _ _dirname , 'web_src/js/easymde.js' ) ,
resolve ( _ _dirname , 'node_modules/easymde/dist/easymde.min.css' ) ,
] ,
2020-01-28 08:30:39 +01:00
... themes ,
2019-11-13 22:52:13 +08:00
} ,
2020-01-14 19:02:08 +01:00
devtool : false ,
2019-11-13 22:52:13 +08:00
output : {
2020-01-28 08:30:39 +01:00
path : resolve ( _ _dirname , 'public' ) ,
2020-05-22 03:45:34 +02:00
filename : ( { chunk } ) => {
// serviceworker can only manage assets below it's script's directory so
// we have to put it in / instead of /js/
2020-05-23 14:58:58 +01:00
return chunk . name === 'serviceworker' ? '[name].js' : 'js/[name].js' ;
2020-05-22 03:45:34 +02:00
} ,
2020-12-27 15:24:27 +01:00
chunkFilename : ( { chunk } ) => {
const language = ( /monaco.*languages?_.+?_(.+?)_/ . exec ( chunk . id ) || [ ] ) [ 1 ] ;
return language ? ` js/monaco-language- ${ language . toLowerCase ( ) } .js ` : ` js/[name].js ` ;
} ,
2019-11-13 22:52:13 +08:00
} ,
optimization : {
2020-02-23 09:47:42 +01:00
minimize : isProduction ,
2020-01-25 09:41:34 +01:00
minimizer : [
new TerserPlugin ( {
extractComments : false ,
terserOptions : {
output : {
comments : false ,
} ,
2019-11-17 22:39:06 +01:00
} ,
2020-01-25 09:41:34 +01:00
} ) ,
2020-08-12 00:30:47 +02:00
new CssMinimizerPlugin ( {
2020-06-28 04:59:56 +02:00
sourceMap : true ,
2020-08-12 00:30:47 +02:00
minimizerOptions : {
2020-01-25 09:41:34 +01:00
preset : [
'default' ,
{
discardComments : {
removeAll : true ,
} ,
} ,
] ,
} ,
} ) ,
] ,
2020-01-28 22:57:20 +01:00
splitChunks : {
chunks : 'async' ,
name : ( _ , chunks ) => chunks . map ( ( item ) => item . name ) . join ( '-' ) ,
2020-06-28 04:59:56 +02:00
} ,
2020-12-27 15:24:27 +01:00
moduleIds : 'named' ,
chunkIds : 'named' ,
2019-11-13 22:52:13 +08:00
} ,
2019-11-14 22:39:51 +01:00
module : {
rules : [
2020-01-20 12:07:30 +02:00
{
test : /\.vue$/ ,
exclude : /node_modules/ ,
2020-01-25 09:41:34 +01:00
loader : 'vue-loader' ,
2020-01-20 12:07:30 +02:00
} ,
2020-04-13 15:02:31 +02:00
{
test : /\.worker\.js$/ ,
2020-05-14 18:06:01 +02:00
exclude : /monaco/ ,
2020-04-13 15:02:31 +02:00
use : [
{
loader : 'worker-loader' ,
options : {
2020-08-12 00:30:47 +02:00
inline : 'no-fallback' ,
2020-04-13 15:02:31 +02:00
} ,
} ,
] ,
} ,
2019-11-14 22:39:51 +01:00
{
test : /\.js$/ ,
exclude : /node_modules/ ,
2020-01-22 07:35:29 +01:00
use : [
{
loader : 'babel-loader' ,
options : {
2020-09-10 06:16:40 +02:00
sourceMaps : true ,
2020-02-01 16:12:41 +01:00
cacheDirectory : true ,
cacheCompression : false ,
cacheIdentifier : [
resolve ( _ _dirname , 'package.json' ) ,
resolve ( _ _dirname , 'package-lock.json' ) ,
resolve ( _ _dirname , 'webpack.config.js' ) ,
] . map ( ( path ) => statSync ( path ) . mtime . getTime ( ) ) . join ( ':' ) ,
2020-01-22 07:35:29 +01:00
presets : [
[
'@babel/preset-env' ,
{
useBuiltIns : 'usage' ,
corejs : 3 ,
2020-01-25 09:41:34 +01:00
} ,
] ,
2020-01-20 12:07:30 +02:00
] ,
2020-01-22 07:35:29 +01:00
plugins : [
[
'@babel/plugin-transform-runtime' ,
{
regenerator : true ,
}
] ,
] ,
2020-06-28 04:59:56 +02:00
generatorOpts : {
compact : false ,
} ,
2020-01-25 09:41:34 +01:00
} ,
2020-01-22 07:35:29 +01:00
} ,
] ,
2019-11-17 22:39:06 +01:00
} ,
{
2020-06-28 04:59:56 +02:00
test : /.css$/i ,
use : [
{
loader : MiniCssExtractPlugin . loader ,
} ,
{
loader : 'css-loader' ,
options : {
2020-09-10 06:16:40 +02:00
sourceMap : true ,
2020-06-28 04:59:56 +02:00
url : filterCssImport ,
import : filterCssImport ,
} ,
} ,
] ,
} ,
{
test : /.less$/i ,
2020-01-25 09:41:34 +01:00
use : [
{
loader : MiniCssExtractPlugin . loader ,
} ,
{
loader : 'css-loader' ,
options : {
2020-09-10 06:16:40 +02:00
sourceMap : true ,
2020-10-19 22:01:06 +02:00
importLoaders : 1 ,
2020-06-28 04:59:56 +02:00
url : filterCssImport ,
import : filterCssImport ,
} ,
2020-01-25 09:41:34 +01:00
} ,
2020-01-28 08:30:39 +01:00
{
loader : 'less-loader' ,
2020-06-28 04:59:56 +02:00
options : {
sourceMap : true ,
} ,
2020-01-28 08:30:39 +01:00
} ,
2020-01-25 09:41:34 +01:00
] ,
2019-11-17 22:39:06 +01:00
} ,
2020-02-11 11:02:41 -06:00
{
test : /\.svg$/ ,
2020-07-12 11:10:56 +02:00
include : resolve ( _ _dirname , 'public/img/svg' ) ,
2020-02-11 11:02:41 -06:00
use : [
{
2020-07-12 11:10:56 +02:00
loader : 'raw-loader' ,
2020-02-11 11:02:41 -06:00
} ,
] ,
} ,
2020-05-14 18:06:01 +02:00
{
test : /\.(ttf|woff2?)$/ ,
use : [
{
loader : 'file-loader' ,
options : {
name : '[name].[ext]' ,
outputPath : 'fonts/' ,
2020-07-29 20:44:23 +02:00
publicPath : ( url ) => ` ../fonts/ ${ url } ` , // required to remove css/ path segment
} ,
} ,
] ,
} ,
{
test : /\.png$/i ,
use : [
{
loader : 'file-loader' ,
options : {
name : '[name].[ext]' ,
outputPath : 'img/webpack/' ,
publicPath : ( url ) => ` ../img/webpack/ ${ url } ` , // required to remove css/ path segment
2020-05-14 18:06:01 +02:00
} ,
} ,
] ,
} ,
2020-01-25 09:41:34 +01:00
] ,
2020-01-14 19:02:08 +01:00
} ,
plugins : [
2020-01-20 12:07:30 +02:00
new VueLoaderPlugin ( ) ,
2020-01-25 09:41:34 +01:00
new MiniCssExtractPlugin ( {
filename : 'css/[name].css' ,
chunkFilename : 'css/[name].css' ,
} ) ,
2020-01-14 19:02:08 +01:00
new SourceMapDevToolPlugin ( {
2020-06-28 04:59:56 +02:00
filename : '[file].map' ,
2020-01-28 22:57:20 +01:00
include : [
'js/index.js' ,
2020-06-28 04:59:56 +02:00
'css/index.css' ,
2020-01-14 19:02:08 +01:00
] ,
} ) ,
2020-05-14 18:06:01 +02:00
new MonacoWebpackPlugin ( {
filename : 'js/monaco-[name].worker.js' ,
} ) ,
2020-12-27 15:24:27 +01:00
isProduction ? new LicenseCheckerWebpackPlugin ( {
2020-06-12 13:26:37 +02:00
outputFilename : 'js/licenses.txt' ,
2020-12-27 15:24:27 +01:00
outputWriter : ( { dependencies } ) => {
2020-06-12 13:26:37 +02:00
const line = '-' . repeat ( 80 ) ;
2020-12-27 15:24:27 +01:00
return dependencies . map ( ( module ) => {
const { name , version , licenseName , licenseText } = module ;
2020-06-12 13:26:37 +02:00
const body = wrapAnsi ( licenseText || '' , 80 ) ;
2020-12-27 15:24:27 +01:00
return ` ${ line } \n ${ name } @ ${ version } - ${ licenseName } \n ${ line } \n ${ body } ` ;
2020-06-12 13:26:37 +02:00
} ) . join ( '\n' ) ;
} ,
2020-12-27 15:24:27 +01:00
override : {
'jquery.are-you-sure@*' : { licenseName : 'MIT' } ,
2020-06-12 13:26:37 +02:00
} ,
2020-08-22 03:23:03 +02:00
} ) : new AddAssetPlugin ( 'js/licenses.txt' , ` Licenses are disabled during development ` ) ,
2020-01-14 19:02:08 +01:00
] ,
performance : {
2020-03-17 23:57:17 +01:00
hints : false ,
2020-05-14 18:06:01 +02:00
maxEntrypointSize : Infinity ,
maxAssetSize : Infinity ,
2020-01-14 19:02:08 +01:00
} ,
2020-01-22 07:35:29 +01:00
resolve : {
symlinks : false ,
2020-02-23 22:34:28 +01:00
alias : {
vue$ : 'vue/dist/vue.esm.js' , // needed because vue's default export is the runtime only
} ,
2020-01-25 09:41:34 +01:00
} ,
2020-02-23 09:47:42 +01:00
watchOptions : {
ignored : [
'node_modules/**' ,
] ,
} ,
2020-05-14 18:06:01 +02:00
stats : {
2020-12-27 15:24:27 +01:00
assetsSort : 'name' ,
assetsSpace : Infinity ,
cached : false ,
cachedModules : false ,
2020-05-14 18:06:01 +02:00
children : false ,
2020-12-27 15:24:27 +01:00
chunkModules : false ,
chunkOrigins : false ,
chunksSort : 'name' ,
colors : true ,
entrypoints : false ,
2020-08-02 16:06:06 +02:00
excludeAssets : [
2020-12-27 15:24:27 +01:00
/^js\/monaco-language-.+\.js$/ ,
! isProduction && /^js\/licenses.txt$/ ,
] . filter ( ( item ) => ! ! item ) ,
groupAssetsByChunk : false ,
groupAssetsByEmitStatus : false ,
groupAssetsByInfo : false ,
groupModulesByAttributes : false ,
modules : false ,
reasons : false ,
runtimeModules : false ,
2020-05-14 18:06:01 +02:00
} ,
2019-11-13 22:52:13 +08:00
} ;