refactor(assets): swap webpack for esbuild

- Remove all webpack and babel related npm dependencies
- Add esbuild and esbuild-plugin-postcss2 as a dependency
- Add a custom `build.js` script to build css and js with esbuild
  and copy static files to the priv/static directory
- Modify `config/dev.exs` to use that build script as a watcher instead
  of webpack
- Modify `package.json` to use that build script in instead of webpack
- Modify `KetbinWeb.Endpoint` to serve the assets directory instead of
  css and js directories from static
- Modify the `app.html.eex` layout to use `assets` directory instead of
  separate css and js directories

Signed-off-by: Akshit Garg <garg.akshit@gmail.com>
This commit is contained in:
Akshit Garg 2021-08-21 17:32:57 +05:30
parent 12ec98d15e
commit 3f5b1d10ac
No known key found for this signature in database
GPG Key ID: 31EE28F4B925E878
7 changed files with 419 additions and 7926 deletions

37
assets/build.js Normal file
View File

@ -0,0 +1,37 @@
const fs = require("fs-extra");
const esbuild = require("esbuild");
const { default: postCSSPlugin } = require("esbuild-plugin-postcss2");
// PostCSS Plugins
const autoprefixer = require("autoprefixer");
const tailwindcss = require("tailwindcss");
const postcssImport = require("postcss-import");
const productionBuild = process.env.NODE_ENV === "production";
fs.copySync("static/", "../priv/static/");
console.log("[build.js] [info] Copying static files from static/");
if (!productionBuild) {
console.log("[build.js] [info] Starting to watching assets for changes");
} else {
console.log("[build.js] [info] Building assets in production mode");
}
esbuild
.build({
entryPoints: ["js/app.js"],
bundle: true,
outfile: "../priv/static/assets/app.js",
minify: productionBuild,
watch: !productionBuild,
plugins: [
postCSSPlugin({
plugins: [postcssImport, tailwindcss, autoprefixer],
}),
],
})
.catch((e) => {
console.error(`[build.js] [error] ${e}`);
process.exit(1);
});

View File

@ -1,7 +1,7 @@
// We need to import the CSS so that webpack will load it. // We need to import the CSS so that webpack will load it.
// The MiniCssExtractPlugin is used to separate it out into // The MiniCssExtractPlugin is used to separate it out into
// its own CSS file. // its own CSS file.
import "../css/app.css" import "../css/app.css";
// webpack automatically bundles all modules in your // webpack automatically bundles all modules in your
// entry points. Those entry points can be configured // entry points. Those entry points can be configured
@ -12,4 +12,4 @@ import "../css/app.css"
// import {Socket} from "phoenix" // import {Socket} from "phoenix"
// import socket from "./socket" // import socket from "./socket"
// //
import "phoenix_html" import "phoenix_html";

8272
assets/package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -3,29 +3,20 @@
"description": " ", "description": " ",
"license": "MIT", "license": "MIT",
"scripts": { "scripts": {
"deploy": "NODE_ENV=production webpack --mode production", "deploy": "NODE_ENV=production node build.js",
"watch": "webpack --mode development --watch" "watch": "node build.js"
}, },
"dependencies": { "dependencies": {
"phoenix": "file:../deps/phoenix", "phoenix": "file:../deps/phoenix",
"phoenix_html": "file:../deps/phoenix_html" "phoenix_html": "file:../deps/phoenix_html"
}, },
"devDependencies": { "devDependencies": {
"@babel/core": "^7.0.0",
"@babel/preset-env": "^7.0.0",
"autoprefixer": "^10.3.1", "autoprefixer": "^10.3.1",
"babel-loader": "^8.0.0", "esbuild": "^0.12.22",
"copy-webpack-plugin": "^5.1.1", "esbuild-plugin-postcss2": "0.0.9",
"css-loader": "^3.4.2", "fs-extra": "^10.0.0",
"hard-source-webpack-plugin": "^0.13.1",
"mini-css-extract-plugin": "^0.9.0",
"optimize-css-assets-webpack-plugin": "^5.0.1",
"postcss": "^8.3.6", "postcss": "^8.3.6",
"postcss-import": "^14.0.2", "postcss-import": "^14.0.2",
"postcss-loader": "^4.2.0", "tailwindcss": "^2.2.7"
"tailwindcss": "^2.2.7",
"terser-webpack-plugin": "^2.3.2",
"webpack": "^4.41.5",
"webpack-cli": "^3.3.2"
} }
} }

View File

@ -13,10 +13,7 @@ config :ketbin, KetbinWeb.Endpoint,
check_origin: false, check_origin: false,
watchers: [ watchers: [
node: [ node: [
"node_modules/webpack/bin/webpack.js", "build.js",
"--mode",
"development",
"--watch-stdin",
cd: Path.expand("../assets", __DIR__) cd: Path.expand("../assets", __DIR__)
] ]
] ]

View File

@ -24,7 +24,7 @@ defmodule KetbinWeb.Endpoint do
at: "/", at: "/",
from: :ketbin, from: :ketbin,
gzip: false, gzip: false,
only: ~w(css fonts images js favicon.ico robots.txt) only: ~w(assets fonts images favicon.ico robots.txt)
# Code reloading can be explicitly enabled under the # Code reloading can be explicitly enabled under the
# :code_reloader configuration of your endpoint. # :code_reloader configuration of your endpoint.

View File

@ -5,11 +5,11 @@
<meta http-equiv="X-UA-Compatible" content="IE=edge"/> <meta http-equiv="X-UA-Compatible" content="IE=edge"/>
<meta name="viewport" content="width=device-width, initial-scale=1.0"/> <meta name="viewport" content="width=device-width, initial-scale=1.0"/>
<title>Katbin</title> <title>Katbin</title>
<link rel="stylesheet" href="<%= Routes.static_path(@conn, "/css/app.css") %>"/> <link rel="stylesheet" href="<%= Routes.static_path(@conn, "/assets/app.css") %>"/>
<link rel="preconnect" href="https://fonts.googleapis.com"> <link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin> <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:wght@400;500;600;700;800&display=swap" rel="stylesheet"> <link href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:wght@400;500;600;700;800&display=swap" rel="stylesheet">
<script defer type="text/javascript" src="<%= Routes.static_path(@conn, "/js/app.js") %>"></script> <script defer type="text/javascript" src="<%= Routes.static_path(@conn, "/assets/app.js") %>"></script>
</head> </head>
<body class="flex flex-col "> <body class="flex flex-col ">
<header class="flex w-full justify-between items-center py-3 px-6"> <header class="flex w-full justify-between items-center py-3 px-6">