@itee/tasks 1.0.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.idea/inspectionProfiles/Project_Default.xml +6 -0
- package/.idea/modules.xml +8 -0
- package/.idea/tasks.iml +8 -0
- package/.idea/vcs.xml +6 -0
- package/CHANGELOG.md +56 -0
- package/README.md +1 -0
- package/configs/builds/build.conf.mjs +1 -0
- package/configs/cleans/clean.conf.mjs +1 -0
- package/configs/docs/doc.conf.json +1 -0
- package/configs/lints/lint.conf.mjs +91 -0
- package/configs/refresh.conf.mjs +1 -0
- package/configs/tests/benchmarks/compute-benchmarks.conf.mjs +5 -0
- package/configs/tests/benchmarks/run-benchmarks-for-frontend.conf.mjs +37 -0
- package/configs/tests/benchmarks/run-benchmarks.conf.mjs +7 -0
- package/configs/tests/bundlings/check-bundling-from-esm-build-import.conf.mjs +45 -0
- package/configs/tests/bundlings/check-bundling-from-esm-files-direct.conf.mjs +51 -0
- package/configs/tests/bundlings/check-bundling-from-esm-files-import.conf.mjs +48 -0
- package/configs/tests/units/compute-unit-tests.conf.mjs +5 -0
- package/configs/tests/units/run-unit-tests-for-frontend.conf.mjs +14 -0
- package/configs/tests/units/run-unit-tests.conf.mjs +7 -0
- package/package.json +100 -0
- package/sources/_utils.mjs +412 -0
- package/sources/builds/build.task.mjs +52 -0
- package/sources/cleans/clean.task.mjs +32 -0
- package/sources/docs/doc.task.mjs +48 -0
- package/sources/helps/help.task.mjs +155 -0
- package/sources/index.mjs +21 -0
- package/sources/lints/lint.task.mjs +46 -0
- package/sources/refresh.mjs +100 -0
- package/sources/releases/release.task.mjs +32 -0
- package/sources/tests/benchmarks/compute-benchmarks.task.mjs +236 -0
- package/sources/tests/benchmarks/run-benchmarks-for-backend.task.mjs +43 -0
- package/sources/tests/benchmarks/run-benchmarks-for-frontend.task.mjs +48 -0
- package/sources/tests/benchmarks/run-benchmarks.task.mjs +16 -0
- package/sources/tests/bundlings/check-bundling-from-esm-build-import.task.mjs +127 -0
- package/sources/tests/bundlings/check-bundling-from-esm-files-direct.task.mjs +94 -0
- package/sources/tests/bundlings/check-bundling-from-esm-files-import.task.mjs +113 -0
- package/sources/tests/bundlings/check-bundling.task.mjs +24 -0
- package/sources/tests/run-tests.task.mjs +22 -0
- package/sources/tests/units/compute-unit-tests.task.mjs +547 -0
- package/sources/tests/units/run-unit-tests-for-backend.task.mjs +48 -0
- package/sources/tests/units/run-unit-tests-for-frontend.task.mjs +48 -0
- package/sources/tests/units/run-unit-tests.task.mjs +16 -0
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
export { buildTask } from './builds/build.task.mjs'
|
|
2
|
+
export { cleanTask } from './cleans/clean.task.mjs'
|
|
3
|
+
export { docTask } from './docs/doc.task.mjs'
|
|
4
|
+
export { helpTask } from './helps/help.task.mjs'
|
|
5
|
+
export { lintTask } from './lints/lint.task.mjs'
|
|
6
|
+
export { releaseTask } from './releases/release.task.mjs'
|
|
7
|
+
export { runTestsTask } from './tests/run-tests.task.mjs'
|
|
8
|
+
export { computeUnitTestsTask } from './tests/units/compute-unit-tests.task.mjs'
|
|
9
|
+
export { runUnitTestsTask } from './tests/units/run-unit-tests.task.mjs'
|
|
10
|
+
export { runUnitTestsForBackendTask } from './tests/units/run-unit-tests-for-backend.task.mjs'
|
|
11
|
+
export { runUnitTestsForFrontendTask } from './tests/units/run-unit-tests-for-frontend.task.mjs'
|
|
12
|
+
export { checkBundlingFromEsmBuildImportTask } from './tests/bundlings/check-bundling-from-esm-build-import.task.mjs'
|
|
13
|
+
export { checkBundlingFromEsmFilesDirectTask } from './tests/bundlings/check-bundling-from-esm-files-direct.task.mjs'
|
|
14
|
+
export { checkBundlingFromEsmFilesImportTask } from './tests/bundlings/check-bundling-from-esm-files-import.task.mjs'
|
|
15
|
+
export { checkBundlingTask } from './tests/bundlings/check-bundling.task.mjs'
|
|
16
|
+
export { computeBenchmarksTask } from './tests/benchmarks/compute-benchmarks.task.mjs'
|
|
17
|
+
export { runBenchmarksTestsTask } from './tests/benchmarks/run-benchmarks.task.mjs'
|
|
18
|
+
export { runBenchmarksForBackendTask } from './tests/benchmarks/run-benchmarks-for-backend.task.mjs'
|
|
19
|
+
export { runBenchmarksForFrontendTask } from './tests/benchmarks/run-benchmarks-for-frontend.task.mjs'
|
|
20
|
+
|
|
21
|
+
export * from './_utils.mjs'
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import colors from 'ansi-colors'
|
|
2
|
+
import log from 'fancy-log'
|
|
3
|
+
import child_process from 'node:child_process'
|
|
4
|
+
import { basename } from 'node:path'
|
|
5
|
+
import { promisify } from 'node:util'
|
|
6
|
+
import {
|
|
7
|
+
getTaskConfigurationPathFor,
|
|
8
|
+
logLoadingTask
|
|
9
|
+
} from '../_utils.mjs'
|
|
10
|
+
|
|
11
|
+
logLoadingTask( import.meta.filename )
|
|
12
|
+
|
|
13
|
+
const execFile = promisify( child_process.execFile )
|
|
14
|
+
const { red } = colors
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* @method npm run lint
|
|
18
|
+
* @global
|
|
19
|
+
* @description Will lint the sources files and try to fix the style when possible
|
|
20
|
+
*/
|
|
21
|
+
const lintTask = async ( done ) => {
|
|
22
|
+
|
|
23
|
+
try {
|
|
24
|
+
|
|
25
|
+
const configurationPath = getTaskConfigurationPathFor( import.meta.filename )
|
|
26
|
+
|
|
27
|
+
const { stdout } = await execFile( 'npx', [ 'eslint', '--config', configurationPath, '--fix' ] )
|
|
28
|
+
if ( stdout !== '' ) {
|
|
29
|
+
log( stdout )
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
done()
|
|
33
|
+
|
|
34
|
+
} catch ( error ) {
|
|
35
|
+
|
|
36
|
+
log( error.stdout )
|
|
37
|
+
done( red( error.message ) )
|
|
38
|
+
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
}
|
|
42
|
+
lintTask.displayName = basename( import.meta.filename, '.task.mjs' )
|
|
43
|
+
lintTask.description = 'Will lint the sources files and try to fix the style when possible.'
|
|
44
|
+
lintTask.flags = null
|
|
45
|
+
|
|
46
|
+
export { lintTask }
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
import colors from 'ansi-colors'
|
|
2
|
+
import log from 'fancy-log'
|
|
3
|
+
import { writeFileSync } from 'fs'
|
|
4
|
+
import {
|
|
5
|
+
basename,
|
|
6
|
+
join,
|
|
7
|
+
relative
|
|
8
|
+
} from 'path'
|
|
9
|
+
import {
|
|
10
|
+
getFilesFrom,
|
|
11
|
+
getTaskConfigurationFor,
|
|
12
|
+
iteePackageRootDirectory,
|
|
13
|
+
iteePackageSourcesDirectory,
|
|
14
|
+
packageNodeModulesDirectory,
|
|
15
|
+
packageRootDirectory,
|
|
16
|
+
packageTasksDirectory
|
|
17
|
+
} from './_utils.mjs'
|
|
18
|
+
|
|
19
|
+
const {
|
|
20
|
+
green,
|
|
21
|
+
yellow
|
|
22
|
+
} = colors
|
|
23
|
+
|
|
24
|
+
const configuration = await getTaskConfigurationFor( import.meta.filename )
|
|
25
|
+
|
|
26
|
+
// Get and filter tasks to expose
|
|
27
|
+
const defaultTaskPattern = join( iteePackageSourcesDirectory, '/{*.task.mjs,**/*.task.mjs,**/**/*.task.mjs}' )
|
|
28
|
+
const defaultTaskFiles = getFilesFrom(
|
|
29
|
+
defaultTaskPattern,
|
|
30
|
+
filePath => {
|
|
31
|
+
const relativeFilepath = relative( iteePackageSourcesDirectory, filePath )
|
|
32
|
+
const filename = basename( filePath )
|
|
33
|
+
const included = !configuration.includes( filename )
|
|
34
|
+
|
|
35
|
+
included
|
|
36
|
+
? log( 'Include default task from', green( relativeFilepath ) )
|
|
37
|
+
: log( 'Exclude default task from', yellow( relativeFilepath ) )
|
|
38
|
+
|
|
39
|
+
return included
|
|
40
|
+
}
|
|
41
|
+
)
|
|
42
|
+
|
|
43
|
+
const userTaskPattern = join( packageTasksDirectory, '/{*.task.mjs,**/*.task.mjs,**/**/*.task.mjs}' )
|
|
44
|
+
const userTaskFiles = getFilesFrom(
|
|
45
|
+
userTaskPattern,
|
|
46
|
+
filePath => {
|
|
47
|
+
const relativeFilepath = relative( packageRootDirectory, filePath )
|
|
48
|
+
const filename = basename( filePath )
|
|
49
|
+
const included = !configuration.includes( filename )
|
|
50
|
+
|
|
51
|
+
included
|
|
52
|
+
? log( 'Include user task from', green( relativeFilepath ) )
|
|
53
|
+
: log( 'Exclude user task from', yellow( relativeFilepath ) )
|
|
54
|
+
|
|
55
|
+
return included
|
|
56
|
+
}
|
|
57
|
+
)
|
|
58
|
+
|
|
59
|
+
// Prepare gulpfile content with header
|
|
60
|
+
let gulpfileContent = '' +
|
|
61
|
+
'/**\n' +
|
|
62
|
+
' * This file is auto-generated by internal gulp command.\n' +
|
|
63
|
+
' * If you want to customize the available gulp tasks, create your own in .tasks folder\n' +
|
|
64
|
+
' * and run "gulp refresh"\n' +
|
|
65
|
+
' */\n\n'
|
|
66
|
+
|
|
67
|
+
// Generate default tasks exports and append to gulpfile content
|
|
68
|
+
gulpfileContent += '// Default Itee tasks\n'
|
|
69
|
+
for ( const taskFile of defaultTaskFiles ) {
|
|
70
|
+
|
|
71
|
+
// we are calling from client and use relative path from it
|
|
72
|
+
if ( iteePackageRootDirectory.includes( 'node_modules' ) ) {
|
|
73
|
+
|
|
74
|
+
const relativeTaskFile = relative( packageNodeModulesDirectory, taskFile )
|
|
75
|
+
gulpfileContent += `export * from '${ relativeTaskFile }'\n`
|
|
76
|
+
|
|
77
|
+
} else { // we are refreshing itee-tasks package internally
|
|
78
|
+
|
|
79
|
+
const relativeTaskFile = relative( iteePackageRootDirectory, taskFile )
|
|
80
|
+
gulpfileContent += `export * from './${ relativeTaskFile }'\n`
|
|
81
|
+
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
gulpfileContent += '\n'
|
|
87
|
+
|
|
88
|
+
// Generate user tasks exports and append to gulpfile content
|
|
89
|
+
if ( userTaskFiles.length > 0 ) {
|
|
90
|
+
gulpfileContent += '// User defined tasks\n'
|
|
91
|
+
}
|
|
92
|
+
for ( const taskFile of userTaskFiles ) {
|
|
93
|
+
const relativeTaskFile = relative( packageRootDirectory, taskFile )
|
|
94
|
+
gulpfileContent += `export * from './${ relativeTaskFile }'\n`
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
// Create gulpfile file
|
|
98
|
+
const gulpfilePath = join( packageRootDirectory, 'gulpfile.mjs' )
|
|
99
|
+
log( 'Refresh', green( gulpfilePath ) )
|
|
100
|
+
writeFileSync( gulpfilePath, gulpfileContent )
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { series } from 'gulp'
|
|
2
|
+
import { basename } from 'node:path'
|
|
3
|
+
import { logLoadingTask } from '../_utils.mjs'
|
|
4
|
+
import { buildTask } from '../builds/build.task.mjs'
|
|
5
|
+
import { cleanTask } from '../cleans/clean.task.mjs'
|
|
6
|
+
import { docTask } from '../docs/doc.task.mjs'
|
|
7
|
+
import { lintTask } from '../lints/lint.task.mjs'
|
|
8
|
+
import { computeBenchmarksTask } from '../tests/benchmarks/compute-benchmarks.task.mjs'
|
|
9
|
+
import { runTestsTask } from '../tests/run-tests.task.mjs'
|
|
10
|
+
import { computeUnitTestsTask } from '../tests/units/compute-unit-tests.task.mjs'
|
|
11
|
+
|
|
12
|
+
logLoadingTask( import.meta.filename )
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* @method npm run release
|
|
16
|
+
* @global
|
|
17
|
+
* @description Will perform a complete release of the library including 'clean', 'lint', 'doc', 'build-tests', 'test' and finally 'build'.
|
|
18
|
+
*/
|
|
19
|
+
const releaseTask = series(
|
|
20
|
+
cleanTask,
|
|
21
|
+
buildTask,
|
|
22
|
+
computeBenchmarksTask,
|
|
23
|
+
computeUnitTestsTask,
|
|
24
|
+
runTestsTask,
|
|
25
|
+
lintTask,
|
|
26
|
+
docTask,
|
|
27
|
+
)
|
|
28
|
+
releaseTask.displayName = basename( import.meta.filename, '.task.mjs' )
|
|
29
|
+
releaseTask.description = 'Will perform a complete release of the library including \'clean\', \'lint\', \'doc\', \'test\' and finally \'build\'.'
|
|
30
|
+
releaseTask.flags = null
|
|
31
|
+
|
|
32
|
+
export { releaseTask }
|
|
@@ -0,0 +1,236 @@
|
|
|
1
|
+
import colors from 'ansi-colors'
|
|
2
|
+
import childProcess from 'child_process'
|
|
3
|
+
import log from 'fancy-log'
|
|
4
|
+
import { glob } from 'glob'
|
|
5
|
+
import {
|
|
6
|
+
basename,
|
|
7
|
+
dirname,
|
|
8
|
+
extname,
|
|
9
|
+
join,
|
|
10
|
+
normalize,
|
|
11
|
+
relative
|
|
12
|
+
} from 'path'
|
|
13
|
+
import {
|
|
14
|
+
createDirectoryIfNotExist,
|
|
15
|
+
createFile,
|
|
16
|
+
getTaskConfigurationFor,
|
|
17
|
+
logLoadingTask,
|
|
18
|
+
packageName,
|
|
19
|
+
packageNodeModulesDirectory,
|
|
20
|
+
packageSourcesDirectory,
|
|
21
|
+
packageTestsBenchmarksDirectory,
|
|
22
|
+
packageTestsDirectory
|
|
23
|
+
} from '../../_utils.mjs'
|
|
24
|
+
|
|
25
|
+
logLoadingTask( import.meta.filename )
|
|
26
|
+
|
|
27
|
+
const {
|
|
28
|
+
red,
|
|
29
|
+
yellow,
|
|
30
|
+
} = colors
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* @description Will generate benchmarks files from source code against provided alternatives
|
|
34
|
+
*/
|
|
35
|
+
const computeBenchmarksTask = async ( done ) => {
|
|
36
|
+
|
|
37
|
+
createDirectoryIfNotExist( packageTestsBenchmarksDirectory )
|
|
38
|
+
|
|
39
|
+
// Get task configuration
|
|
40
|
+
const filePathsToIgnore = await getTaskConfigurationFor( import.meta.filename )
|
|
41
|
+
|
|
42
|
+
// Get source files to process
|
|
43
|
+
const pattern = join( packageSourcesDirectory, '**' )
|
|
44
|
+
const sourceFiles = glob.sync( pattern )
|
|
45
|
+
.map( filePath => normalize( filePath ) )
|
|
46
|
+
.filter( filePath => {
|
|
47
|
+
const fileName = basename( filePath )
|
|
48
|
+
const isJsFile = fileName.endsWith( '.js' )
|
|
49
|
+
const isNotPrivateFile = !fileName.startsWith( '_' )
|
|
50
|
+
const isNotIgnoredFile = !filePathsToIgnore.includes( fileName )
|
|
51
|
+
return isJsFile && isNotPrivateFile && isNotIgnoredFile
|
|
52
|
+
} )
|
|
53
|
+
|
|
54
|
+
const benchRootImports = []
|
|
55
|
+
for ( let sourceFile of sourceFiles ) {
|
|
56
|
+
|
|
57
|
+
const specificFilePath = sourceFile.replace( packageSourcesDirectory, '' )
|
|
58
|
+
const specificDir = dirname( specificFilePath )
|
|
59
|
+
|
|
60
|
+
const fileName = basename( sourceFile, extname( sourceFile ) )
|
|
61
|
+
const benchFileName = `${ fileName }.bench.js`
|
|
62
|
+
const benchDirPath = join( packageTestsBenchmarksDirectory, specificDir )
|
|
63
|
+
const benchFilePath = join( benchDirPath, benchFileName )
|
|
64
|
+
|
|
65
|
+
const nsName = `${ fileName }Namespace`
|
|
66
|
+
const importDirPath = relative( benchDirPath, packageSourcesDirectory )
|
|
67
|
+
const importFilePath = join( importDirPath, specificFilePath ).replace( /\\/g, '/' )
|
|
68
|
+
|
|
69
|
+
try {
|
|
70
|
+
|
|
71
|
+
const jsdocPath = join( packageNodeModulesDirectory, '/jsdoc/jsdoc.js' )
|
|
72
|
+
const jsdocOutput = childProcess.execFileSync( 'node', [ jsdocPath, '-X', sourceFile ] ).toString()
|
|
73
|
+
|
|
74
|
+
const classNames = []
|
|
75
|
+
const usedLongnames = []
|
|
76
|
+
const jsonData = JSON.parse( jsdocOutput ).filter( data => {
|
|
77
|
+
|
|
78
|
+
const longName = data.longname
|
|
79
|
+
|
|
80
|
+
const kind = data.kind
|
|
81
|
+
if ( kind !== 'function' ) {
|
|
82
|
+
if ( kind === 'class' && !classNames.includes( longName ) ) {
|
|
83
|
+
classNames.push( longName )
|
|
84
|
+
}
|
|
85
|
+
return false
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
// We don't care that data bloc have comment they are unused to generate benchmarks
|
|
89
|
+
// const undocumented = data.undocumented
|
|
90
|
+
// if ( undocumented ) {
|
|
91
|
+
// return false
|
|
92
|
+
// }
|
|
93
|
+
|
|
94
|
+
const scope = data.scope
|
|
95
|
+
if ( ![ 'global', 'static' ].includes( scope ) ) {
|
|
96
|
+
return false
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
if ( longName.includes( ' ' ) || longName.includes( '~' ) || usedLongnames.includes( longName ) ) {
|
|
100
|
+
return false
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
for ( let className of classNames ) {
|
|
104
|
+
if ( longName.includes( className ) ) {
|
|
105
|
+
return false
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
usedLongnames.push( longName )
|
|
110
|
+
|
|
111
|
+
return true
|
|
112
|
+
|
|
113
|
+
} )
|
|
114
|
+
|
|
115
|
+
if ( jsonData.length === 0 ) {
|
|
116
|
+
log( 'Ignoring', yellow( `${ sourceFile }, no usable exports found` ) )
|
|
117
|
+
continue
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
// Compute benchmark suites by grouping logically function by name[_x]
|
|
121
|
+
const suiteGroups = {}
|
|
122
|
+
for ( let docData of jsonData ) {
|
|
123
|
+
|
|
124
|
+
try {
|
|
125
|
+
|
|
126
|
+
const functionName = docData.name
|
|
127
|
+
const nameSplits = functionName.split( '_' )
|
|
128
|
+
const rootName = nameSplits[ 0 ]
|
|
129
|
+
|
|
130
|
+
if ( !( rootName in suiteGroups ) ) {
|
|
131
|
+
suiteGroups[ rootName ] = []
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
suiteGroups[ rootName ].push( functionName )
|
|
135
|
+
|
|
136
|
+
} catch ( error ) {
|
|
137
|
+
|
|
138
|
+
log( red( error.message ) )
|
|
139
|
+
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
// Generate suites
|
|
145
|
+
let benchSuites = ''
|
|
146
|
+
const suitesToExports = []
|
|
147
|
+
for ( let suiteGroupName in suiteGroups ) {
|
|
148
|
+
suitesToExports.push( `${ suiteGroupName }Suite` )
|
|
149
|
+
benchSuites += `const ${ suiteGroupName }Suite = Benchmark.Suite( '${ nsName }.${ suiteGroupName }', Testing.createSuiteOptions() )` + '\n'
|
|
150
|
+
|
|
151
|
+
for ( let suiteGroupValue of suiteGroups[ suiteGroupName ] ) {
|
|
152
|
+
benchSuites += ` .add( '${ suiteGroupValue }()', Testing.iterateOverDataMap( ${ nsName }.${ suiteGroupValue } ), Testing.createBenchmarkOptions() )` + '\n'
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
benchSuites += '\n'
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
// compute relative level to get import wrappers
|
|
159
|
+
const wrapperDirPath = relative( benchDirPath, packageTestsDirectory )
|
|
160
|
+
const importBenchmarkFilePath = join( wrapperDirPath, 'import.benchmarks.js' )
|
|
161
|
+
const importTestingFilePath = join( wrapperDirPath, 'import.testing.js' )
|
|
162
|
+
|
|
163
|
+
const template = '' +
|
|
164
|
+
`import * as ${ nsName } from '${ importFilePath }'` + '\n' +
|
|
165
|
+
`import { getBenchmarkPackage } from '${ importBenchmarkFilePath }'` + '\n' +
|
|
166
|
+
`import { getTestingPackage } from '${ importTestingFilePath }'` + '\n' +
|
|
167
|
+
'\n' +
|
|
168
|
+
`const Benchmark = await getBenchmarkPackage()` + '\n' +
|
|
169
|
+
`const Testing = await getTestingPackage()` + '\n' +
|
|
170
|
+
'\n' +
|
|
171
|
+
`${ benchSuites }` +
|
|
172
|
+
// '\n' +
|
|
173
|
+
`export { ${ suitesToExports } }` + '\n' +
|
|
174
|
+
'\n'
|
|
175
|
+
|
|
176
|
+
const importBenchFilePath = relative( packageTestsBenchmarksDirectory, benchFilePath ).replace( /\\/g, '/' )
|
|
177
|
+
benchRootImports.push( {
|
|
178
|
+
path: importBenchFilePath,
|
|
179
|
+
exports: suitesToExports
|
|
180
|
+
} )
|
|
181
|
+
|
|
182
|
+
createDirectoryIfNotExist( benchDirPath )
|
|
183
|
+
createFile( benchFilePath, template )
|
|
184
|
+
|
|
185
|
+
} catch ( error ) {
|
|
186
|
+
|
|
187
|
+
log( red( error.message ) )
|
|
188
|
+
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
let templateImports = ''
|
|
194
|
+
let suites = []
|
|
195
|
+
for ( let i = 0 ; i < benchRootImports.length ; i++ ) {
|
|
196
|
+
|
|
197
|
+
const currentBench = benchRootImports[ i ]
|
|
198
|
+
const namedExports = currentBench.exports
|
|
199
|
+
const imports = namedExports.join( ', ' )
|
|
200
|
+
suites.push( ...namedExports )
|
|
201
|
+
|
|
202
|
+
templateImports += `import {${ imports }} from './${ currentBench.path }'` + '\n'
|
|
203
|
+
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
// Use a fallback in case no benches were found at all
|
|
207
|
+
if ( benchRootImports.length === 0 ) {
|
|
208
|
+
log( 'Warning ', yellow( 'No usable exports found, generate default file to avoid frontend breakage.' ) )
|
|
209
|
+
const defaultBenchesDir = join( packageTestsBenchmarksDirectory, 'default' )
|
|
210
|
+
const defaultBenchesPath = join( defaultBenchesDir, 'default.bench.js' )
|
|
211
|
+
|
|
212
|
+
createDirectoryIfNotExist( defaultBenchesDir )
|
|
213
|
+
createFile( defaultBenchesPath, '// Avoid web test runner crash on empty benches' )
|
|
214
|
+
}
|
|
215
|
+
|
|
216
|
+
const benchesTemplate = '' +
|
|
217
|
+
`${ templateImports }` + '\n' +
|
|
218
|
+
'const suites = [' + '\n' +
|
|
219
|
+
`${ suites.map( suite => `\t${ suite }` ).join( ',\n' ) }` + '\n' +
|
|
220
|
+
']' + '\n' +
|
|
221
|
+
'\n' +
|
|
222
|
+
`for ( const suite of suites ) {` + '\n' +
|
|
223
|
+
`\tsuite.run()` + '\n' +
|
|
224
|
+
`}` + '\n'
|
|
225
|
+
|
|
226
|
+
const benchesFilePath = join( packageTestsBenchmarksDirectory, `${ packageName }.benchmarks.js` )
|
|
227
|
+
createFile( benchesFilePath, benchesTemplate )
|
|
228
|
+
|
|
229
|
+
done()
|
|
230
|
+
|
|
231
|
+
}
|
|
232
|
+
computeBenchmarksTask.displayName = basename( import.meta.filename, '.task.mjs' )
|
|
233
|
+
computeBenchmarksTask.description = 'Will generate benchmarks files from source code against provided alternatives.'
|
|
234
|
+
computeBenchmarksTask.flags = null
|
|
235
|
+
|
|
236
|
+
export { computeBenchmarksTask }
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import colors from 'ansi-colors'
|
|
2
|
+
import log from 'fancy-log'
|
|
3
|
+
import { existsSync } from 'fs'
|
|
4
|
+
import { basename } from 'node:path'
|
|
5
|
+
import { join } from 'path'
|
|
6
|
+
import {
|
|
7
|
+
logLoadingTask,
|
|
8
|
+
packageName,
|
|
9
|
+
packageTestsBenchmarksDirectory
|
|
10
|
+
} from '../../_utils.mjs'
|
|
11
|
+
|
|
12
|
+
logLoadingTask( import.meta.filename )
|
|
13
|
+
|
|
14
|
+
const {
|
|
15
|
+
red,
|
|
16
|
+
yellow
|
|
17
|
+
} = colors
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* @description Will run benchmarks with node
|
|
21
|
+
*/
|
|
22
|
+
const runBenchmarksForBackendTask = async ( done ) => {
|
|
23
|
+
|
|
24
|
+
const benchesPath = join( packageTestsBenchmarksDirectory, `/${ packageName }.benchmarks.js` )
|
|
25
|
+
if ( !existsSync( benchesPath ) ) {
|
|
26
|
+
log( yellow( `${ benchesPath } does not exist, skip backend benchmarks...` ) )
|
|
27
|
+
done()
|
|
28
|
+
return
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
try {
|
|
32
|
+
await import(benchesPath)
|
|
33
|
+
done()
|
|
34
|
+
} catch ( error ) {
|
|
35
|
+
done( red( error ) )
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
}
|
|
39
|
+
runBenchmarksForBackendTask.displayName = basename( import.meta.filename, '.task.mjs' )
|
|
40
|
+
runBenchmarksForBackendTask.description = 'Will run benchmarks with node'
|
|
41
|
+
runBenchmarksForBackendTask.flags = null
|
|
42
|
+
|
|
43
|
+
export { runBenchmarksForBackendTask }
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import { startTestRunner } from '@web/test-runner'
|
|
2
|
+
import colors from 'ansi-colors'
|
|
3
|
+
import { basename } from 'node:path'
|
|
4
|
+
import {
|
|
5
|
+
getTaskConfigurationFor,
|
|
6
|
+
logLoadingTask
|
|
7
|
+
} from '../../_utils.mjs'
|
|
8
|
+
|
|
9
|
+
logLoadingTask( import.meta.filename )
|
|
10
|
+
|
|
11
|
+
const { red } = colors
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* @description Will run benchmarks with web-test-runner
|
|
15
|
+
*/
|
|
16
|
+
const runBenchmarksForFrontendTask = () => {
|
|
17
|
+
return new Promise( async ( resolve, reject ) => {
|
|
18
|
+
|
|
19
|
+
const configuration = await getTaskConfigurationFor( import.meta.filename )
|
|
20
|
+
const testRunner = await startTestRunner( {
|
|
21
|
+
config: configuration,
|
|
22
|
+
readCliArgs: false,
|
|
23
|
+
readFileConfig: false,
|
|
24
|
+
autoExitProcess: false,
|
|
25
|
+
} )
|
|
26
|
+
|
|
27
|
+
if ( !testRunner ) {
|
|
28
|
+
reject( red( 'Internal test runner error.' ) )
|
|
29
|
+
return
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
// To ensure that testRunner exit event won't be used by other instance of test runner,
|
|
33
|
+
// we need to be sure that current test runner is ended
|
|
34
|
+
testRunner.on( 'finished', () => {
|
|
35
|
+
testRunner.stop()
|
|
36
|
+
} )
|
|
37
|
+
|
|
38
|
+
testRunner.on( 'stopped', () => {
|
|
39
|
+
resolve()
|
|
40
|
+
} )
|
|
41
|
+
|
|
42
|
+
} )
|
|
43
|
+
}
|
|
44
|
+
runBenchmarksForFrontendTask.displayName = basename( import.meta.filename, '.task.mjs' )
|
|
45
|
+
runBenchmarksForFrontendTask.description = 'Will run benchmarks with web-test-runner.'
|
|
46
|
+
runBenchmarksForFrontendTask.flags = null
|
|
47
|
+
|
|
48
|
+
export { runBenchmarksForFrontendTask }
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { basename } from 'node:path'
|
|
2
|
+
import {
|
|
3
|
+
getTaskConfigurationFor,
|
|
4
|
+
logLoadingTask,
|
|
5
|
+
serializeTasksFrom
|
|
6
|
+
} from '../../_utils.mjs'
|
|
7
|
+
|
|
8
|
+
logLoadingTask( import.meta.filename )
|
|
9
|
+
|
|
10
|
+
const configuration = await getTaskConfigurationFor( import.meta.filename )
|
|
11
|
+
const runBenchmarksTestsTask = await serializeTasksFrom( configuration )
|
|
12
|
+
runBenchmarksTestsTask.displayName = basename( import.meta.filename, '.task.mjs' )
|
|
13
|
+
runBenchmarksTestsTask.description = 'Will run benchmarks in back and front environments.'
|
|
14
|
+
runBenchmarksTestsTask.flags = null
|
|
15
|
+
|
|
16
|
+
export { runBenchmarksTestsTask }
|
|
@@ -0,0 +1,127 @@
|
|
|
1
|
+
import colors from 'ansi-colors'
|
|
2
|
+
import log from 'fancy-log'
|
|
3
|
+
import {
|
|
4
|
+
existsSync,
|
|
5
|
+
mkdirSync,
|
|
6
|
+
readFileSync,
|
|
7
|
+
rmSync,
|
|
8
|
+
writeFileSync
|
|
9
|
+
} from 'fs'
|
|
10
|
+
import {
|
|
11
|
+
basename,
|
|
12
|
+
join,
|
|
13
|
+
relative
|
|
14
|
+
} from 'path'
|
|
15
|
+
import { rollup } from 'rollup'
|
|
16
|
+
import {
|
|
17
|
+
getTaskConfigurationFor,
|
|
18
|
+
logLoadingTask,
|
|
19
|
+
packageBuildsDirectory,
|
|
20
|
+
packageName,
|
|
21
|
+
packageTestsBundlesDirectory
|
|
22
|
+
} from '../../_utils.mjs'
|
|
23
|
+
|
|
24
|
+
logLoadingTask( import.meta.filename )
|
|
25
|
+
|
|
26
|
+
const {
|
|
27
|
+
red,
|
|
28
|
+
green,
|
|
29
|
+
magenta,
|
|
30
|
+
} = colors
|
|
31
|
+
|
|
32
|
+
const checkBundlingFromEsmBuildImportTask = async ( done ) => {
|
|
33
|
+
|
|
34
|
+
const configuration = await getTaskConfigurationFor( import.meta.filename )
|
|
35
|
+
|
|
36
|
+
const buildFilePath = join( packageBuildsDirectory, `${ packageName }.esm.js` )
|
|
37
|
+
if ( !existsSync( buildFilePath ) ) {
|
|
38
|
+
done( red( buildFilePath + ' does not exist' ) )
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
const outputDir = join( packageTestsBundlesDirectory, 'from_build_import' )
|
|
42
|
+
const temporaryDir = join( packageTestsBundlesDirectory, 'from_build_import', '.tmp' )
|
|
43
|
+
const importDir = relative( temporaryDir, packageBuildsDirectory )
|
|
44
|
+
const importFilePath = join( importDir, `${ packageName }.esm.js` )
|
|
45
|
+
|
|
46
|
+
if ( existsSync( outputDir ) ) {
|
|
47
|
+
log( 'Clean up', magenta( outputDir ) )
|
|
48
|
+
rmSync( outputDir, { recursive: true } )
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
try {
|
|
52
|
+
|
|
53
|
+
// Get build exports list
|
|
54
|
+
const data = readFileSync( buildFilePath, 'utf8' )
|
|
55
|
+
const regex = /export\s{\s(.*)\s}/
|
|
56
|
+
const found = data.match( regex )
|
|
57
|
+
if ( found === null ) {
|
|
58
|
+
log( red( `Unable to find exports in ${ buildFilePath }` ) )
|
|
59
|
+
return
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
const exports = found[ 1 ].split( ',' )
|
|
63
|
+
.map( item => item.trim() )
|
|
64
|
+
|
|
65
|
+
// Create temporary imports files for each build export
|
|
66
|
+
// And then bundle it
|
|
67
|
+
let temporaryFilePaths = []
|
|
68
|
+
for ( let namedExport of exports ) {
|
|
69
|
+
if ( namedExport.includes( ' as ' ) ) {
|
|
70
|
+
namedExport = namedExport.split( ' as ' )[ 1 ]
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
const temporaryFileName = `${ namedExport }.import.js`
|
|
74
|
+
const temporaryFilePath = join( temporaryDir, temporaryFileName )
|
|
75
|
+
const temporaryFileData = `import { ${ namedExport } } from '${ importFilePath.replace( /\\/g, '/' ) }'`
|
|
76
|
+
|
|
77
|
+
mkdirSync( temporaryDir, { recursive: true } )
|
|
78
|
+
writeFileSync( temporaryFilePath, temporaryFileData )
|
|
79
|
+
|
|
80
|
+
temporaryFilePaths.push( temporaryFilePath )
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
// Bundle each temporary files and check side effects
|
|
84
|
+
let fileName, bundleFileName, bundleFilePath
|
|
85
|
+
for ( const temporaryFilePath of temporaryFilePaths ) {
|
|
86
|
+
|
|
87
|
+
fileName = basename( temporaryFilePath )
|
|
88
|
+
bundleFileName = fileName.replace( '.tmp.', '.bundle.' )
|
|
89
|
+
bundleFilePath = join( outputDir, bundleFileName )
|
|
90
|
+
|
|
91
|
+
try {
|
|
92
|
+
|
|
93
|
+
configuration.input = temporaryFilePath
|
|
94
|
+
configuration.output.file = bundleFilePath
|
|
95
|
+
|
|
96
|
+
const bundle = await rollup( configuration )
|
|
97
|
+
const { output } = await bundle.generate( configuration.output )
|
|
98
|
+
|
|
99
|
+
let code = output[ 0 ].code
|
|
100
|
+
if ( code.length > 1 ) {
|
|
101
|
+
log( red( `[${ bundleFileName }] contain side-effects !` ) )
|
|
102
|
+
await bundle.write( configuration.output )
|
|
103
|
+
} else {
|
|
104
|
+
log( green( `[${ bundleFileName }] is side-effect free.` ) )
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
} catch ( error ) {
|
|
108
|
+
|
|
109
|
+
log( red( error.message ) )
|
|
110
|
+
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
} catch ( error ) {
|
|
115
|
+
log( red( error.message ) )
|
|
116
|
+
} finally {
|
|
117
|
+
|
|
118
|
+
done()
|
|
119
|
+
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
}
|
|
123
|
+
checkBundlingFromEsmBuildImportTask.displayName = basename( import.meta.filename, '.task.mjs' )
|
|
124
|
+
checkBundlingFromEsmBuildImportTask.description = 'Verify that the project esm build is correctly importable in third party esm files'
|
|
125
|
+
checkBundlingFromEsmBuildImportTask.flags = null
|
|
126
|
+
|
|
127
|
+
export { checkBundlingFromEsmBuildImportTask }
|