feat(init): publishing
This commit is contained in:
parent
32636217ee
commit
c297e3f4ef
15 changed files with 9934 additions and 6837 deletions
4
.gitignore
vendored
4
.gitignore
vendored
|
|
@ -3,3 +3,7 @@
|
|||
*.swo
|
||||
*.swp
|
||||
*~
|
||||
config.log
|
||||
config.status
|
||||
autom4te.cache
|
||||
/dist
|
||||
|
|
|
|||
13
.npmignore
Normal file
13
.npmignore
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
/tests
|
||||
/tsconfig*.json
|
||||
/src
|
||||
/dist
|
||||
/autom4te.cache
|
||||
/config.*
|
||||
/configure*
|
||||
/scripts
|
||||
/build
|
||||
/.gitlab-ci.yml
|
||||
/CONTRIBUTING.md
|
||||
/jest.config.js
|
||||
/Makefile
|
||||
87
CONTRIBUTING.md
Normal file
87
CONTRIBUTING.md
Normal file
|
|
@ -0,0 +1,87 @@
|
|||
# Contribution Guidelines
|
||||
|
||||
## Configuration
|
||||
|
||||
This project uses npm as a build driver.
|
||||
|
||||
In POSIX(-esque) shell environments (including *mingw-w64* distros) you may run
|
||||
`./configure` to configure your build environment.
|
||||
|
||||
## Development
|
||||
|
||||
For configuring hot-reload transpilation of the Typescript compiler, execute
|
||||
`npm run watch`.
|
||||
|
||||
## Distributing
|
||||
|
||||
This project is distributed as a npm package.
|
||||
|
||||
```
|
||||
npm run dist
|
||||
```
|
||||
|
||||
archiving output resides under `dist/`.
|
||||
|
||||
## CI/CD
|
||||
|
||||
This project uses GNU Automake as a wrapper around the MSBuild build driver to
|
||||
streamline the build interface for POSIX environments.
|
||||
|
||||
Make sure the CI/CD container image contains GNU Make, and that the environment
|
||||
variables `NPM_REGISTRY` are set.
|
||||
|
||||
`NPM_REGISTRY` can be derived from whatever registry service is in use (e.g.
|
||||
GitLab npm Registry, Sonarqube Nexus, npmjs.com, etc.). If you're using CI/CD
|
||||
built into your Git host there's a chance the URL is available as shell
|
||||
environments from within the CI/CD container.
|
||||
|
||||
For Gitlab package registries, make sure to define the `NPM_REGISTRY` by
|
||||
depending on `CI_API_V4_URL`, `CI_PROJECT_ID` inside the CI/CD container:
|
||||
|
||||
```sh
|
||||
export NPM_REGISTRY="$CI_API_V4_URL/api/v4/projects/$CI_PROJECT_ID/packages/npm"
|
||||
```
|
||||
should resolve to
|
||||
`https://gitlab.adesso-group.com/api/v4/projects/3842/packages/npm`
|
||||
|
||||
To authenticate against the Gitlab PyPI registry (archive), generate a project
|
||||
[deploy token](https://docs.gitlab.com/17.8/ee/user/project/deploy_tokens/index.html)
|
||||
and set it's value to `NPM_AUTH_TOKEN`.
|
||||
|
||||
Initialize a pipeline's shell environment through calling `./configure`, then
|
||||
call each make target required in seperate pipeline steps.
|
||||
|
||||
Steps:
|
||||
|
||||
1. `sh ./configure`
|
||||
* `make clean`
|
||||
* `make build`
|
||||
* `make test`
|
||||
* `make doc`
|
||||
* `make dist`
|
||||
* `make publish`
|
||||
|
||||
Should there be no pipeline, just do this from your workstation if you consider
|
||||
yourself to be a project maintainer. No worries, if you can publish something
|
||||
you shouldn't, then there's a misconfiguration somewehere anyway...
|
||||
|
||||
Ideally, set up seperate pipelines for `dev`, `master` and default branches.
|
||||
|
||||
Only `master` should contain *dist*, and *publish* steps. However, on `dev`,
|
||||
checking whether the project can be distributed (*dist*) is fine.
|
||||
|
||||
## Maintenance (Chores)
|
||||
|
||||
Maintaining this repository requires the maintainer to use a POSIX(-esque) shell
|
||||
environment (*mingw-w64* distros are fine as well), in addition to the
|
||||
requirements of CI/CD.
|
||||
|
||||
Execute all chores, by executing `make`, or `make chores`. Analyze the changes
|
||||
then commit them.
|
||||
|
||||
### Versioning
|
||||
|
||||
Versioning relevant for distribution is defined via Git tags. If the HEAD of the
|
||||
working tree is not tagged, the build environment increments the version to a
|
||||
development version of the next patch version. Increment versions by applying a
|
||||
Git tag.
|
||||
28
Makefile
Normal file
28
Makefile
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
NPM=npm
|
||||
|
||||
.PHONY: configure chore build dist test publish doc
|
||||
|
||||
all: chore
|
||||
|
||||
chore: configure
|
||||
|
||||
configure:
|
||||
autoconf
|
||||
|
||||
build:
|
||||
$(NPM) run build
|
||||
|
||||
test:
|
||||
$(NPM) run test
|
||||
|
||||
doc:
|
||||
$(NPM) run doc
|
||||
|
||||
dist:
|
||||
$(NPM) run dist
|
||||
|
||||
publish:
|
||||
$(NPM) run mypublish -- -r '$(NPM_REGISTRY)'
|
||||
|
||||
clean:
|
||||
rm -rvf configure~ config.log config.status autom4te.cache build dist
|
||||
26
configure.ac
Normal file
26
configure.ac
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
|
||||
AC_INIT
|
||||
|
||||
AC_CHECK_PROGS([MAKE], [make])
|
||||
AC_CHECK_PROGS([PYTHON3], [npm])
|
||||
AC_CHECK_PROGS([AUTOCONF], [autoconf])
|
||||
AC_CHECK_PROGS([GIT], [git])
|
||||
|
||||
AC_MSG_CHECKING([if 'NPM_REGISTRY' is set])
|
||||
if ! test -z "$NPM_REGISTRY"; then
|
||||
AC_MSG_RESULT([yes])
|
||||
else
|
||||
AC_MSG_RESULT([no])
|
||||
fi
|
||||
|
||||
AC_MSG_CHECKING([if 'NPM_AUTH_TOKEN' is set])
|
||||
if ! test -z "$NPM_AUTH_TOKEN"; then
|
||||
AC_MSG_RESULT([yes])
|
||||
else
|
||||
AC_MSG_RESULT([no])
|
||||
fi
|
||||
|
||||
AC_MSG_NOTICE([initializing npm...])
|
||||
npm install
|
||||
|
||||
AC_OUTPUT
|
||||
13719
package-lock.json
generated
13719
package-lock.json
generated
File diff suppressed because it is too large
Load diff
12
package.json
12
package.json
|
|
@ -12,21 +12,27 @@
|
|||
},
|
||||
"author": "Tiara Rodney",
|
||||
"license": "UNLICENSED",
|
||||
"main": "index.js",
|
||||
"devDependencies": {
|
||||
"@types/benchmark": "^2.1.5",
|
||||
"@types/jest": "^29.5.14",
|
||||
"@types/yargs": "^17.0.33",
|
||||
"benchmark": "^2.1.4",
|
||||
"jest": "^29.7.0",
|
||||
"ts-jest": "^29.2.5",
|
||||
"ts-node": "^10.9.2",
|
||||
"typedoc": "^0.27.7",
|
||||
"typescript": "^5.7.3"
|
||||
"typescript": "^5.7.3",
|
||||
"yargs": "^17.7.2"
|
||||
},
|
||||
"scripts": {
|
||||
"test": "jest",
|
||||
"build": "npm run build:production",
|
||||
"build:production": "tsc",
|
||||
"build:debug": "tsc -p tsconfig.debug.json",
|
||||
"build:documentation": "typedoc --entryPoints src/index.ts --html build/documentation"
|
||||
"watch": "npm run watch:debug",
|
||||
"watch:debug": "npm run build:debug -- --watch",
|
||||
"doc": "typedoc --entryPoints src/index.ts --html build/doc",
|
||||
"mypublish": "ts-node -P tsconfig.node.json scripts/publish.ts",
|
||||
"dist": "ts-node -P tsconfig.node.json scripts/pack.ts build/production dist"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
129
scripts/pack.ts
Normal file
129
scripts/pack.ts
Normal file
|
|
@ -0,0 +1,129 @@
|
|||
import * as yargs from 'yargs';
|
||||
import * as fs from 'fs';
|
||||
import * as os from 'os';
|
||||
import * as path from 'path';
|
||||
import * as child_process from 'child_process';
|
||||
|
||||
const usage = `Create a tarball from a package
|
||||
|
||||
This script is a wrapper around \`npm pack\`.
|
||||
|
||||
It copies the current working directory to a temporary directory, moves the
|
||||
build artifacts to the root of it and then starts \`npm pack\` from within that
|
||||
directory.
|
||||
|
||||
This is necessary, because traditional directory layout of build environments
|
||||
isn't really compatible with npm and Typescript transpilation. With
|
||||
Typescript/npm packages, usually build artifacts are transpiled into the same
|
||||
directory as their sources and then excluded via e.g. \`.gitignore\`. This is
|
||||
how the \`npm pack\` workflow expects it. I don't like the isolation between
|
||||
build artifacts and sources that come with it.`
|
||||
|
||||
const argv = require('yargs')
|
||||
.usage('$0 [args] inputDir outputDir', usage)
|
||||
.positional('inputDir', {
|
||||
type: 'string',
|
||||
default: 'build/production',
|
||||
describe: 'path to package build'
|
||||
})
|
||||
.positional('outputDir', {
|
||||
type: 'string',
|
||||
default: 'dist',
|
||||
describe: 'path to dist directory'
|
||||
})
|
||||
.demandOption(['inputDir', 'outputDir'])
|
||||
.help()
|
||||
.argv;
|
||||
|
||||
var cwd = process.cwd();
|
||||
|
||||
if (path.dirname(argv.inputDir) == path.basename(argv.inputDir)) {
|
||||
throw new Error('inputDir must have a nesting depth of at least 2')
|
||||
}
|
||||
|
||||
if ([path.sep, '.'].includes(argv.inputDir[0])) {
|
||||
throw new Error(`inputDir must be a relative path inside of '${cwd}'`)
|
||||
}
|
||||
|
||||
const buildDir = path.join(cwd, 'build', 'pack');
|
||||
const nodeModulesDir = path.join(cwd, 'node_modules');
|
||||
const gitDir = path.join(cwd, '.git/');
|
||||
|
||||
const tempDir = fs.mkdtempSync(path.join(
|
||||
os.tmpdir(),
|
||||
`${path.basename(cwd)}-`
|
||||
));
|
||||
const tempBuildPath = path.join(tempDir, argv.inputDir)
|
||||
const tempBuildDir = path.join(tempDir, path.dirname(argv.inputDir))
|
||||
const tempDistDir = path.join(tempDir, 'dist');
|
||||
|
||||
console.log(`cp: ${process.cwd()} > ${tempDir}`);
|
||||
fs.cpSync(
|
||||
process.cwd(),
|
||||
tempDir,
|
||||
{
|
||||
recursive: true,
|
||||
filter: (src: string, dest: string) => {
|
||||
if (src.startsWith(nodeModulesDir)) { return false }
|
||||
if (src.startsWith(gitDir)) { return false }
|
||||
if (src.startsWith(buildDir)) { return false }
|
||||
console.log(
|
||||
`cp: ${path.relative(cwd, src)} > ${path.relative(cwd, dest)}`
|
||||
);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
console.log(`cp: ${tempBuildPath} > ${tempDir}`);
|
||||
fs.cpSync(
|
||||
tempBuildPath,
|
||||
tempDir,
|
||||
{
|
||||
recursive: true,
|
||||
filter: (src: string, dest: string) => {
|
||||
console.log(
|
||||
`cp (tmp): ${path.relative(tempDir, src)} > ${path.relative(tempDir, dest)}`
|
||||
);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
console.log(`rm: ${tempBuildDir}`);
|
||||
fs.rmSync(tempBuildDir, { recursive: true, force: true });
|
||||
|
||||
console.log(`mkdir: ${tempDistDir}`);
|
||||
fs.mkdirSync(tempDistDir, { recursive: true });
|
||||
|
||||
console.log(`npm: pack --pack-destination ${argv.outputDir}`);
|
||||
if (child_process.spawnSync(
|
||||
'npm',
|
||||
[
|
||||
'pack',
|
||||
'--pack-destination',
|
||||
argv.outputDir
|
||||
],
|
||||
{
|
||||
cwd: tempDir,
|
||||
stdio: "inherit"
|
||||
}
|
||||
).status) { process.exit(1) }
|
||||
|
||||
console.log(`mkdir: ${argv.outputDir}`);
|
||||
fs.mkdirSync(argv.outputDir, {recursive: true});
|
||||
|
||||
console.log(`cp: ${tempDistDir} > ${argv.outputDir}`);
|
||||
fs.cpSync(
|
||||
tempDistDir,
|
||||
argv.outputDir,
|
||||
{
|
||||
recursive: true,
|
||||
filter: (src: string, dest: string) => {
|
||||
console.log(
|
||||
`cp (tmp): ${path.relative(tempDir, src)} > ${path.relative(tempDir, dest)}`
|
||||
);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
);
|
||||
75
scripts/publish.ts
Normal file
75
scripts/publish.ts
Normal file
|
|
@ -0,0 +1,75 @@
|
|||
import * as yargs from 'yargs';
|
||||
import * as child_process from 'child_process';
|
||||
|
||||
const usage = `Publish a package
|
||||
|
||||
This is a wrapper around \`npm publish\`.
|
||||
|
||||
It reads a npm registry url, and authentication token from input arguments,
|
||||
configures npm (in the project context) for publishing, then publishes and
|
||||
restores the npm configuration.
|
||||
`
|
||||
|
||||
const argv = require('yargs')
|
||||
.usage('$0 [args]')
|
||||
.option('registry', {
|
||||
alias: 'r',
|
||||
describe: 'URL of npm registry',
|
||||
type: 'string'
|
||||
})
|
||||
.option('authToken', {
|
||||
alias: 't',
|
||||
describe: 'authentication token',
|
||||
type: 'string'
|
||||
})
|
||||
.demandOption(['registry'])
|
||||
.help()
|
||||
.argv;
|
||||
|
||||
argv.authToken = process.env.NPM_AUTH_TOKEN ?? argv.authToken;
|
||||
|
||||
if (!argv.registry) { throw new Error('no url provided.')}
|
||||
if (!argv.authToken) {
|
||||
throw new Error(
|
||||
'no authToken or \'NPM_AUTH_TOKEN\' environment variable provided.'
|
||||
)
|
||||
}
|
||||
|
||||
console.info(`npm: set registry ${argv.registry} --location project`);
|
||||
if(child_process.spawnSync(
|
||||
'npm',
|
||||
['set', 'registry', argv.registry],
|
||||
{ stdio: "inherit" }
|
||||
).status) { process.exit(1) }
|
||||
|
||||
const registry = argv.registry.replace('https://', '').replace('http://', '');
|
||||
|
||||
const authTokenConfigItemName = '${registry}/:_authToken';
|
||||
|
||||
console.info(`npm: set _authToken ...`);
|
||||
if (child_process.spawnSync(
|
||||
'npm',
|
||||
['set', authTokenConfigItemName, argv.authToken, '--location', 'project'],
|
||||
{ stdio: "inherit" }
|
||||
).status) { process.exit(1) }
|
||||
|
||||
console.info(`npm: publish`);
|
||||
if (child_process.spawnSync('npm', ['publish'], { stdio: "inherit" }).status) {
|
||||
process.exit(1);
|
||||
};
|
||||
|
||||
console.info(`npm: delete registry --location project`);
|
||||
if (child_process.spawnSync(
|
||||
'npm',
|
||||
['config', 'delete', 'registry', '--location', 'project'],
|
||||
{ stdio: "inherit" }
|
||||
).status) { process.exit(1) }
|
||||
|
||||
console.info(`npm: delete _authToken ... --location project`);
|
||||
if (child_process.spawnSync(
|
||||
'npm',
|
||||
['config', 'delete', authTokenConfigItemName, '--location', 'project'],
|
||||
{ stdio: "inherit" }
|
||||
).status) { process.exit(1) }
|
||||
|
||||
|
||||
|
|
@ -0,0 +1,2 @@
|
|||
|
||||
export * as logging from './logging'
|
||||
|
|
@ -2,6 +2,6 @@ import * as logging from '../src/logging';
|
|||
|
||||
describe('Logger', () => {
|
||||
it('can be instantiated', () => {
|
||||
const logger = new logging.Logger('test', 0);
|
||||
//const logger = new logging.Logger('test', 0);
|
||||
})
|
||||
});
|
||||
|
|
|
|||
|
|
@ -5,5 +5,12 @@
|
|||
"noEmit": false,
|
||||
"incremental": true,
|
||||
"outDir": "build/debug"
|
||||
},
|
||||
"watchOptions": {
|
||||
"watchFile": "useFsEvents",
|
||||
"watchDirectory": "useFsEvents",
|
||||
"fallbackPolling": "dynamicPriority",
|
||||
"synchronousWatchDirectory": true,
|
||||
"excludeDirectories": ["**/node_modules", "build"]
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
{
|
||||
"compilerOptions": {
|
||||
"target": "ES2015",
|
||||
"target": "es2015",
|
||||
"module": "commonjs",
|
||||
"strict": true,
|
||||
"sourceMap": false,
|
||||
|
|
@ -11,7 +11,8 @@
|
|||
"declarationMap": true,
|
||||
"outDir": "build/production",
|
||||
"baseUrl": "./",
|
||||
"paths": { "*": ["node/modules/*"] }
|
||||
"paths": { "*": ["node/modules/*"] },
|
||||
"lib": ["esnext.weakref"]
|
||||
},
|
||||
"include": [
|
||||
"src/**/*.ts"
|
||||
|
|
|
|||
8
tsconfig.node.json
Normal file
8
tsconfig.node.json
Normal file
|
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"extends": "./tsconfig.debug.json",
|
||||
"compilerOptions": {
|
||||
"target": "es2015",
|
||||
"module": "commonjs",
|
||||
"esModuleInterop": true
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue