|
7 | 7 | * |
8 | 8 | * You can also specify a specific version to compare with the current version, |
9 | 9 | * for example: |
10 | | - * `npm run compare-performance -- 2.14.0` |
| 10 | + * `npm run compare-performance -- -v 2.14.0` |
| 11 | + * |
| 12 | + * To see all available options: |
| 13 | + * npm run compare-performance -- -h |
11 | 14 | * |
12 | 15 | * The results will be saved in the folder `./benchmark/results` |
13 | 16 | */ |
14 | | -const { spawn } = require('child_process'); |
15 | | -const myArgs = process.argv.slice(2); |
16 | | -const prevVersion = myArgs.length === 1 ? '@' + myArgs[0] : '@latest'; |
| 17 | +const { spawn, fork } = require('child_process'); |
17 | 18 |
|
18 | | -const benny = require('benny'); |
19 | | -const open = require('open'); |
20 | | -const current_fhirpath = require('../src/fhirpath'); |
21 | | -const current_r4_model = require('../fhir-context/r4'); |
22 | | -const minimumDataset = require('./resources/Minimum-Data-Set---version-3.0.R4.json'); |
23 | | -const _ = require('lodash'); |
24 | | -const currentVersion = 'current'; |
| 19 | +// Insert performance test suites here: |
| 20 | +const availableTests = [ |
| 21 | + 'intersect', |
| 22 | + 'member-invocation', |
| 23 | + 'union', |
| 24 | + 'exclude', |
| 25 | + 'subsetof', |
| 26 | + 'distinct', |
| 27 | + 'contains' |
| 28 | +]; |
25 | 29 |
|
| 30 | +const options = require('commander'); |
| 31 | +options.description('Compare performance between the latest published version and the current version.'); |
| 32 | +options.option('-v, --prevVersion <version>', 'use a specific version instead of latest published version.', 'latest'); |
| 33 | +options.option('-t, --tests <list>', `list of comma-separated tests (e.g. "${availableTests.join(',')}")`, availableTests.join(',')); |
| 34 | +options.option('-c, --compileOnly', 'skip tests for evaluate().', 'latest'); |
| 35 | +options.parse(process.argv); |
26 | 36 |
|
27 | | -const child = spawn('npm', ['i','--prefix', './test/benchmark/prev-fhirpath', 'fhirpath' + prevVersion], { |
| 37 | +const npmInstallProcess = spawn('npm', ['i', '--prefix', './test/benchmark/prev-fhirpath', 'fhirpath@' + options.prevVersion], { |
28 | 38 | stdio: 'inherit' |
29 | 39 | }); |
30 | 40 |
|
31 | | -child.on('exit', code => { |
32 | | - if (code === 0) { |
33 | | - const previous_fhirpath = require('./benchmark/prev-fhirpath/node_modules/fhirpath'); |
34 | | - const previous_r4_model = require('./benchmark/prev-fhirpath/node_modules/fhirpath/fhir-context/r4'); |
35 | | - const previousVersion = require('./benchmark/prev-fhirpath/node_modules/fhirpath/package.json').version; |
36 | | - const bigItems = current_fhirpath.evaluate(minimumDataset,'repeat(item)', {}, current_r4_model); |
37 | | - const bigItemsCopy = _.cloneDeep(bigItems); |
38 | | - const smallItems = current_fhirpath.evaluate(minimumDataset,'repeat(item).repeat(code)', {}, current_r4_model) |
39 | | - const smallItemsCopy = _.cloneDeep(smallItems); |
40 | | - // Insert performance test suites here: |
41 | | - [ |
42 | | - 'intersect', |
43 | | - 'member-invocation', |
44 | | - 'union', |
45 | | - 'exclude', |
46 | | - 'subsetof', |
47 | | - 'distinct', |
48 | | - 'contains' |
49 | | - ].forEach(filename => { |
50 | | - const suites = require('./benchmark/'+ filename)({ |
51 | | - benny, |
52 | | - open, |
53 | | - previous_fhirpath, |
54 | | - previous_r4_model, |
55 | | - current_fhirpath, |
56 | | - current_r4_model, |
57 | | - minimumDataset, |
58 | | - currentVersion, |
59 | | - previousVersion, |
60 | | - bigItems, |
61 | | - bigItemsCopy, |
62 | | - smallItems, |
63 | | - smallItemsCopy |
64 | | - }); |
65 | | - suites.forEach(suite => { |
66 | | - const cases = suite.cases.reduce((arr, item) => { |
67 | | - arr.push( |
68 | | - benny.add( |
69 | | - `${item.name} [${previousVersion}]`, |
70 | | - item.testFunction.bind( |
71 | | - this, |
72 | | - previous_fhirpath, |
73 | | - previous_r4_model, |
74 | | - previous_fhirpath.compile(suite.expression, previous_r4_model) |
75 | | - ) |
76 | | - ) |
77 | | - ); |
78 | | - arr.push( |
79 | | - benny.add( |
80 | | - `${item.name} [${currentVersion}]`, |
81 | | - item.testFunction.bind( |
82 | | - this, |
83 | | - current_fhirpath, |
84 | | - current_r4_model, |
85 | | - current_fhirpath.compile(suite.expression, current_r4_model) |
86 | | - ) |
87 | | - ) |
88 | | - ); |
89 | | - return arr; |
90 | | - }, []); |
| 41 | +// Process for running benchmarks. We need a separate process to run the tests |
| 42 | +// to free the main process from synchronous code to listen for the SIGINT event. |
| 43 | +let benchmarkingProcess; |
| 44 | + |
| 45 | +process.on('SIGINT', () => { |
| 46 | + // Kill the benchmarking process |
| 47 | + if (benchmarkingProcess) { |
| 48 | + benchmarkingProcess.kill('SIGKILL'); |
| 49 | + // Displays the bash prompt on a new line. |
| 50 | + console.log(''); |
| 51 | + } |
91 | 52 |
|
92 | | - benny.suite( |
93 | | - suite.name, |
94 | | - ...cases, |
95 | | - benny.cycle(), |
96 | | - benny.complete(), |
97 | | - benny.configure({ |
98 | | - minDisplayPrecision: 2 |
99 | | - }), |
100 | | - benny.save({ file: suite.filename, folder: __dirname + '/results', version: currentVersion }), |
101 | | - benny.save({ file: suite.filename, folder: __dirname + '/results', format: 'chart.html' }), |
102 | | - ).then(() => { |
103 | | - open(__dirname + `/results/${suite.filename}.chart.html`); |
104 | | - }); |
105 | | - }); |
106 | | - }) |
| 53 | + // The value of the SIGINT signal code is 2 (See https://man7.org/linux/man-pages/man7/signal.7.html). |
| 54 | + // If Node.js receives a fatal signal such as SIGKILL or SIGHUP, then its exit |
| 55 | + // code will be 128 plus the value of the signal code: |
| 56 | + // 128 + 2 = 130 (see https://nodejs.org/api/process.html#exit-codes) |
| 57 | + process.exit(130); |
| 58 | +}); |
| 59 | + |
| 60 | +npmInstallProcess.on('exit', code => { |
| 61 | + if (code === 0) { |
| 62 | + benchmarkingProcess = fork(__dirname + '/benchmark/runner.js', { stdio: 'inherit'}); |
| 63 | + // Pass options to the benchmarking process to run benchmarks |
| 64 | + benchmarkingProcess.send(options); |
107 | 65 | } |
108 | 66 | }); |
0 commit comments