astro/scripts/memory/index.js
Bjorn Lu 49ab4f231c
Remove proload for config loading (#5778)
* Refactor resolve and load config

* Add changeset

* Update name

* Remove unnecessary node_env handling

* Fix test

* Update comment
2023-01-06 12:49:18 -05:00

85 lines
2.6 KiB
JavaScript

import { fileURLToPath } from 'url';
import v8 from 'v8';
import dev from '../../packages/astro/dist/core/dev/index.js';
import { openConfig } from '../../packages/astro/dist/core/config.js';
import { nodeLogDestination } from '../../packages/astro/dist/core/logger/node.js';
import prettyBytes from 'pretty-bytes';
if (!global.gc) {
console.error('ERROR: Node must be run with --expose-gc');
process.exit(1);
}
const isCI = process.argv.includes('--ci');
/** URL directory containing the entire project. */
const projDir = new URL('./project/', import.meta.url);
let { astroConfig: config } = await openConfig({
cwd: fileURLToPath(projDir),
logging: {
dest: nodeLogDestination,
level: 'error',
},
cmd: 'dev',
});
const telemetry = {
record() {
return Promise.resolve();
},
};
const server = await dev(config, { logging: { level: 'error' }, telemetry });
// Prime the server so initial memory is created
await fetch(`http://localhost:3000/page-0`);
async function run() {
for (let i = 0; i < 100; i++) {
let path = `/page-${i}`;
await fetch(`http://localhost:3000${path}`);
}
}
global.gc();
const startSize = v8.getHeapStatistics().used_heap_size;
// HUMAN mode: Runs forever. Optimized for accurate results on each snapshot Slower than CI.
if (!isCI) {
console.log(
`Greetings, human. This test will run forever. Run with the "--ci" flag to finish with a result.`
);
let i = 1;
while (i++) {
await run();
global.gc();
const checkpoint = v8.getHeapStatistics().used_heap_size;
console.log(`Snapshot ${String(i).padStart(3, '0')}: ${(checkpoint / startSize) * 100}%`);
}
}
// CI mode: Runs 100 times. Optimized for speed with an accurate final result.
for (let i = 0; i < 100; i++) {
await run();
const checkpoint = v8.getHeapStatistics().used_heap_size;
console.log(`Estimate ${String(i).padStart(3, '0')}/100: ${(checkpoint / startSize) * 100}%`);
}
console.log(`Test complete. Running final garbage collection...`);
global.gc();
const endSize = v8.getHeapStatistics().used_heap_size;
// If the trailing average is higher than the median, see if it's more than 5% higher
let percentage = endSize / startSize;
const TEST_THRESHOLD = 1.5;
const isPass = percentage < TEST_THRESHOLD;
console.log(``);
console.log(`Result: ${isPass ? 'PASS' : 'FAIL'} (${percentage * 100}%)`);
console.log(
`Memory usage began at ${prettyBytes(startSize)} and finished at ${prettyBytes(endSize)}.`
);
console.log(`The threshold for a probable memory leak is ${TEST_THRESHOLD * 100}%`);
console.log(``);
console.log(`Exiting...`);
await server.stop();
process.exit(isPass ? 0 : 1);