9
Build dan Distribusi
npm run build menjalankan dua tahap secara berurutan: ./script/build-esm.js lebih dahulu, lalu ./script/build-dist.sh. Keduanya dirangkai dengan &&, sehingga tahap kedua tidak dijalankan bila tahap pertama gagal package.json:2451. Varian build+test hanya menambahkan npm run test di belakang rantai yang sama package.json:2462.
Tahap pertama bekerja di dalam src/ dan menghasilkan berkas ESM serta satu berkas deklarasi tipe. Tahap kedua membaca hasil tahap pertama dan memanggil uglifyjs untuk mengisi dist/.
graph LR
SRC["src/**/*.js (CommonJS)"]
ESM["script/build-esm.js"]
MJS["src/**/*.mjs + ua-parser-enums.d.ts"]
DIST["script/build-dist.sh"]
MIN["dist/ua-parser.min.js + .min.mjs"]
PACK["dist/ua-parser.pack.js + .pack.mjs"]
SRC --> ESM --> MJS --> DIST
DIST --> MIN
DIST --> PACK
style SRC fill:#2d7d46,color:#fff
style ESM fill:#f59e0b,color:#000
style MJS fill:#8b5cf6,color:#fff
style DIST fill:#f59e0b,color:#000
style MIN fill:#8b5cf6,color:#fff
style PACK fill:#8b5cf6,color:#fff
%% fig: Rantai build dari src ke dist
%% desc: build-esm.js mengubah sumber CommonJS menjadi .mjs, lalu build-dist.sh memanggil uglifyjs untuk menghasilkan empat berkas di dist.Tahap 1: script/build-esm.js
Skrip ini tidak memakai parser JavaScript. Ia membaca berkas CommonJS dengan fs.readFileSync, menjalankan deret penggantian regex, lalu menulis hasilnya ke berkas tujuan dengan fs.writeFileSync script/build-esm.js:14-303. Deret replacement default untuk .mjs berisi empat pola berurutan: menambahkan as pada alias const yang diikuti require, mengubah require path relatif menjadi import ... from '.x.mjs', mengubah require paket menjadi import, dan mengubah module.exports = menjadi export script/build-esm.js:5-124.
Setiap berkas hasil diberi tiga baris header sebelum isi hasil transformasi: judul entri, baris // DO NOT EDIT THIS FILE!, dan path sumber asalnya script/build-esm.js:24-295. Header itu terlihat pada berkas hasil yang tersimpan di repository src/main/ua-parser.mjs:1-36.
Daftar target bersifat statis di dalam array files, dan setiap entri dijalankan lewat generateFile script/build-esm.js:32-917, script/build-esm.js:938. Delapan entri dihasilkan dari tujuh berkas sumber, karena src/enums/ua-parser-enums.js dipakai dua kali.
src | dest | replacement |
|---|---|---|
src/main/ua-parser.js | src/main/ua-parser.mjs | empat pola khusus lalu default script/build-esm.js:37-429 |
src/bot-detection/bot-detection.js | src/bot-detection/bot-detection.mjs | default |
src/browser-detection/browser-detection.js | src/browser-detection/browser-detection.mjs | default |
src/device-detection/device-detection.js | src/device-detection/device-detection.mjs | default |
src/enums/ua-parser-enums.js | src/enums/ua-parser-enums.mjs | default |
src/enums/ua-parser-enums.js | src/enums/ua-parser-enums.d.ts | empat pola deklarasi tipe script/build-esm.js:68-7810 |
src/extensions/ua-parser-extensions.js | src/extensions/ua-parser-extensions.mjs | default |
src/helpers/ua-parser-helpers.js | src/helpers/ua-parser-helpers.mjs | default |
Entri src/main/ua-parser.js menambahkan empat pola khusus sebelum pola default. Pola itu membuang pembungkus fungsi dan komentar jshint lama, menaikkan esversion ke 6, dan menutup berkas dengan export {UAParser}; script/build-esm.js:37-429. Entri src/enums/ua-parser-enums.js yang kedua menghasilkan berkas .d.ts dengan pola sendiri: = object.freeze( menjadi export ...: Readonly<, deklarasi biasa menjadi typeof, }); menjadi }>;, dan baris module.exports dihapus script/build-esm.js:68-7810.
Karena konversi dilakukan dengan regex, hasilnya bergantung pada bentuk teks sumber: nama identifier dan urutan pola harus cocok persis dengan yang tertulis di src/.
Tahap 2: script/build-dist.sh
Skrip ini menetapkan enam variabel path lebih dahulu: tiga untuk .js dan tiga untuk .mjs, masing-masing SRC, MIN, dan PACK script/build-dist.sh:3-911. Empat pemanggilan uglifyjs kemudian menulis langsung ke dist/ dengan kombinasi flag berikut script/build-dist.sh:11-2312.
| Keluaran | Sumber | Flag uglifyjs |
|---|---|---|
dist/ua-parser.min.js | src/main/ua-parser.js | --comments "/^ UA/" |
dist/ua-parser.min.mjs | src/main/ua-parser.mjs | --comments "/^ UA/" --module |
dist/ua-parser.pack.js | src/main/ua-parser.js | --comments "/^ UA/" --compress --mangle |
dist/ua-parser.pack.mjs | src/main/ua-parser.mjs | --comments "/^ UA/" --compress --mangle --module |
Hanya varian pack yang memakai --compress --mangle; varian min mempertahankan nama identifier asli. Flag --module menandai keluaran sebagai ES module untuk sumber .mjs script/build-dist.sh:11-2312. Opsi --comments "/^ UA/" mempertahankan banner lisensi, dan banner itu memang muncul di baris pertama artefak dist/ua-parser.min.js:1-313 serta dist/ua-parser.pack.js:1-314.
Biner uglifyjs berasal dari devDependency uglify-js versi ~3.19.3 package.json:27515, sehingga npm install atau npm ci harus dijalankan sebelum tahap kedua bisa berhasil.
Pemetaan artefak ke konsumen
Isi dist/ tidak dipakai langsung oleh require atau import bawaan. Field main menunjuk src/main/ua-parser.js, field module menunjuk src/main/ua-parser.mjs, dan field browser menunjuk dist/ua-parser.pack.js package.json:195-19916.
graph LR
PKG["package.json"]
REQ["require: src/main/ua-parser.js"]
IMP["import: src/main/ua-parser.mjs"]
BRW["browser: dist/ua-parser.pack.js"]
PKG -->|"main"| REQ
PKG -->|"module"| IMP
PKG -->|"browser"| BRW
style PKG fill:#f59e0b,color:#000
style REQ fill:#336791,color:#fff
style IMP fill:#8b5cf6,color:#fff
style BRW fill:#8b5cf6,color:#fff
%% fig: Rute resolusi berkas per field package.json
%% desc: main dan module menunjuk berkas di src, sedangkan browser menunjuk artefak pack di dist.Peta exports mengulang pola yang sama untuk tujuh subpath: require menunjuk .js di src/, import menunjuk .mjs di src/, dan types menunjuk .d.ts di src/ package.json:200-23617. Field files yang dikirim ke registry berisi dist/*.?(m)js, dist/icons, dan src, sedangkan bin menunjuk ./script/cli.js package.json:237-24218. Karena dist/icons termasuk, direktori itu perlu ada saat artefak didistribusikan. Rincian pemakaian tiap jalur masuk ada di Instalasi dan Penggunaan.
⚠️ Berkas hasil build disimpan di repository. Jangan mengedit
src/**/*.mjsatau berkas didist/secara manual: header hasil build menyatakan// DO NOT EDIT THIS FILE!script/build-esm.js:24-295, dan pernyataan itu terlihat pada berkas.mjsyang di-commit src/main/ua-parser.mjs:1-36. Ubahsrc/main/ua-parser.jslalu jalankannpm run build.
⚠️ Workflow publish hanya menjalankan
npm cilalunpm publish --provenance --access public, tanpanpm run build.github/workflows/publish-npm.yml:28-2919. Artefak yang terbit karena itu adalah berkas yang sudah di-commit, sehinggadist/yang usang akan ikut terbit bila lupa di-build ulang.
Workflow CI menjalankan npm run build+test .github/workflows/ci-build-test.yml:41-4420, dan script/test-all.sh juga membuka dengan npm run build script/test-all.sh:3-621. Keduanya meregenerasi artefak sebelum pengujian, jadi tidak ada langkah yang membandingkan hasil build dengan berkas yang di-commit. Rangkaian pengujian selengkapnya dibahas di Pengujian dan Kontribusi.