diff --git a/.github/workflows/release-semantic-release.yml b/.github/workflows/release-semantic-release.yml new file mode 100644 index 0000000..cf07219 --- /dev/null +++ b/.github/workflows/release-semantic-release.yml @@ -0,0 +1,144 @@ +# ALTERNATIVE release pipeline — NOT the active one. +# +# This is the semantic-release variant of .github/workflows/release.yml, kept +# alongside it so maintainers can compare the two approaches on real files +# rather than in the abstract (see docs/RELEASING.md for the trade-offs and +# for how to make this the active workflow). +# +# UNVALIDATED: this has never been executed. It deliberately avoids +# @semantic-release/npm (whose verifyConditions would fail on the not-yet-built +# dist/ package root) and drives the bump/build/publish through +# @semantic-release/exec instead, so the publish command is byte-identical to +# release.yml's and picks up OIDC the same way. Confirm with a real `dry-run` +# before trusting it. The standard-version variant has no such unknowns because +# it reuses the tooling this repo already releases with. +# +# Requires devDependencies that are NOT installed by default: +# semantic-release @semantic-release/changelog @semantic-release/git +# @semantic-release/exec +name: Release (semantic-release) + +on: + workflow_dispatch: + inputs: + dry-run: + description: 'Dry run (analyze commits + build; no publish, commit, tag, or push)' + required: false + type: boolean + default: true + +permissions: + contents: write + id-token: write + issues: write + pull-requests: write + +concurrency: + group: release-${{ github.ref }} + cancel-in-progress: false + +jobs: + gate: + if: ${{ github.ref == 'refs/heads/main' || inputs.dry-run }} + name: ${{ matrix.target }} + runs-on: ubuntu-latest + timeout-minutes: 15 + strategy: + fail-fast: true + matrix: + target: ['test:lib', 'test:schematics', 'build:lib', 'build'] + steps: + - uses: actions/checkout@v4 + with: + persist-credentials: false + + - uses: actions/setup-node@v4 + with: + node-version: 22 + cache: 'npm' + + - run: npm ci + + - name: Run ${{ matrix.target }} + env: + TARGET: ${{ matrix.target }} + run: npm run "$TARGET" + + release: + needs: gate + if: ${{ github.ref == 'refs/heads/main' || inputs.dry-run }} + runs-on: ubuntu-latest + timeout-minutes: 30 + env: + # @semantic-release/git commits internally; skip the husky commit-msg + # (commitlint) and pre-commit (lint-staged) hooks in CI + HUSKY: 0 + steps: + # See the equivalent step in release.yml — the app must be a bypass actor + # on the `protect-main` ruleset for @semantic-release/git to push to main. + - name: Generate app token + id: app-token + uses: actions/create-github-app-token@v3 + with: + app-id: ${{ secrets.RELEASE_APP_ID }} + private-key: ${{ secrets.RELEASE_APP_PRIVATE_KEY }} + permission-contents: write + + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 0 + fetch-tags: true + token: ${{ steps.app-token.outputs.token }} + + # No registry-url — see release.yml for why OIDC depends on that + - name: Setup Node + uses: actions/setup-node@v4 + with: + node-version: 22 + cache: 'npm' + + # OIDC trusted publishing requires npm >= 11.5.1; Node 22 ships 10.9.x + - name: Upgrade npm + run: | + npm i -g npm@latest + npm -v + + - run: npm ci + + - name: Configure Git + run: | + git config user.name "github-actions[bot]" + git config user.email "41898282+github-actions[bot]@users.noreply.github.com" + + # semantic-release runs the whole pipeline itself. With the plugin order + # in .releaserc.json the effective sequence is: + # prepare: write CHANGELOG.md -> bump projects/openng/cashew/package.json + # + npm run build:lib -> commit and push to main + # publish: npm publish dist/openng/cashew -> create the GitHub Release + # so, as in release.yml, the irreversible npm publish comes after the git + # push. Note there is no bump input: semantic-release always infers the + # version from the conventional commits since the last tag. + - name: Release + env: + GITHUB_TOKEN: ${{ steps.app-token.outputs.token }} + DRY_RUN: ${{ inputs.dry-run }} + run: | + DRY=() + if [[ "$DRY_RUN" == "true" ]]; then DRY=(--dry-run); fi + npx semantic-release "${DRY[@]}" + + - name: Summary + if: always() + env: + DRY_RUN: ${{ inputs.dry-run }} + REF: ${{ github.ref }} + ACTOR: ${{ github.actor }} + run: | + { + echo "## Release run (semantic-release)" + echo "" + echo "- Dry run: \`${DRY_RUN}\`" + echo "- Ref: \`${REF}\`" + echo "- Triggered by: @${ACTOR}" + } >> "$GITHUB_STEP_SUMMARY" diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 0000000..5331ea6 --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,232 @@ +name: Release + +on: + workflow_dispatch: + inputs: + bump: + description: 'Version bump (auto = infer from conventional commits)' + required: false + type: choice + default: auto + options: + - auto + - patch + - minor + - major + - prerelease + dry-run: + description: 'Dry run (versions + builds + packs + publish --dry-run; no real publish, commit, tag, or push)' + required: false + type: boolean + default: true + +permissions: + contents: write + id-token: write + +# Per-ref group: real releases (main-only) still serialize, while a +# dry-run dispatched from a branch never queue-blocks a real release +concurrency: + group: release-${{ github.ref }} + cancel-in-progress: false + +jobs: + # Real releases are main-only; dry-runs touch nothing remote (publish runs + # with --dry-run; push/release are gated on !inputs.dry-run), so they may + # be dispatched from any branch to test the pipeline + gate: + if: ${{ github.ref == 'refs/heads/main' || inputs.dry-run }} + name: ${{ matrix.target }} + runs-on: ubuntu-latest + timeout-minutes: 15 + strategy: + fail-fast: true + matrix: + target: ['test:lib', 'test:schematics', 'build:lib', 'build'] + steps: + - uses: actions/checkout@v4 + with: + persist-credentials: false + + - uses: actions/setup-node@v4 + with: + node-version: 22 + cache: 'npm' + + - run: npm ci + + - name: Run ${{ matrix.target }} + env: + TARGET: ${{ matrix.target }} + run: npm run "$TARGET" + + release: + needs: gate + if: ${{ github.ref == 'refs/heads/main' || inputs.dry-run }} + runs-on: ubuntu-latest + timeout-minutes: 30 + env: + # standard-version commits internally; skip the husky commit-msg + # (commitlint) and pre-commit (lint-staged) hooks in CI + HUSKY: 0 + PACKAGE_DIR: dist/openng/cashew + MANIFEST: projects/openng/cashew/package.json + steps: + # Mint a short-lived GitHub App installation token. The app must be a + # bypass actor on the `protect-main` ruleset, so the release commit/tag + # push below is authorized while humans still go through PRs + review. + # The token is auto-revoked when the job ends (effective lifetime ≈ job + # run) and is scoped to repo Contents only. See docs/RELEASING.md. + - name: Generate app token + id: app-token + uses: actions/create-github-app-token@v3 + with: + app-id: ${{ secrets.RELEASE_APP_ID }} + private-key: ${{ secrets.RELEASE_APP_PRIVATE_KEY }} + # Least-privilege: the token only needs Contents (push release + # commit/tag to main + create the GitHub Release). Declaring it + # here enforces the scope at the workflow level instead of relying + # solely on the app installation's configured permissions. + permission-contents: write + + # Persist the app token so the later `git push HEAD:main` authenticates + # as the bypass-capable app — the default GITHUB_TOKEN cannot push to the + # protected branch (rejected with GH006). + # fetch-depth: 0 + fetch-tags: true are required for standard-version to + # find the previous tag; on a shallow clone it treats the whole history + # as unreleased and generates a bogus changelog. + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 0 + fetch-tags: true + token: ${{ steps.app-token.outputs.token }} + + # Deliberately no registry-url: it writes an .npmrc containing + # `_authToken=${NODE_AUTH_TOKEN}`, and with no token set `npm publish` + # fails ENEEDAUTH before it ever attempts OIDC. Trusted publishing + # (below) depends on that file being absent. + - name: Setup Node + uses: actions/setup-node@v4 + with: + node-version: 22 + cache: 'npm' + + # OIDC trusted publishing requires npm >= 11.5.1; Node 22 ships 10.9.x + - name: Upgrade npm + run: | + npm i -g npm@latest + npm -v + + - run: npm ci + + - name: Configure Git + run: | + git config user.name "github-actions[bot]" + git config user.email "41898282+github-actions[bot]@users.noreply.github.com" + + # Always bump the manifest for real so the version is on disk for the + # build + publish steps. On a dry run we pass --skip.commit --skip.tag: + # the files are written (never pushed) so the publish dry-run can pack a + # non-colliding version, but no commit or tag is made. + # projects/openng/cashew/package.json is therefore the authoritative + # version source in both modes (a stable JSON contract; drives the + # changelog + GitHub release). + - name: Version + id: version + env: + BUMP: ${{ inputs.bump }} + DRY_RUN: ${{ inputs.dry-run }} + run: | + set -o pipefail + ARGS=() + case "$BUMP" in + auto) ;; + prerelease) ARGS=(--prerelease) ;; + *) ARGS=(--release-as "$BUMP") ;; + esac + if [[ "$DRY_RUN" == "true" ]]; then ARGS+=(--skip.commit --skip.tag); fi + + ( cd projects/openng/cashew && npx standard-version --infile ../../../CHANGELOG.md "${ARGS[@]}" ) + + VERSION=$(node -p "require('./$MANIFEST').version") + echo "value=$VERSION" >> "$GITHUB_OUTPUT" + echo "Released version: $VERSION" + + # Build AFTER version so the generated dist manifest carries the bumped + # version. postbuild:lib also copies README/LICENSE and compiles the + # schematics into the package directory. + - name: Build + run: npm run build:lib + + # The vX.Y.Z tag must be on the remote BEFORE the release step, otherwise + # the API invents the tag at the old main HEAD + - name: Push commit and tag + if: ${{ !inputs.dry-run }} + run: git push --follow-tags origin HEAD:main + + # Notes come from the CHANGELOG section standard-version just wrote, so + # the GitHub Release and the changelog can never disagree. Uses the app + # token (not the default GITHUB_TOKEN) for consistency with the push. + - name: GitHub release + if: ${{ !inputs.dry-run }} + env: + GH_TOKEN: ${{ steps.app-token.outputs.token }} + VERSION: ${{ steps.version.outputs.value }} + run: | + set -o pipefail + awk -v tag="## [$VERSION]" ' + index($0, tag) == 1 { found = 1; next } + found && index($0, "## ") == 1 { exit } + found { print } + ' CHANGELOG.md > release-notes.md + + if [[ -s release-notes.md ]]; then + gh release create "v$VERSION" --verify-tag --title "v$VERSION" --notes-file release-notes.md + else + echo "::warning::No CHANGELOG section found for $VERSION; falling back to generated notes" + gh release create "v$VERSION" --verify-tag --title "v$VERSION" --generate-notes + fi + rm -f release-notes.md + + # Publish LAST: npm publish is irreversible, so it runs only after every + # fallible git step (push to protected main, tag push, GitHub release) has + # succeeded — preventing an npm-ahead-of-git split-brain where a version + # is on the registry while main stays un-updated. Re-running after a + # publish failure is safe: npm rejects a version that already exists. + # Always runs; on a dry run, --dry-run packs the tarball and exercises + # the publish path (version, package dir, tag, access) without uploading + # — note this does NOT exercise OIDC auth, which only a real publish + # does. Prereleases go to the `next` dist-tag so + # `npm i @openng/cashew` (latest) never resolves to a prerelease. + # Provenance attestations are generated automatically with trusted + # publishing — no --provenance flag needed. + - name: Publish to npm (OIDC trusted publishing + provenance) + env: + BUMP: ${{ inputs.bump }} + DRY_RUN: ${{ inputs.dry-run }} + run: | + TAG="latest" + if [[ "$BUMP" == "prerelease" ]]; then TAG="next"; fi + DRY=() + if [[ "$DRY_RUN" == "true" ]]; then DRY=(--dry-run); fi + npm publish "$PACKAGE_DIR" --access public --tag "$TAG" "${DRY[@]}" + + - name: Summary + if: always() + env: + OUT_VERSION: ${{ steps.version.outputs.value }} + BUMP: ${{ inputs.bump }} + DRY_RUN: ${{ inputs.dry-run }} + REF: ${{ github.ref }} + ACTOR: ${{ github.actor }} + run: | + { + echo "## Release run" + echo "" + echo "- Version: \`${OUT_VERSION:-n/a}\`" + echo "- Bump input: \`${BUMP}\`" + echo "- Dry run: \`${DRY_RUN}\`" + echo "- Ref: \`${REF}\`" + echo "- Triggered by: @${ACTOR}" + } >> "$GITHUB_STEP_SUMMARY" diff --git a/.releaserc.json b/.releaserc.json new file mode 100644 index 0000000..0794418 --- /dev/null +++ b/.releaserc.json @@ -0,0 +1,30 @@ +{ + "$schema": "https://json.schemastore.org/semantic-releaserc.json", + "branches": ["main"], + "tagFormat": "v${version}", + "plugins": [ + "@semantic-release/commit-analyzer", + "@semantic-release/release-notes-generator", + [ + "@semantic-release/changelog", + { + "changelogFile": "CHANGELOG.md" + } + ], + [ + "@semantic-release/exec", + { + "prepareCmd": "npm version ${nextRelease.version} --no-git-tag-version --prefix projects/openng/cashew && npm run build:lib", + "publishCmd": "npm publish dist/openng/cashew --access public --tag latest" + } + ], + "@semantic-release/github", + [ + "@semantic-release/git", + { + "assets": ["CHANGELOG.md", "projects/openng/cashew/package.json"], + "message": "chore(release): ${nextRelease.version} [skip ci]" + } + ] + ] +} diff --git a/docs/RELEASING.md b/docs/RELEASING.md new file mode 100644 index 0000000..c86950c --- /dev/null +++ b/docs/RELEASING.md @@ -0,0 +1,220 @@ +# Releasing `@openng/cashew` + +Releases are cut by the [`Release` workflow](../.github/workflows/release.yml) — a manually +dispatched pipeline that versions, builds, tags, publishes to npm with provenance, and creates the +GitHub Release. + +> [!IMPORTANT] +> The workflow **cannot succeed until the [one-time setup](#one-time-setup) below is done**. It needs +> a GitHub App that can bypass the `protect-main` ruleset, an npm trusted publisher for the package, +> and the missing `v5.x` tags restored. The first two require repository/organization admin. + +## Cutting a release + +1. **Actions → Release → Run workflow**, with `main` selected as the branch. +2. Pick a **bump**: + | Bump | Effect | + | --- | --- | + | `auto` (default) | standard-version infers the bump from the conventional commits since the last tag — `fix:` → patch, `feat:` → minor, `BREAKING CHANGE:` → major | + | `patch` / `minor` / `major` | Force that bump regardless of the commits | + | `prerelease` | Cut a `-0` prerelease and publish it under the **`next`** dist-tag, so `npm i @openng/cashew` never resolves to it | +3. Leave **dry run** ticked for a rehearsal, or **untick it** for a real release. +4. Watch the run. The step summary reports the version, the bump, and whether it was a dry run. + +That's it — there is nothing to do locally. The `npm run release` script still exists for a manual +release, but the workflow is the supported path. + +### What the workflow does, in order + +``` +gate ─ test:lib · test:schematics · build:lib · build (matrix, fail-fast) + │ + ▼ +release + 1. mint GitHub App token (bypasses protect-main) + 2. checkout with full history + tags ← standard-version needs them + 3. Node 22, no registry-url ← OIDC depends on there being no .npmrc + 4. npm ci, then npm i -g npm@latest ← trusted publishing needs npm >= 11.5.1 + 5. standard-version → bump projects/openng/cashew/package.json, + write CHANGELOG.md, commit, tag vX.Y.Z + 6. npm run build:lib → dist/openng/cashew, carrying the new version + 7. git push --follow-tags origin HEAD:main + 8. gh release create vX.Y.Z, notes taken from the new CHANGELOG section + 9. npm publish dist/openng/cashew --access public --tag latest|next + 10. step summary +``` + +Two ordering properties are deliberate and worth preserving if you edit the workflow: + +- **The build runs after the version bump**, so the generated `dist/openng/cashew/package.json` + carries the released version. +- **`npm publish` runs last.** It is the only irreversible step, so every fallible git operation + (push to protected `main`, tag push, release creation) has to succeed first. This is what prevents + an npm-ahead-of-git split-brain where a version exists on the registry but `main` was never + updated. + +On a dry run the manifest and changelog are still written to disk — that is what lets +`npm publish --dry-run` pack a realistic, non-colliding tarball — but nothing is committed, tagged, +pushed, or uploaded. + +## One-time setup + +### 1. GitHub App for the release commit + +`openng-org/cashew` has an active **`protect-main`** ruleset: pushes to `main` must go through a pull +request with one approving review, and there are no bypass actors. The default `GITHUB_TOKEN` is +therefore rejected with `GH006` when the workflow tries to push the `chore(release): X.Y.Z` commit. +A GitHub App added as a bypass actor is the narrowest way around this — it keeps the PR requirement +in force for humans while letting exactly one automated identity push release commits. + +1. **Create the app** (org **Settings → Developer settings → GitHub Apps → New GitHub App**). + Name it something like `openng-release-bot`. Under **Repository permissions** grant + **Contents: Read and write** and nothing else. No webhook needed. +2. **Generate a private key** and note the **App ID**. +3. **Install the app** on `openng-org/cashew` only. +4. **Add repository secrets** (Settings → Secrets and variables → Actions): + - `RELEASE_APP_ID` — the App ID + - `RELEASE_APP_PRIVATE_KEY` — the full contents of the `.pem` file +5. **Add the app as a bypass actor**: Settings → Rules → `protect-main` → **Bypass list** → Add → + the app. Without this step the workflow fails at _Push commit and tag_. + +The workflow requests `permission-contents: write` on the minted token, so the token is scoped down +at dispatch time even if the installation is granted more later. Tokens are short-lived and revoked +when the job ends. + +### 2. npm trusted publishing (OIDC) + +The workflow publishes with [npm trusted publishing](https://docs.npmjs.com/trusted-publishers): +no long-lived `NPM_TOKEN` is stored anywhere, and npm attaches a +[provenance attestation](https://docs.npmjs.com/generating-provenance-statements) automatically — +no `--provenance` flag required. + +**Bootstrap caveat:** `@openng/cashew` does not exist on the registry yet, and a trusted publisher is +configured on an existing package's settings page. So the first publish has to be done by hand: + +1. An owner of the npm `@openng` organization runs, from a clean checkout of `main`: + ```shell + npm ci + npm run build:lib + npm publish dist/openng/cashew --access public + ``` +2. Then on npmjs.com → the package → **Settings → Trusted publishing → GitHub Actions**, with: + - Organization or user: `openng-org` + - Repository: `cashew` + - Workflow filename: `release.yml` +3. From then on every release is fully automated and no token is ever needed. + +Two requirements the workflow already handles, but which break silently if someone "tidies" them: + +- **npm ≥ 11.5.1** (and Node ≥ 22.14.0). Node 22 ships npm 10.9.x, hence the explicit + `npm i -g npm@latest` step. +- **No `registry-url` on `actions/setup-node`.** Setting it writes an `.npmrc` containing + `_authToken=${NODE_AUTH_TOKEN}`; with no token in the environment, `npm publish` then fails + `ENEEDAUTH` before it ever attempts OIDC. + +### 3. Restore the missing `v5.x` tags + +**Do this before the first automated release.** The repository's tags stop at `v4.1.0`, but three +5.x releases were cut — the `chore(release)` commits are on `main` and the entries are in +`CHANGELOG.md`, only the tags were never pushed. standard-version derives its commit range from the +last reachable tag, so as things stand `auto` walks all the way back to `v4.1.0`: it proposes +**6.0.0** (picking up `BREAKING CHANGE:` footers that shipped in 5.0.0) and regenerates a changelog +section duplicating everything already recorded for 5.0.0, 5.1.0 and 5.3.0. + +Recreate the tags on their release commits and push them: + +```shell +git tag v5.0.0 cc781c8 # chore(release): 5.0.0 +git tag v5.1.0 ac663d7 # chore(release): 5.1.0 +git tag v5.3.0 88a5ce9 # chore(release): 5.3.0 +git push origin v5.0.0 v5.1.0 v5.3.0 +``` + +With `v5.3.0` in place, `auto` sees only the commits since it — `feat: add devcontainer setup` and +`feat: add ng add schematic support` — and correctly proposes **5.4.0**. Verify before releasing: + +```shell +cd projects/openng/cashew && npx standard-version --infile ../../../CHANGELOG.md --dry-run +``` + +(If you would rather not rewrite history's tags, the alternative is to dispatch the first release +with an explicit `bump` instead of `auto` and hand-correct `CHANGELOG.md` afterwards. Tagging is +much less work.) + +## Testing the workflow + +`workflow_dispatch` workflows only become dispatchable once the workflow file exists on the +**default branch**. This is a GitHub limitation, not a bug in the workflow: until `release.yml` is +merged to `main`, it will not appear in the Actions tab and the dry run cannot be exercised — even +though the `gate`/`release` jobs are written to allow dry runs from any branch. + +Two ways to rehearse before merging: + +- Push the branch to a **fork** and temporarily make it the fork's default branch, then dispatch with + dry run ticked. The `gate` job and the version/build/pack steps all run; the app-token step will + fail unless the fork has the secrets, so this mainly validates the gate and the version logic. +- Temporarily add a `push:` trigger for the branch, let it run, then remove it before merging. + +Locally you can validate the two parts that carry the most risk: + +```shell +# What version would be cut, and what changelog would be written? +cd projects/openng/cashew && npx standard-version --infile ../../../CHANGELOG.md --dry-run + +# Is the tarball the workflow would publish correct? +npm run build:lib && npm pack --dry-run ./dist/openng/cashew +``` + +## If a release fails + +- **Failure before `npm publish`** — nothing reached the registry. Fix the cause and re-run. If the + commit and tag were already pushed, dispatch again with the same explicit bump, or bump manually. +- **Failure at `npm publish`** — `main` and the tag are already updated, so re-running is safe: npm + rejects a version that already exists, and every step before publish is idempotent. +- **A bad version reached npm** — do not unpublish. Cut a new patch release, and use + `npm deprecate @openng/cashew@x.y.z ""` to steer people off it. + +## Choosing the release tool + +Two workflows are checked in. **`release.yml` (standard-version) is the active one**; +`release-semantic-release.yml` is a dispatch-only alternative that does nothing unless deliberately +run, kept so the two can be compared on real files. + +| | `release.yml` — standard-version | `release-semantic-release.yml` — semantic-release | +| ---------------- | -------------------------------------------------------------------------------- | -------------------------------------------------- | +| Version source | Conventional commits, **overridable** via the `bump` input | Conventional commits, always automatic | +| Tooling | `standard-version`, already a devDependency and what wrote the current CHANGELOG | 4 new devDependencies | +| Changelog format | Unchanged from the existing `CHANGELOG.md` | Regenerated in semantic-release's format | +| Publish safety | git push → GitHub release → npm publish | git push → npm publish → GitHub release | +| Status | Reuses tooling this repo already releases with | **Never executed — validate with a dry run first** | +| Caveat | `standard-version` is deprecated upstream (still functional) | Actively maintained | + +`release-semantic-release.yml` deliberately avoids `@semantic-release/npm`, whose `verifyConditions` +runs before the library is built and would fail on a missing `dist/openng/cashew` package root. +Instead [`.releaserc.json`](../.releaserc.json) drives the bump, the build, and the publish through +`@semantic-release/exec`, so the publish command is identical to the one in `release.yml` and picks +up OIDC the same way. It publishes to the `latest` dist-tag only; prereleases would need a +prerelease branch entry in `branches` and a channel-aware `publishCmd`. + +### To switch to semantic-release + +```shell +npm i -D semantic-release @semantic-release/changelog @semantic-release/git @semantic-release/exec +git rm .github/workflows/release.yml +git mv .github/workflows/release-semantic-release.yml .github/workflows/release.yml +npm uninstall standard-version # and drop the root "release" script +``` + +Then re-point the npm trusted publisher at the new workflow filename if it changed, and update the +`bump`-input references in this document. + +## Related + +- Issue [openng-org/cashew#2](https://github.com/openng-org/cashew/issues/2) — scope of the first + `@openng`-scoped release, and where this workflow was requested. +- [jsverse/transloco's `release.yml`](https://github.com/jsverse/transloco/blob/master/.github/workflows/release.yml) + — the workflow this one is ported from. transloco is an Nx monorepo and drives everything through + `nx release`; the Nx steps are replaced here by `standard-version`, `gh release create`, and + `npm publish dist/openng/cashew`. +- [`ci.yml`](../.github/workflows/ci.yml) — the test/build workflow that runs on every push and PR. + Note it installs with `npm i` while the release path uses `npm ci`. diff --git a/package.json b/package.json index 26a8589..85d1286 100644 --- a/package.json +++ b/package.json @@ -1,5 +1,7 @@ { "name": "cashew-playground", + "version": "0.0.0", + "private": true, "scripts": { "release": "cd projects/openng/cashew && standard-version --infile ../../../CHANGELOG.md", "contributors:add": "all-contributors add", @@ -13,7 +15,7 @@ "build:schematics": "tsc -p projects/openng/cashew/schematics/tsconfig.json", "ng": "ng", "commit": "git-cz", - "postbuild:lib": "cp README.md dist/openng/cashew && npm run build:schematics", + "postbuild:lib": "cp README.md LICENSE dist/openng/cashew && npm run build:schematics", "prepare": "husky install", "pre-commit": "lint-staged --allow-empty" }, diff --git a/projects/openng/cashew/package.json b/projects/openng/cashew/package.json index eab16c6..1c41fa0 100644 --- a/projects/openng/cashew/package.json +++ b/projects/openng/cashew/package.json @@ -15,15 +15,15 @@ "save": "dependencies" }, "bugs": { - "url": "https://github.com/openng-foundation/cashew/issues" + "url": "https://github.com/openng-org/cashew/issues" }, "peerDependencies": { "@angular/core": ">=17.0.0" }, - "homepage": "https://github.com/openng-foundation/cashew#readme", + "homepage": "https://github.com/openng-org/cashew#readme", "repository": { "type": "git", - "url": "https://github.com/openng-foundation/cashew" + "url": "https://github.com/openng-org/cashew" }, "keywords": [ "angular",