@voxgig/sdkgen-infrapack 0.0.6 → 0.0.8
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.
|
@@ -65,20 +65,32 @@ main: kit: target: 'seneca-provider': {
|
|
|
65
65
|
# `repo` defaults to the SDK's own repository, so normally only the ref is
|
|
66
66
|
# stated.
|
|
67
67
|
#
|
|
68
|
-
#
|
|
69
|
-
#
|
|
70
|
-
# TypeScript SDK into `ts
|
|
71
|
-
#
|
|
72
|
-
#
|
|
68
|
+
# WHICH KIND TO USE DEPENDS ON WHERE THE PACKAGE SITS. npm resolves a git
|
|
69
|
+
# dependency against the repository ROOT, and sdkgen generates the
|
|
70
|
+
# TypeScript SDK into `ts/` — so `git` suits an SDK that IS its repository
|
|
71
|
+
# root, and `release` suits this toolchain's own layout:
|
|
72
|
+
#
|
|
73
|
+
# kind: 'git' github:owner/repo#<ref>
|
|
74
|
+
# kind: 'release' https://github.com/owner/repo/releases/download/
|
|
75
|
+
# <ref>/<asset>.tgz
|
|
76
|
+
#
|
|
77
|
+
# A release asset is `npm pack` output attached to the tag; npm installs an
|
|
78
|
+
# https tarball natively and never looks at the repository layout. `asset`
|
|
79
|
+
# names the file when it is not the usual `<scope>-<name>-<version>.tgz`.
|
|
80
|
+
#
|
|
81
|
+
# There is no subdirectory option, deliberately. npm's spec parser accepts
|
|
82
|
+
# `#<ref>::path:ts` and reports a gitSubdir, so it reads as supported — but
|
|
83
|
+
# the INSTALLER ignores it and fails with ENOENT, on linux, macOS and
|
|
84
|
+
# Windows alike. A knob that produces an uninstallable dependency is worse
|
|
85
|
+
# than no knob.
|
|
73
86
|
#
|
|
74
87
|
# `spec` states the whole dependency value outright and wins over
|
|
75
|
-
# everything
|
|
76
|
-
# URL, say.
|
|
88
|
+
# everything.
|
|
77
89
|
sdk: dep: {
|
|
78
|
-
kind: *'npm' | 'git'
|
|
90
|
+
kind: *'npm' | 'git' | 'release'
|
|
79
91
|
ref: *'' | string
|
|
80
92
|
repo: *'' | string
|
|
81
|
-
|
|
93
|
+
asset: *'' | string
|
|
82
94
|
spec: *'' | string
|
|
83
95
|
}
|
|
84
96
|
|
|
@@ -1741,14 +1741,30 @@ ${!provider.liveApp ? '' : `
|
|
|
1741
1741
|
# lets npm exchange a GitHub OIDC token for a short-lived publish credential,
|
|
1742
1742
|
# and provenance is attached automatically.
|
|
1743
1743
|
#
|
|
1744
|
+
# TWO JOBS, BECAUSE THEY NEED DIFFERENT PRIVILEGES.
|
|
1745
|
+
#
|
|
1746
|
+
# verify contents: read, and nothing else. Runs npm install, the build
|
|
1747
|
+
# and the tests — i.e. dependency lifecycle scripts and project
|
|
1748
|
+
# code. It holds no publish credential.
|
|
1749
|
+
# publish id-token: write, contents: read. Installs NO project
|
|
1750
|
+
# dependencies and runs NO project code: this package ships
|
|
1751
|
+
# \`dist\`, which is committed, so nothing needs building to pack.
|
|
1752
|
+
#
|
|
1753
|
+
# THE SPLIT IS THE POINT. A compromised dependency lifecycle script can ask
|
|
1754
|
+
# the runner for any OIDC token the JOB is permitted to mint, so a job that
|
|
1755
|
+
# both installs dependencies and holds \`id-token: write\` can be made to
|
|
1756
|
+
# publish as this package before its own gates finish. Keeping the install in
|
|
1757
|
+
# a job with no id-token, and the credential in a job that installs nothing,
|
|
1758
|
+
# is what makes the isolation real rather than nominal.
|
|
1759
|
+
#
|
|
1744
1760
|
# The trusted publisher must be registered on npmjs.com for this package
|
|
1745
1761
|
# against THIS filename (publish.yml); renaming this file breaks publishing
|
|
1746
1762
|
# until the npm-side config is updated to match.
|
|
1747
1763
|
#
|
|
1748
|
-
# npm cannot
|
|
1749
|
-
#
|
|
1750
|
-
#
|
|
1751
|
-
# release after that is a tag push.
|
|
1764
|
+
# npm cannot configure a trusted publisher for a package that does not exist
|
|
1765
|
+
# yet — the settings page appears once a version is on the registry. So the
|
|
1766
|
+
# FIRST version of a new package is published by hand, once, with an
|
|
1767
|
+
# authenticated npm; every release after that is a tag push.
|
|
1752
1768
|
#
|
|
1753
1769
|
# Release flow: bump the version in the SDK model
|
|
1754
1770
|
# (\`main: kit: target: 'seneca-provider': publish: version\`), regenerate,
|
|
@@ -1762,25 +1778,24 @@ on:
|
|
|
1762
1778
|
workflow_dispatch:
|
|
1763
1779
|
|
|
1764
1780
|
jobs:
|
|
1765
|
-
|
|
1766
|
-
name:
|
|
1781
|
+
verify:
|
|
1782
|
+
name: verify
|
|
1767
1783
|
runs-on: ubuntu-latest
|
|
1768
1784
|
timeout-minutes: 15
|
|
1785
|
+
|
|
1786
|
+
# Deliberately the default-minimum. This job runs third-party code.
|
|
1769
1787
|
permissions:
|
|
1770
|
-
id-token: write
|
|
1771
1788
|
contents: read
|
|
1772
1789
|
|
|
1790
|
+
outputs:
|
|
1791
|
+
version: \${{ steps.version.outputs.version }}
|
|
1792
|
+
|
|
1773
1793
|
steps:
|
|
1774
1794
|
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7
|
|
1775
1795
|
|
|
1776
1796
|
- uses: actions/setup-node@820762786026740c76f36085b0efc47a31fe5020 # v7
|
|
1777
1797
|
with:
|
|
1778
1798
|
node-version: 24.x
|
|
1779
|
-
registry-url: 'https://registry.npmjs.org'
|
|
1780
|
-
|
|
1781
|
-
# Trusted publishing requires npm >= 11.5.1.
|
|
1782
|
-
- name: Use a trusted-publishing capable npm
|
|
1783
|
-
run: npm install -g npm@latest
|
|
1784
1799
|
|
|
1785
1800
|
# install, not ci: this package does not commit a lockfile.
|
|
1786
1801
|
- run: npm install
|
|
@@ -1789,11 +1804,10 @@ jobs:
|
|
|
1789
1804
|
# needs it installed explicitly.
|
|
1790
1805
|
#
|
|
1791
1806
|
# --no-save IS LOAD-BEARING. Without it npm rewrites the peer ranges in
|
|
1792
|
-
# package.json to carets on whatever it resolved, and
|
|
1793
|
-
#
|
|
1794
|
-
#
|
|
1795
|
-
#
|
|
1796
|
-
# narrowed. Install into node_modules, leave the manifest alone.
|
|
1807
|
+
# package.json to carets on whatever it resolved, and a later publish
|
|
1808
|
+
# ships that rewritten manifest — so an authored \`>=26\` reaches
|
|
1809
|
+
# consumers as \`^28.1.0\` and the package refuses to install for anyone
|
|
1810
|
+
# on a newer major. The repo looks fine; only the artifact is narrowed.
|
|
1797
1811
|
- run: npm i --no-save seneca seneca-entity seneca-promisify @seneca/provider @seneca/env
|
|
1798
1812
|
|
|
1799
1813
|
- run: npm run build
|
|
@@ -1802,15 +1816,75 @@ jobs:
|
|
|
1802
1816
|
# The tag must match what the manifest declares, or a tag push silently
|
|
1803
1817
|
# republishes whatever version happens to be in package.json.
|
|
1804
1818
|
- name: Check the tag matches the manifest version
|
|
1819
|
+
id: version
|
|
1820
|
+
run: |
|
|
1821
|
+
set -euo pipefail
|
|
1822
|
+
PKG=\$(node -p "require('./package.json').version")
|
|
1823
|
+
if [ "\${GITHUB_REF_TYPE:-}" = "tag" ]; then
|
|
1824
|
+
TAG="\${GITHUB_REF_NAME#v}"
|
|
1825
|
+
if [ "\$TAG" != "\$PKG" ]; then
|
|
1826
|
+
echo "::error::tag v\$TAG does not match package.json \$PKG"
|
|
1827
|
+
exit 1
|
|
1828
|
+
fi
|
|
1829
|
+
fi
|
|
1830
|
+
echo "version=\$PKG" >> "\$GITHUB_OUTPUT"
|
|
1831
|
+
|
|
1832
|
+
# WHAT THE PUBLISH JOB WILL PACK, checked HERE where the code already
|
|
1833
|
+
# ran. That job builds nothing, so a missing or stale \`dist\` would
|
|
1834
|
+
# otherwise be discovered by consumers rather than by this workflow.
|
|
1835
|
+
- name: The committed dist matches the source
|
|
1805
1836
|
run: |
|
|
1806
|
-
|
|
1807
|
-
|
|
1808
|
-
|
|
1809
|
-
|
|
1837
|
+
set -euo pipefail
|
|
1838
|
+
if ! git diff --quiet -- dist; then
|
|
1839
|
+
echo "::error::dist/ is not up to date with src/ -- rebuild and commit it"
|
|
1840
|
+
git diff --stat -- dist
|
|
1810
1841
|
exit 1
|
|
1811
1842
|
fi
|
|
1812
1843
|
|
|
1844
|
+
publish:
|
|
1845
|
+
name: npm publish
|
|
1846
|
+
needs: verify
|
|
1847
|
+
runs-on: ubuntu-latest
|
|
1848
|
+
timeout-minutes: 15
|
|
1849
|
+
|
|
1850
|
+
# The ONLY job holding the publish credential — and it installs no
|
|
1851
|
+
# project dependencies and runs no project code. See the header.
|
|
1852
|
+
permissions:
|
|
1853
|
+
id-token: write
|
|
1854
|
+
contents: read
|
|
1855
|
+
|
|
1856
|
+
steps:
|
|
1857
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7
|
|
1858
|
+
|
|
1859
|
+
- uses: actions/setup-node@820762786026740c76f36085b0efc47a31fe5020 # v7
|
|
1860
|
+
with:
|
|
1861
|
+
node-version: 24.x
|
|
1862
|
+
registry-url: 'https://registry.npmjs.org'
|
|
1863
|
+
|
|
1864
|
+
# Trusted publishing requires npm >= 11.5.1. This is npm itself, not a
|
|
1865
|
+
# project dependency: no package.json here is consulted.
|
|
1866
|
+
- name: Use a trusted-publishing capable npm
|
|
1867
|
+
run: npm install -g npm@latest
|
|
1868
|
+
|
|
1869
|
+
# THE REGISTRY IS THE SOURCE OF TRUTH FOR "IS THIS RELEASED", not the
|
|
1870
|
+
# tag. A re-run of a workflow that already published would otherwise
|
|
1871
|
+
# fail on a version conflict and report a red release that in fact
|
|
1872
|
+
# succeeded.
|
|
1873
|
+
- name: Is this version already on npm?
|
|
1874
|
+
id: registry
|
|
1875
|
+
env:
|
|
1876
|
+
VERSION: \${{ needs.verify.outputs.version }}
|
|
1877
|
+
run: |
|
|
1878
|
+
set -euo pipefail
|
|
1879
|
+
if npm view "${provider.pkgName}@\$VERSION" version >/dev/null 2>&1; then
|
|
1880
|
+
echo "published=true" >> "\$GITHUB_OUTPUT"
|
|
1881
|
+
echo "\$VERSION is already on npm — skipping publish"
|
|
1882
|
+
else
|
|
1883
|
+
echo "published=false" >> "\$GITHUB_OUTPUT"
|
|
1884
|
+
fi
|
|
1885
|
+
|
|
1813
1886
|
- name: Publish to npm
|
|
1887
|
+
if: steps.registry.outputs.published == 'false'
|
|
1814
1888
|
run: npm publish --access public
|
|
1815
1889
|
`)
|
|
1816
1890
|
})
|
|
@@ -708,14 +708,21 @@ const Main = cmp(function Main(props: any) {
|
|
|
708
708
|
// into every generated provider's CI.
|
|
709
709
|
const liveApp = true === live.app || (loopback(specBase) && '' === (live.base || ''))
|
|
710
710
|
|
|
711
|
+
const sdkDep = sdkDependency(model, target, {
|
|
712
|
+
sdkPkg, sdkVersion, sdkRepoUrl: repoInfo(model).repoUrl,
|
|
713
|
+
})
|
|
714
|
+
|
|
711
715
|
const provider = {
|
|
712
716
|
Name, lower, ENV, sdkClass, pluginName, fileBase,
|
|
713
717
|
sdkPkg, sdkVersion, entities,
|
|
714
|
-
//
|
|
715
|
-
//
|
|
716
|
-
//
|
|
717
|
-
|
|
718
|
-
|
|
718
|
+
// The SDK dependency, resolved ONCE. PackageJson emits it and the CI
|
|
719
|
+
// note describes it, and computing it twice is how the second caller
|
|
720
|
+
// came to pass a half-built provider object into it.
|
|
721
|
+
sdkDep,
|
|
722
|
+
// Whether that dependency comes from outside a registry. The generated
|
|
723
|
+
// CI note says so, because "npm install is all you need" stops being
|
|
724
|
+
// true the moment git or a tarball URL is in the path.
|
|
725
|
+
sdkGit: !sdkDep.startsWith('^'),
|
|
719
726
|
repoUrl: repo.url,
|
|
720
727
|
// The SDK's own repo, for pointing at the companion test server which is
|
|
721
728
|
// only distributed in source.
|
|
@@ -790,13 +797,21 @@ const Main = cmp(function Main(props: any) {
|
|
|
790
797
|
// `kind: 'git'` points at a GIT TAG instead, which needs no registry.
|
|
791
798
|
//
|
|
792
799
|
// NPM RESOLVES A GIT DEPENDENCY AGAINST THE REPOSITORY ROOT, and sdkgen
|
|
793
|
-
// generates the TypeScript SDK into `ts
|
|
794
|
-
//
|
|
795
|
-
//
|
|
796
|
-
//
|
|
797
|
-
//
|
|
798
|
-
//
|
|
799
|
-
//
|
|
800
|
+
// generates the TypeScript SDK into `ts/`. So `kind: 'git'` suits an SDK
|
|
801
|
+
// whose package.json IS the repository root, and NOT the layout this
|
|
802
|
+
// toolchain produces.
|
|
803
|
+
//
|
|
804
|
+
// THE `::path:` SUBDIRECTORY SYNTAX DOES NOT WORK, and it looks like it
|
|
805
|
+
// does. npm-package-arg parses `#<ref>::path:ts` and reports
|
|
806
|
+
// `gitSubdir: /ts`, so a spec built that way reads as correct — but the
|
|
807
|
+
// INSTALLER ignores it: npm clones the repository and opens package.json at
|
|
808
|
+
// the clone root, failing with ENOENT on linux, macOS and Windows alike.
|
|
809
|
+
// That was measured, on all three, after the parser had said otherwise.
|
|
810
|
+
//
|
|
811
|
+
// `kind: 'release'` is the form that works for a package in a subdirectory:
|
|
812
|
+
// a GitHub release asset, which is `npm pack` output attached to the tag.
|
|
813
|
+
// npm installs an https tarball natively and never looks at the repository
|
|
814
|
+
// layout at all.
|
|
800
815
|
//
|
|
801
816
|
// `spec` still wins over all of it, for anything the shorthand cannot say.
|
|
802
817
|
function sdkDependency(model: any, target: any, provider: any): string {
|
|
@@ -807,7 +822,8 @@ function sdkDependency(model: any, target: any, provider: any): string {
|
|
|
807
822
|
return spec
|
|
808
823
|
}
|
|
809
824
|
|
|
810
|
-
|
|
825
|
+
const kind = String(dep.kind || 'npm')
|
|
826
|
+
if ('git' !== kind && 'release' !== kind) {
|
|
811
827
|
return `^${provider.sdkVersion}`
|
|
812
828
|
}
|
|
813
829
|
|
|
@@ -837,11 +853,17 @@ function sdkDependency(model: any, target: any, provider: any): string {
|
|
|
837
853
|
'on, e.g. `sdk.dep.ref: "v' + provider.sdkVersion + '"`.')
|
|
838
854
|
}
|
|
839
855
|
|
|
840
|
-
|
|
841
|
-
|
|
856
|
+
if ('release' === kind) {
|
|
857
|
+
// The asset `npm pack` produces: scope and name flattened, then the
|
|
858
|
+
// version. `asset` overrides it for a project that names its own.
|
|
859
|
+
const asset = String(dep.asset || '').trim() || (
|
|
860
|
+
provider.sdkPkg.replace(/^@/, '').replace(/\//g, '-') +
|
|
861
|
+
'-' + provider.sdkVersion + '.tgz')
|
|
862
|
+
|
|
863
|
+
return `https://github.com/${repo}/releases/download/${ref}/${asset}`
|
|
864
|
+
}
|
|
842
865
|
|
|
843
|
-
return `github:${repo}#${ref}`
|
|
844
|
-
('' === sub || '.' === sub ? '' : `::path:${sub}`)
|
|
866
|
+
return `github:${repo}#${ref}`
|
|
845
867
|
}
|
|
846
868
|
|
|
847
869
|
|
|
@@ -948,7 +970,7 @@ const PackageJson = cmp(function PackageJson(props: any) {
|
|
|
948
970
|
// The SDK this plugin wraps. Published-and-pinned by default; a git
|
|
949
971
|
// tag when the project says so, because an unpublished SDK otherwise
|
|
950
972
|
// leaves this package unable to install at all. See sdkDependency.
|
|
951
|
-
[provider.sdkPkg]:
|
|
973
|
+
[provider.sdkPkg]: provider.sdkDep,
|
|
952
974
|
...dep('prod'),
|
|
953
975
|
},
|
|
954
976
|
peerDependencies: dep('peer'),
|
package/package.json
CHANGED