better support for Node.js ESM

This commit is contained in:
Juanra Dikal 2022-08-01 04:04:00 +02:00
parent e29be711a7
commit 94d0a78c00
19 changed files with 2482 additions and 1280 deletions

View File

@ -15,7 +15,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
strategy: strategy:
matrix: matrix:
node-version: [10, 12, 14, 16] node-version: [14, 16, 18]
steps: steps:
- uses: actions/checkout@v2 - uses: actions/checkout@v2

View File

@ -1,7 +1,7 @@
[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT) [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
[![Contributor Covenant](https://img.shields.io/badge/Contributor%20Covenant-2.1-4baaaa.svg)](CODE_OF_CONDUCT.md) [![Contributor Covenant](https://img.shields.io/badge/Contributor%20Covenant-2.1-4baaaa.svg)](CODE_OF_CONDUCT.md)
[![JavaScript Style Guide](https://img.shields.io/badge/code_style-standard-brightgreen.svg)](https://standardjs.com) [![JavaScript Style Guide](https://img.shields.io/badge/code_style-standard-brightgreen.svg)](https://standardjs.com)
[![Node.js CI](https://github.com/juanelas/bigint-mod-arith/workflows/Node.js%20CI/badge.svg)](https://github.com/juanelas/bigint-mod-arith/actions?query=workflow%3A%22Node.js+CI%22) [![Node.js CI](https://github.com/juanelas/bigint-mod-arith/workflows/build/badge.svg)](https://github.com/juanelas/bigint-mod-arith/actions?query=workflow%3A%22build%22)
[![Coverage Status](https://coveralls.io/repos/github/juanelas/bigint-mod-arith/badge.svg?branch=master)](https://coveralls.io/github/juanelas/bigint-mod-arith?branch=master) [![Coverage Status](https://coveralls.io/repos/github/juanelas/bigint-mod-arith/badge.svg?branch=master)](https://coveralls.io/github/juanelas/bigint-mod-arith?branch=master)
# bigint-mod-arith # bigint-mod-arith

View File

@ -84,7 +84,7 @@ if (repoProvider) {
iifeBundle = `[IIFE bundle](https://raw.githubusercontent.com/${repoUsername}/${repoName}/master/${iifeBundlePath})` iifeBundle = `[IIFE bundle](https://raw.githubusercontent.com/${repoUsername}/${repoName}/master/${iifeBundlePath})`
esmBundle = `[ESM bundle](https://raw.githubusercontent.com/${repoUsername}/${repoName}/master/${esmBundlePath})` esmBundle = `[ESM bundle](https://raw.githubusercontent.com/${repoUsername}/${repoName}/master/${esmBundlePath})`
umdBundle = `[UMD bundle](https://raw.githubusercontent.com/${repoUsername}/${repoName}/master/${umdBundlePath})` umdBundle = `[UMD bundle](https://raw.githubusercontent.com/${repoUsername}/${repoName}/master/${umdBundlePath})`
workflowBadget = `[![Node.js CI](https://github.com/${repoUsername}/${repoName}/workflows/Node.js%20CI/badge.svg)](https://github.com/${repoUsername}/${repoName}/actions?query=workflow%3A%22Node.js+CI%22)` workflowBadget = `[![Node.js CI](https://github.com/${repoUsername}/${repoName}/workflows/build/badge.svg)](https://github.com/${repoUsername}/${repoName}/actions?query=workflow%3A%22build%22)`
coverallsBadge = `[![Coverage Status](https://coveralls.io/repos/github/${repoUsername}/${repoName}/badge.svg?branch=master)](https://coveralls.io/github/${repoUsername}/${repoName}?branch=master)` coverallsBadge = `[![Coverage Status](https://coveralls.io/repos/github/${repoUsername}/${repoName}/badge.svg?branch=master)](https://coveralls.io/github/${repoUsername}/${repoName}?branch=master)`
break break

View File

@ -108,16 +108,16 @@ export default [
typescriptPlugin(tsBundleOptions), typescriptPlugin(tsBundleOptions),
resolve({ resolve({
browser: true, browser: true,
exportConditions: ['browser', 'module', 'import', 'default'], exportConditions: ['browser', 'default'],
mainFields: ['browser', 'module', 'main'] mainFields: ['browser', 'main']
}), }),
commonjs({ commonjs({
namedExports: { // namedExports: {
'bn.js': ['BN'], // 'bn.js': ['BN'],
'hash.js': ['hmac', 'ripemd160', 'sha256', 'sha512'], // 'hash.js': ['hmac', 'ripemd160', 'sha256', 'sha512'],
elliptic: ['ec'], // elliptic: ['ec'],
'scrypt-js': ['scrypt', 'syncScrypt'] // 'scrypt-js': ['scrypt', 'syncScrypt']
} // }
}), }),
json() json()
] ]

View File

@ -1,4 +1,9 @@
const path = require('path')
const puppeteer = require('puppeteer') const puppeteer = require('puppeteer')
const minimatch = require('minimatch')
const glob = require('glob')
const rootDir = path.join(__dirname, '../../..')
const browserTests = async ( const browserTests = async (
{ {
@ -9,9 +14,9 @@ const browserTests = async (
headless: false, headless: false,
devtools: true devtools: true
} }
}) => { }, testFiles) => {
const server = require('./server.js').server const server = require('./server.cjs').server
await server.init() await server.init(testFiles)
await server.listen(serverPort) await server.listen(serverPort)
const browser = await puppeteer.launch(puppeteerOptions) const browser = await puppeteer.launch(puppeteerOptions)
const page = (await browser.pages())[0] const page = (await browser.pages())[0]
@ -76,6 +81,24 @@ const browserTests = async (
} }
} }
function processedTestFiles (testFilesStr) {
if (testFilesStr === undefined) {
return undefined
}
// Let us first remove surrounding quotes in string (it gives issues in windows)
testFilesStr = testFilesStr.replace(/^['"]/, '').replace(/['"]$/, '')
const filenames = glob.sync(testFilesStr, { cwd: rootDir, matchBase: true })
if (filenames.length > 0) {
filenames.forEach(file => {
const isTsTestFile = minimatch(file, '{test/**/*.ts,src/**/*.spec.ts}', { matchBase: true })
if (!isTsTestFile) {
throw new Error(`test file '${file}' not found`)
}
})
}
return filenames
}
const opts = { const opts = {
// puppeteer options // puppeteer options
puppeteerOptions: { puppeteerOptions: {
@ -92,6 +115,7 @@ const opts = {
const args = process.argv.slice(2) const args = process.argv.slice(2)
if (args[0] === 'headless') { if (args[0] === 'headless') {
opts.puppeteerOptions.headless = true opts.puppeteerOptions.headless = true
args.shift()
} }
browserTests(opts) browserTests(opts, processedTestFiles(args[0]))

View File

@ -4,6 +4,7 @@ const fs = require('fs')
const http = require('http') const http = require('http')
const path = require('path') const path = require('path')
const pkgJson = require('../../../package.json') const pkgJson = require('../../../package.json')
require('dotenv').config()
const rollup = require('rollup') const rollup = require('rollup')
const resolve = require('@rollup/plugin-node-resolve').nodeResolve const resolve = require('@rollup/plugin-node-resolve').nodeResolve
@ -54,10 +55,11 @@ const tsBundleOptions = {
outDir: undefined // ignore outDir in tsconfig.json outDir: undefined // ignore outDir in tsconfig.json
} }
async function buildTests () { async function buildTests (testFiles) {
// create a bundle // create a bundle
const input = testFiles ?? [path.join(rootDir, pkgJson.directories.test, '**/*.ts'), path.join(rootDir, pkgJson.directories.src, '**/*.spec.ts')]
const inputOptions = { const inputOptions = {
input: [path.join(rootDir, pkgJson.directories.test, '**/*.ts'), path.join(rootDir, pkgJson.directories.src, '**/*.spec.ts')], input,
plugins: [ plugins: [
multi({ exports: true }), multi({ exports: true }),
replace({ replace({
@ -77,7 +79,12 @@ async function buildTests () {
const bundle = await rollup.rollup(inputOptions) const bundle = await rollup.rollup(inputOptions)
const { output } = await bundle.generate({ format: 'esm' }) const { output } = await bundle.generate({ format: 'esm' })
await bundle.close() await bundle.close()
return output[0].code let bundledCode = output[0].code
const replacements = _getEnvVarsReplacements(bundledCode)
for (const replacement in replacements) {
bundledCode = bundledCode.replaceAll(replacement, replacements[replacement])
}
return bundledCode
} }
class TestServer { class TestServer {
@ -85,8 +92,8 @@ class TestServer {
this.server = http.createServer() this.server = http.createServer()
} }
async init () { async init (testFiles) {
const tests = await buildTests() const tests = await buildTests(testFiles)
this.server.on('request', function (req, res) { this.server.on('request', function (req, res) {
if (req.url === `/${name}.esm.js`) { if (req.url === `/${name}.esm.js`) {
fs.readFile(path.join(rootDir, pkgJson.directories.dist, 'bundles/esm.js'), function (err, data) { fs.readFile(path.join(rootDir, pkgJson.directories.dist, 'bundles/esm.js'), function (err, data) {
@ -148,4 +155,29 @@ class TestServer {
} }
} }
function _getEnvVarsReplacements (testsCode) {
const replacements = {}
const missingEnvVars = []
for (const match of testsCode.matchAll(/process\.env\.(\w+)/g)) {
const envVar = match[1]
if (process.env[envVar] !== undefined) {
replacements[match[0]] = '`' + process.env[envVar] + '`'
} else {
missingEnvVars.push(envVar)
}
}
for (const match of testsCode.matchAll(/process\.env\[['"](\w+)['"]\]/g)) {
const envVar = match[1]
if (process.env[envVar] !== undefined) {
replacements[match[0]] = '`' + process.env[envVar] + '`'
} else {
missingEnvVars.push(envVar)
}
}
if (missingEnvVars.length > 0) {
throw EvalError('The folloinwg environment variables are missing in your .env file: ' + missingEnvVars)
}
return replacements
}
exports.server = new TestServer() exports.server = new TestServer()

View File

@ -3,9 +3,9 @@ const fs = require('fs')
const path = require('path') const path = require('path')
const rollup = require('rollup') const rollup = require('rollup')
const loadAndParseConfigFile = require('rollup/dist/loadConfigFile') const loadAndParseConfigFile = require('rollup/dist/loadConfigFile.js')
const Builder = require('./Builder.js') const Builder = require('./Builder.cjs')
const rootDir = path.join(__dirname, '../../../../') const rootDir = path.join(__dirname, '../../../../')
const pkgJson = require(path.join(rootDir, 'package.json')) const pkgJson = require(path.join(rootDir, 'package.json'))

View File

@ -4,7 +4,7 @@ const fs = require('fs')
const ts = require('typescript') const ts = require('typescript')
const JSON5 = require('json5') const JSON5 = require('json5')
const Builder = require('./Builder.js') const Builder = require('./Builder.cjs')
const rootDir = path.join(__dirname, '../../../../') const rootDir = path.join(__dirname, '../../../../')
const mochaTsRelativeDir = '.mocha-ts' const mochaTsRelativeDir = '.mocha-ts'

View File

@ -5,8 +5,10 @@ const path = require('path')
const chai = require('chai') const chai = require('chai')
const rimraf = require('rimraf') const rimraf = require('rimraf')
const RollupBuilder = require('./builders/RollupBuilder.js') const RollupBuilder = require('./builders/RollupBuilder.cjs')
const TestsBuilder = require('./builders/TestsBuilder.js') const TestsBuilder = require('./builders/TestsBuilder.cjs')
require('dotenv').config()
const rootDir = path.join(__dirname, '../../../') const rootDir = path.join(__dirname, '../../../')

2
dist/bundles/esm.js vendored

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -43,7 +43,7 @@ The absolute value of a
#### Defined in #### Defined in
[abs.ts:8](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/abs.ts#L8) [abs.ts:8](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/abs.ts#L8)
___ ___
@ -67,7 +67,7 @@ The bit length
#### Defined in #### Defined in
[bitLength.ts:7](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/bitLength.ts#L7) [bitLength.ts:7](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/bitLength.ts#L7)
___ ___
@ -78,7 +78,8 @@ ___
An iterative implementation of the extended euclidean algorithm or extended greatest common divisor algorithm. An iterative implementation of the extended euclidean algorithm or extended greatest common divisor algorithm.
Take positive integers a, b as input, and return a triple (g, x, y), such that ax + by = g = gcd(a, b). Take positive integers a, b as input, and return a triple (g, x, y), such that ax + by = g = gcd(a, b).
**`throws`** {RangeError} **`Throws`**
This excepction is thrown if a or b are less than 0 This excepction is thrown if a or b are less than 0
#### Parameters #### Parameters
@ -96,7 +97,7 @@ A triple (g, x, y), such that ax + by = g = gcd(a, b).
#### Defined in #### Defined in
[egcd.ts:18](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/egcd.ts#L18) [egcd.ts:18](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/egcd.ts#L18)
___ ___
@ -121,7 +122,7 @@ The greatest common divisor of a and b
#### Defined in #### Defined in
[gcd.ts:10](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/gcd.ts#L10) [gcd.ts:10](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/gcd.ts#L10)
___ ___
@ -146,7 +147,7 @@ The least common multiple of a and b
#### Defined in #### Defined in
[lcm.ts:10](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/lcm.ts#L10) [lcm.ts:10](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/lcm.ts#L10)
___ ___
@ -171,7 +172,7 @@ Maximum of numbers a and b
#### Defined in #### Defined in
[max.ts:9](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/max.ts#L9) [max.ts:9](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/max.ts#L9)
___ ___
@ -196,7 +197,7 @@ Minimum of numbers a and b
#### Defined in #### Defined in
[min.ts:9](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/min.ts#L9) [min.ts:9](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/min.ts#L9)
___ ___
@ -206,7 +207,8 @@ ___
Modular inverse. Modular inverse.
**`throws`** {RangeError} **`Throws`**
Excpeption thorwn when a does not have inverse modulo n Excpeption thorwn when a does not have inverse modulo n
#### Parameters #### Parameters
@ -224,7 +226,7 @@ The inverse modulo n
#### Defined in #### Defined in
[modInv.ts:14](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/modInv.ts#L14) [modInv.ts:14](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/modInv.ts#L14)
___ ___
@ -234,7 +236,8 @@ ___
Modular exponentiation b**e mod n. Currently using the right-to-left binary method Modular exponentiation b**e mod n. Currently using the right-to-left binary method
**`throws`** {RangeError} **`Throws`**
Excpeption thrown when n is not > 0 Excpeption thrown when n is not > 0
#### Parameters #### Parameters
@ -253,7 +256,7 @@ b**e mod n
#### Defined in #### Defined in
[modPow.ts:16](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/modPow.ts#L16) [modPow.ts:16](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/modPow.ts#L16)
___ ___
@ -263,10 +266,12 @@ ___
Finds the smallest positive element that is congruent to a in modulo n Finds the smallest positive element that is congruent to a in modulo n
**`remarks`** **`Remarks`**
a and b must be the same type, either number or bigint a and b must be the same type, either number or bigint
**`throws`** {RangeError} **`Throws`**
Excpeption thrown when n is not > 0 Excpeption thrown when n is not > 0
#### Parameters #### Parameters
@ -284,4 +289,4 @@ A bigint with the smallest positive representation of a modulo n
#### Defined in #### Defined in
[toZn.ts:15](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/toZn.ts#L15) [toZn.ts:15](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/toZn.ts#L15)

View File

@ -16,7 +16,7 @@
#### Defined in #### Defined in
[egcd.ts:2](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/egcd.ts#L2) [egcd.ts:2](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/egcd.ts#L2)
___ ___
@ -26,7 +26,7 @@ ___
#### Defined in #### Defined in
[egcd.ts:3](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/egcd.ts#L3) [egcd.ts:3](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/egcd.ts#L3)
___ ___
@ -36,4 +36,4 @@ ___
#### Defined in #### Defined in
[egcd.ts:4](https://github.com/juanelas/bigint-mod-arith/blob/41c8b15/src/ts/egcd.ts#L4) [egcd.ts:4](https://github.com/juanelas/bigint-mod-arith/blob/e29be71/src/ts/egcd.ts#L4)

3567
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -23,6 +23,7 @@
"engines": { "engines": {
"node": ">=10.4.0" "node": ">=10.4.0"
}, },
"type": "module",
"types": "./types/index.d.ts", "types": "./types/index.d.ts",
"main": "./dist/cjs/index.node.cjs", "main": "./dist/cjs/index.node.cjs",
"browser": "./dist/esm/index.browser.js", "browser": "./dist/esm/index.browser.js",
@ -31,7 +32,8 @@
".": { ".": {
"node": { "node": {
"require": "./dist/cjs/index.node.cjs", "require": "./dist/cjs/index.node.cjs",
"import": "./dist/esm/index.node.js" "import": "./dist/esm/index.node.js",
"module": "./dist/esm/index.node.js"
}, },
"default": "./dist/esm/index.browser.js" "default": "./dist/esm/index.browser.js"
}, },
@ -51,18 +53,21 @@
"build": "run-s lint build:js docs", "build": "run-s lint build:js docs",
"build:js": "rollup -c build/rollup.config.js", "build:js": "rollup -c build/rollup.config.js",
"clean": "rimraf .nyc_output .mocha-ts coverage dist types docs", "clean": "rimraf .nyc_output .mocha-ts coverage dist types docs",
"coverage": "nyc --check-coverage --exclude build --exclude '{src/ts/**/*.spec.ts,test/**/*.ts,.mocha-ts/**/*}' --reporter=text --reporter=lcov node ./build/bin/mocha-ts.js --require build/testing/mocha/mocha-init.js '{src/ts/**/*.spec.ts,test/**/*.ts}'", "coverage": "nyc --check-coverage --exclude build --exclude '{src/ts/**/*.spec.ts,test/**/*.ts,.mocha-ts/**/*}' --reporter=text --reporter=lcov node ./build/bin/mocha-ts.cjs --require build/testing/mocha/mocha-init.js '{src/ts/**/*.spec.ts,test/**/*.ts}'",
"docs": "node build/build.docs.js", "docs": "node build/build.docs.cjs",
"git:add": "git add -A", "git:add": "git add -A",
"lint": "ts-standard --fix", "lint": "ts-standard --fix",
"mocha": "node ./build/bin/mocha-ts.js --require build/testing/mocha/mocha-init.js ", "mocha-ts": "node ./build/bin/mocha-ts.cjs --require build/testing/mocha/mocha-init.cjs ",
"version": "run-s build test:browser-headless coverage git:add", "mocha-ts:browser": "node build/testing/browser/index.cjs ",
"mocha-ts:browser-headless": "node build/testing/browser/index.cjs headless ",
"preversion": "run-s clean lint build:js coverage test:browser-headless",
"version": "run-s docs git:add",
"postversion": "git push --follow-tags", "postversion": "git push --follow-tags",
"test": "run-s test:browser-headless test:node", "test": "run-s test:browser-headless test:node",
"test:browser": "node build/testing/browser/index.js", "test:browser": "npm run mocha-ts:browser ",
"test:browser-headless": "node build/testing/browser/index.js headless", "test:browser-headless": "npm run mocha-ts:browser-headless ",
"test:node": "npm run mocha -- '{src/ts/**/*.spec.ts,test/**/*.ts}'", "test:node": "npm run mocha-ts -- '{src/ts/**/*.spec.ts,test/**/*.ts}'",
"watch": "npm run mocha -- --watch '{src/ts/**/*.spec.ts,test/**/*.ts}'" "watch": "npm run mocha-ts:node -- --watch '{src/ts/**/*.spec.ts,test/**/*.ts}'"
}, },
"ts-standard": { "ts-standard": {
"env": [ "env": [
@ -83,30 +88,31 @@
] ]
}, },
"devDependencies": { "devDependencies": {
"@rollup/plugin-commonjs": "^21.0.0", "@rollup/plugin-commonjs": "^22.0.0",
"@rollup/plugin-json": "^4.1.0", "@rollup/plugin-json": "^4.1.0",
"@rollup/plugin-multi-entry": "^4.0.0", "@rollup/plugin-multi-entry": "^4.0.0",
"@rollup/plugin-node-resolve": "^13.0.5", "@rollup/plugin-node-resolve": "^13.0.5",
"@rollup/plugin-replace": "^3.0.0", "@rollup/plugin-replace": "^4.0.0",
"@rollup/plugin-typescript": "^8.2.0", "@rollup/plugin-typescript": "^8.2.0",
"@types/chai": "^4.2.22", "@types/chai": "^4.2.22",
"@types/mocha": "^9.0.0", "@types/mocha": "^9.0.0",
"chai": "^4.3.3", "chai": "^4.3.3",
"dotenv": "^16.0.0",
"fs-extra": "^10.0.0", "fs-extra": "^10.0.0",
"glob": "^7.2.0", "glob": "^8.0.1",
"json5": "^2.2.0", "json5": "^2.2.0",
"minimatch": "^3.0.4", "minimatch": "^5.0.1",
"mocha": "^9.1.1", "mocha": "^10.0.0",
"npm-run-all": "^4.1.5", "npm-run-all": "^4.1.5",
"nyc": "^15.1.0", "nyc": "^15.1.0",
"pirates": "^4.0.1", "pirates": "^4.0.1",
"puppeteer": "^12.0.1", "puppeteer": "^15.5.0",
"rimraf": "^3.0.2", "rimraf": "^3.0.2",
"rollup": "^2.57.0", "rollup": "^2.57.0",
"rollup-plugin-terser": "^7.0.2", "rollup-plugin-terser": "^7.0.2",
"ts-standard": "^11.0.0", "ts-standard": "^11.0.0",
"tslib": "^2.3.1", "tslib": "^2.3.1",
"typedoc": "^0.22.0", "typedoc": "^0.23.0",
"typedoc-plugin-markdown": "^3.11.0", "typedoc-plugin-markdown": "^3.11.0",
"typescript": "^4.4.3" "typescript": "^4.4.3"
} }