About
Deadcode elimination via running end-to-end tests.
Sample project: DCE for threejs
Install
npm i -D ycw/e2edce
Usage
First, create a configuration file in project root
Then, config package.json
{
"scripts": {
"build": "e2edce e2edce.config.js"
}
}
Finally, run npm run build
to build artifacts
- index.build.js (min)
- index.build.js.gz (min + gzipped)
Configuration File
e2edce.config.js
export default {
// --- required ---
configs: [ // array of configs
{
// --- required ---
input: 'src/index.js', // path to entry
output: 'index.build.js', // path to output file
test: 'e2e/test.js', // path to test file
// --- optional ---
compress: true, // compress?
mangle: true, // mangle?
minify: true, // trim whitespaces?
debug: false, // create a debug build?
port: 8081, // dev server port
headless: true, // run tests in headless browser?
}
],
// --- optional ---
setup: async() => {}, // run once before processing
teardown: async() => {}, // run once after processing
resolve: async() => {}, // custom module resolve
}
-
compress
is https://github.com/terser/terser#compress-options -
debug
if true, all uncovered fns willthrow
at runtime instead of removal at compile time;compress
,mangle
andminify
are forced to befalse
. -
resolve
is https://rollupjs.org/guide/en/#resolveidWe could generate tmp modules (in
setup
) for module replacement (inresolve
) and finally remove those tmp modules (inteardown
)
Test File
e2e/test.js
Export a async fn or an object
export default async (page) => {
await page.goto('http://localhost:8081', { waitUntil: 'networkidle' })
// ...
}
export default {
// --- required ---
test: async () => {
await page.goto('http://localhost:8081', { waitUntil: 'networkidle' })
},
// --- optional ---
inject: () => {..}
}
-
inject
, a fn to be run at the end of input file.We could add mocks inside
inject()
to directly cover certain code branches instead of writing complex e2e tests insidetest()