Skip to content

Commit

Permalink
Add esbuild-rails and upgrade esbuild (#760)
Browse files Browse the repository at this point in the history
* Add `esbuild-rails` and upgrade `esbuild`

* Change `js` process in `Procfile.assets`
  • Loading branch information
marcoroth authored Aug 29, 2024
1 parent 0f1d3cc commit 2c90204
Show file tree
Hide file tree
Showing 5 changed files with 269 additions and 202 deletions.
2 changes: 1 addition & 1 deletion Procfile.assets
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
js: yarn build --watch=forever
js: yarn build --watch
css: yarn watch:css
61 changes: 4 additions & 57 deletions app/javascript/controllers/index.js
Original file line number Diff line number Diff line change
@@ -1,59 +1,6 @@
// This file is auto-generated by ./bin/rails stimulus:manifest:update
// Run that command whenever you add a new controller or create them with
// ./bin/rails generate stimulus controllerName

import { application } from "./application"
import controllers from "./**/*_controller.js"

import DatePickerController from "./date_picker_controller"
application.register("date-picker", DatePickerController)

import DropdownController from "./dropdown_controller"
application.register("dropdown", DropdownController)

import DynamicFieldsController from "./dynamic_fields_controller"
application.register("dynamic-fields", DynamicFieldsController)

import FilterController from "./filter_controller"
application.register("filter", FilterController)

import HighlightController from "./highlight_controller"
application.register("highlight", HighlightController)

import ImageUploadController from "./image_upload_controller"
application.register("image-upload", ImageUploadController)

import InstantClickController from "./instant_click_controller"
application.register("instant-click", InstantClickController)

import LangSelectionController from "./lang_selection_controller"
application.register("lang-selection", LangSelectionController)

import NationalityTwoController from "./nationality_two_controller"
application.register("nationality-two", NationalityTwoController)

import PeopleController from "./people_controller"
application.register("people", PeopleController)

import PeopleSkillsController from "./people_skills_controller"
application.register("people-skills", PeopleSkillsController)

import PeopleSkillsFilterController from "./people_skills_filter_controller"
application.register("people-skills-filter", PeopleSkillsFilterController)

import RemoteModalController from "./remote_modal_controller"
application.register("remote-modal", RemoteModalController)

import ScrollController from "./scroll_controller"
application.register("scroll", ScrollController)

import SearchController from "./search_controller"
application.register("search", SearchController)

import SkillsEmptySpaceController from "./skills_empty_space_controller"
application.register("skills-empty-space", SkillsEmptySpaceController)

import SkillsFilterController from "./skills_filter_controller"
application.register("skills-filter", SkillsFilterController)

import SkillsetSelectedController from "./skillset_selected_controller"
application.register("skillset-selected", SkillsetSelectedController)
controllers.forEach((controller) => {
application.register(controller.name, controller.module.default)
})
106 changes: 106 additions & 0 deletions esbuild.config.mjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
#!/usr/bin/env node

// Requires esbuild 0.17+
//
// Esbuild is configured with 3 modes:
//
// `yarn build` - Build JavaScript and exit
// `yarn build --watch` - Rebuild JavaScript on change
// `yarn build --reload` - Reloads page when views, JavaScript, or stylesheets change
//
// Minify is enabled when "RAILS_ENV=production"
// Sourcemaps are enabled in non-production environments

import * as esbuild from "esbuild"
import path from "path"
import rails from "esbuild-rails"
import chokidar from "chokidar"
import http from "http"
import { setTimeout } from "timers/promises"

const clients = []

const entryPoints = [
"application.js"
]

const watchDirectories = [
"./app/javascript/**/*.js",
"./app/views/**/*.html.haml",
"./app/assets/builds/**/*.css", // Wait for cssbundling changes
]

const config = {
absWorkingDir: path.join(process.cwd(), "app/javascript"),
bundle: true,
format: 'esm',
entryPoints: entryPoints,
minify: process.env.RAILS_ENV == "production",
sourcemap: process.env.RAILS_ENV != "production",
outdir: path.join(process.cwd(), "app/assets/builds"),
publicPath: '/assets',
loader: {
'.woff': 'file',
'.woff2': 'file'
},
plugins: [
rails()
],
}

async function buildAndReload() {
// Foreman & Overmind assign a separate PORT for each process
const port = parseInt(process.env.PORT)
const context = await esbuild.context({
...config,
banner: {
js: ` (() => new EventSource("http://localhost:${port}").onmessage = () => location.reload())();`,
}
})

// Reload uses an HTTP server as an even stream to reload the browser
http.createServer((req, res) => {
return clients.push(
res.writeHead(200, {
"Content-Type": "text/event-stream",
"Cache-Control": "no-cache",
"Access-Control-Allow-Origin": "*",
Connection: "keep-alive",
})
)
}).listen(port)

await context.rebuild()

console.log("[reload] initial build succeeded")

let ready = false

chokidar.watch(watchDirectories).on("ready", () => {
console.log("[reload] ready")
ready = true
}).on("all", async (event, path) => {
if (ready === false) return

if (path.includes("javascript")) {
try {
await setTimeout(20)
await context.rebuild()
console.log("[reload] build succeeded")
} catch (error) {
console.error("[reload] build failed", error)
}
}
clients.forEach((res) => res.write("data: update\n\n"))
clients.length = 0
})
}

if (process.argv.includes("--reload")) {
buildAndReload()
} else if (process.argv.includes("--watch")) {
let context = await esbuild.context({...config, logLevel: 'info'})
context.watch()
} else {
esbuild.build(config)
}
5 changes: 3 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,16 @@
"autoprefixer": "^10.4.17",
"bootstrap": "^5.3.2",
"bootstrap-icons": "^1.11.3",
"esbuild": "^0.20.0",
"esbuild": "^0.23.1",
"esbuild-rails": "^1.0.7",
"nodemon": "^3.0.3",
"postcss": "^8.4.33",
"postcss-cli": "^11.0.0",
"sass": "^1.70.0",
"slim-select": "^2.8.2"
},
"scripts": {
"build": "esbuild app/javascript/*.* --bundle --sourcemap --loader:.woff=file --loader:.woff2=file --format=esm --outdir=app/assets/builds --public-path=/assets",
"build": "node esbuild.config.mjs",
"build:css:compile": "sass ./app/assets/stylesheets/application.scss:./app/assets/builds/application.css --no-source-map --load-path=node_modules",
"build:css:prefix": "postcss ./app/assets/builds/application.css --use=autoprefixer --output=./app/assets/builds/application.css",
"build:css": "yarn build:css:compile && yarn build:css:prefix",
Expand Down
Loading

0 comments on commit 2c90204

Please sign in to comment.