chore: import upstream snapshot with attribution
Publish SDK (PyPI) / publish (push) Has been cancelled
Publish SDK (npm) / publish (@aionui/officecli-sdk) (push) Has been cancelled
SDK smoke / smoke (windows-latest) (push) Has been cancelled
Publish SDK (npm) / publish (@officecli/officecli-sdk) (push) Has been cancelled
Publish SDK (npm) / publish (@officecli/sdk) (push) Has been cancelled
Publish SDK (npm) / publish (officecli-sdk) (push) Has been cancelled
SDK smoke / smoke (macos-latest) (push) Has been cancelled
SDK smoke / smoke (ubuntu-latest) (push) Has been cancelled
Skill parity / diff (push) Has been cancelled
Publish SDK (PyPI) / publish (push) Has been cancelled
Publish SDK (npm) / publish (@aionui/officecli-sdk) (push) Has been cancelled
SDK smoke / smoke (windows-latest) (push) Has been cancelled
Publish SDK (npm) / publish (@officecli/officecli-sdk) (push) Has been cancelled
Publish SDK (npm) / publish (@officecli/sdk) (push) Has been cancelled
Publish SDK (npm) / publish (officecli-sdk) (push) Has been cancelled
SDK smoke / smoke (macos-latest) (push) Has been cancelled
SDK smoke / smoke (ubuntu-latest) (push) Has been cancelled
Skill parity / diff (push) Has been cancelled
This commit is contained in:
@@ -0,0 +1,235 @@
|
||||
name: Build
|
||||
|
||||
on:
|
||||
workflow_dispatch:
|
||||
push:
|
||||
tags:
|
||||
- 'v*'
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
build:
|
||||
strategy:
|
||||
matrix:
|
||||
include:
|
||||
- rid: osx-arm64
|
||||
name: officecli-mac-arm64
|
||||
os: macos-latest
|
||||
- rid: osx-x64
|
||||
name: officecli-mac-x64
|
||||
os: macos-latest
|
||||
- rid: linux-x64
|
||||
name: officecli-linux-x64
|
||||
os: ubuntu-latest
|
||||
- rid: linux-arm64
|
||||
name: officecli-linux-arm64
|
||||
os: ubuntu-latest
|
||||
- rid: linux-musl-x64
|
||||
name: officecli-linux-alpine-x64
|
||||
os: ubuntu-latest
|
||||
- rid: linux-musl-arm64
|
||||
name: officecli-linux-alpine-arm64
|
||||
os: ubuntu-latest
|
||||
- rid: win-x64
|
||||
name: officecli-win-x64.exe
|
||||
os: windows-latest
|
||||
- rid: win-arm64
|
||||
name: officecli-win-arm64.exe
|
||||
os: windows-latest
|
||||
runs-on: ${{ matrix.os }}
|
||||
|
||||
defaults:
|
||||
run:
|
||||
shell: bash
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v5
|
||||
|
||||
- name: Setup .NET
|
||||
uses: actions/setup-dotnet@v5
|
||||
with:
|
||||
dotnet-version: '10.0.x'
|
||||
|
||||
- name: Publish
|
||||
run: dotnet publish src/officecli/officecli.csproj -c Release -r ${{ matrix.rid }} -o publish --nologo
|
||||
|
||||
- name: Rename output
|
||||
run: |
|
||||
if [ -f publish/officecli.exe ]; then
|
||||
mv publish/officecli.exe publish/${{ matrix.name }}
|
||||
else
|
||||
mv publish/officecli publish/${{ matrix.name }}
|
||||
fi
|
||||
|
||||
- name: Setup macOS code signing
|
||||
if: startsWith(matrix.rid, 'osx-')
|
||||
env:
|
||||
BUILD_CERTIFICATE_BASE64: ${{ secrets.BUILD_CERTIFICATE_BASE64 }}
|
||||
P12_PASSWORD: ${{ secrets.P12_PASSWORD }}
|
||||
KEYCHAIN_PASSWORD: ${{ secrets.KEYCHAIN_PASSWORD }}
|
||||
run: |
|
||||
CERT_PATH="$RUNNER_TEMP/build_certificate.p12"
|
||||
KEYCHAIN_PATH="$RUNNER_TEMP/build.keychain-db"
|
||||
|
||||
echo -n "$BUILD_CERTIFICATE_BASE64" | base64 --decode > "$CERT_PATH"
|
||||
|
||||
security create-keychain -p "$KEYCHAIN_PASSWORD" "$KEYCHAIN_PATH"
|
||||
security set-keychain-settings -lut 21600 "$KEYCHAIN_PATH"
|
||||
security unlock-keychain -p "$KEYCHAIN_PASSWORD" "$KEYCHAIN_PATH"
|
||||
security import "$CERT_PATH" -P "$P12_PASSWORD" -A -t cert -f pkcs12 -k "$KEYCHAIN_PATH"
|
||||
security set-key-partition-list -S apple-tool:,apple:,codesign: -k "$KEYCHAIN_PASSWORD" "$KEYCHAIN_PATH"
|
||||
security list-keychain -d user -s "$KEYCHAIN_PATH" login.keychain-db
|
||||
rm -f "$CERT_PATH"
|
||||
|
||||
- name: Codesign (macOS)
|
||||
if: startsWith(matrix.rid, 'osx-')
|
||||
run: |
|
||||
IDENTITY=$(security find-identity -v -p codesigning | grep "Developer ID Application" | head -n 1 | sed -E 's/.*"(.+)"/\1/')
|
||||
echo "Signing with: $IDENTITY"
|
||||
# --options runtime (Hardened Runtime, required by notarization) denies the
|
||||
# self-contained CoreCLR's MAP_JIT executable memory by default, so the runtime
|
||||
# fails to start with "Failed to create CoreCLR, HRESULT: 0x80070008" on every
|
||||
# command. build/officecli.entitlements re-permits exactly allow-jit (the plist
|
||||
# holds no XML comments — codesign's AMFI parser rejects them).
|
||||
codesign --force --options runtime --entitlements build/officecli.entitlements --timestamp --sign "$IDENTITY" publish/${{ matrix.name }}
|
||||
codesign --verify --strict --verbose=2 publish/${{ matrix.name }}
|
||||
# Fail the build if allow-jit did not actually embed (e.g. a malformed plist
|
||||
# makes codesign silently drop entitlements) — otherwise the bug ships again.
|
||||
codesign -d --entitlements - --xml publish/${{ matrix.name }} | grep -q allow-jit
|
||||
|
||||
- name: Notarize (macOS)
|
||||
if: startsWith(matrix.rid, 'osx-')
|
||||
env:
|
||||
APPLE_ID: ${{ secrets.APPLE_ID }}
|
||||
APP_SPECIFIC_PASSWORD: ${{ secrets.APP_SPECIFIC_PASSWORD }}
|
||||
TEAM_ID: ${{ secrets.TEAM_ID }}
|
||||
run: |
|
||||
# A bare Mach-O binary cannot be stapled; notarytool requires a
|
||||
# zip/pkg/dmg container. Submit a zip — the notarization ticket is
|
||||
# recorded on Apple's servers and Gatekeeper validates online.
|
||||
ditto -c -k --keepParent publish/${{ matrix.name }} "$RUNNER_TEMP/notarize.zip"
|
||||
xcrun notarytool submit "$RUNNER_TEMP/notarize.zip" \
|
||||
--apple-id "$APPLE_ID" \
|
||||
--team-id "$TEAM_ID" \
|
||||
--password "$APP_SPECIFIC_PASSWORD" \
|
||||
--wait
|
||||
rm -f "$RUNNER_TEMP/notarize.zip"
|
||||
|
||||
- name: Smoke test - create document
|
||||
if: >-
|
||||
(matrix.rid == 'osx-arm64' && runner.arch == 'ARM64') ||
|
||||
(matrix.rid == 'osx-x64' && runner.arch == 'X64') ||
|
||||
(matrix.rid == 'linux-x64' && runner.os == 'Linux') ||
|
||||
(matrix.rid == 'win-x64' && runner.os == 'Windows')
|
||||
env:
|
||||
# Disable Git Bash (MSYS) POSIX-to-Windows path conversion on
|
||||
# windows-latest, which otherwise mangles `/body` into
|
||||
# `C:/Program Files/Git/body` before it reaches the CLI.
|
||||
MSYS_NO_PATHCONV: '1'
|
||||
MSYS2_ARG_CONV_EXCL: '*'
|
||||
run: |
|
||||
chmod +x publish/${{ matrix.name }}
|
||||
publish/${{ matrix.name }} create test_smoke.docx
|
||||
publish/${{ matrix.name }} add test_smoke.docx /body --type paragraph --prop text="Hello from CI"
|
||||
publish/${{ matrix.name }} get test_smoke.docx '/body/p[1]'
|
||||
publish/${{ matrix.name }} close test_smoke.docx
|
||||
rm -f test_smoke.docx
|
||||
|
||||
- name: Smoke test - .NET 8-only runtime (linux-x64)
|
||||
if: matrix.rid == 'linux-x64' && runner.os == 'Linux'
|
||||
run: |
|
||||
chmod +x publish/${{ matrix.name }}
|
||||
mkdir -p smoke_net8
|
||||
docker run --rm \
|
||||
-v "$PWD/publish:/app:ro" \
|
||||
-v "$PWD/smoke_net8:/work" \
|
||||
-w /work \
|
||||
mcr.microsoft.com/dotnet/runtime:8.0 \
|
||||
bash -c "set -e; \
|
||||
/app/${{ matrix.name }} create issue115.docx; \
|
||||
/app/${{ matrix.name }} add issue115.docx /body --type paragraph --prop text='net8 smoke'; \
|
||||
/app/${{ matrix.name }} close issue115.docx; \
|
||||
/app/${{ matrix.name }} view issue115.docx text --json"
|
||||
|
||||
- name: Smoke test - install
|
||||
if: >-
|
||||
(matrix.rid == 'osx-arm64' && runner.arch == 'ARM64') ||
|
||||
(matrix.rid == 'osx-x64' && runner.arch == 'X64') ||
|
||||
(matrix.rid == 'linux-x64' && runner.os == 'Linux') ||
|
||||
(matrix.rid == 'win-x64' && runner.os == 'Windows')
|
||||
env:
|
||||
MSYS_NO_PATHCONV: '1'
|
||||
MSYS2_ARG_CONV_EXCL: '*'
|
||||
run: |
|
||||
publish/${{ matrix.name }} install
|
||||
if [ "$RUNNER_OS" == "Windows" ]; then
|
||||
test -f "$LOCALAPPDATA/OfficeCLI/officecli.exe" || { echo "FAIL: officecli.exe not found in %LOCALAPPDATA%\\OfficeCLI"; exit 1; }
|
||||
"$LOCALAPPDATA/OfficeCLI/officecli.exe" --version
|
||||
else
|
||||
test -f "$HOME/.local/bin/officecli" || { echo "FAIL: officecli not found in ~/.local/bin"; exit 1; }
|
||||
"$HOME/.local/bin/officecli" --version
|
||||
fi
|
||||
|
||||
- name: Smoke test - install.sh / install.ps1
|
||||
# Exercises the shell installers themselves (separate from the CLI's
|
||||
# own `install` subcommand tested above). Downloads from
|
||||
# d.officecli.ai with github fallback — validates the production
|
||||
# mirror is reachable AND the in-repo script is syntactically and
|
||||
# logically correct on each platform.
|
||||
if: >-
|
||||
(matrix.rid == 'osx-arm64' && runner.arch == 'ARM64') ||
|
||||
(matrix.rid == 'osx-x64' && runner.arch == 'X64') ||
|
||||
(matrix.rid == 'linux-x64' && runner.os == 'Linux') ||
|
||||
(matrix.rid == 'win-x64' && runner.os == 'Windows')
|
||||
shell: bash
|
||||
env:
|
||||
MSYS_NO_PATHCONV: '1'
|
||||
MSYS2_ARG_CONV_EXCL: '*'
|
||||
run: |
|
||||
if [ "$RUNNER_OS" == "Windows" ]; then
|
||||
pwsh -NoProfile -ExecutionPolicy Bypass -File ./install.ps1
|
||||
test -f "$LOCALAPPDATA/OfficeCLI/officecli.exe" || { echo "FAIL: officecli.exe not installed"; exit 1; }
|
||||
"$LOCALAPPDATA/OfficeCLI/officecli.exe" --version
|
||||
else
|
||||
bash install.sh
|
||||
test -f "$HOME/.local/bin/officecli" || { echo "FAIL: officecli not installed at ~/.local/bin"; exit 1; }
|
||||
"$HOME/.local/bin/officecli" --version
|
||||
fi
|
||||
|
||||
- name: Upload artifact
|
||||
uses: actions/upload-artifact@v6
|
||||
with:
|
||||
name: ${{ matrix.name }}
|
||||
path: publish/${{ matrix.name }}
|
||||
|
||||
release:
|
||||
needs: build
|
||||
runs-on: ubuntu-latest
|
||||
if: startsWith(github.ref, 'refs/tags/v')
|
||||
permissions:
|
||||
contents: write
|
||||
steps:
|
||||
- name: Download all artifacts
|
||||
uses: actions/download-artifact@v8
|
||||
with:
|
||||
path: artifacts
|
||||
|
||||
- name: Flatten artifacts and generate checksums
|
||||
run: |
|
||||
mkdir -p flat
|
||||
find artifacts -type f -exec mv {} flat/ \;
|
||||
rm -rf artifacts
|
||||
mv flat artifacts
|
||||
cd artifacts
|
||||
sha256sum officecli-* > SHA256SUMS
|
||||
echo "=== SHA256SUMS ==="
|
||||
cat SHA256SUMS
|
||||
|
||||
- name: Create Draft Release
|
||||
uses: softprops/action-gh-release@v3
|
||||
with:
|
||||
files: artifacts/**/*
|
||||
generate_release_notes: true
|
||||
draft: true
|
||||
@@ -0,0 +1,95 @@
|
||||
name: Publish npm
|
||||
|
||||
# Fires when a GitHub Release is PUBLISHED (not on the draft created by
|
||||
# build.yml). By then the release assets — the platform binaries and
|
||||
# SHA256SUMS the npm postinstall downloads — are publicly live, so a user who
|
||||
# `npm install`s immediately can fetch them.
|
||||
#
|
||||
# Auth: npm Trusted Publishing (OIDC). No NPM_TOKEN / secret required — the
|
||||
# `id-token: write` permission below lets the runner mint a short-lived token.
|
||||
# Configure the trusted publisher for BOTH packages on npmjs.com:
|
||||
# org/user: iOfficeAI repo: OfficeCLI workflow: publish-npm.yml action: npm publish
|
||||
|
||||
on:
|
||||
release:
|
||||
types: [published]
|
||||
workflow_dispatch:
|
||||
inputs:
|
||||
version:
|
||||
description: 'Version to publish (X.Y.Z, or X.Y.Z-pre for a test build). Required for manual runs.'
|
||||
required: false
|
||||
dist_tag:
|
||||
description: 'npm dist-tag (default: latest). Use e.g. "test" for a prerelease that must not move latest.'
|
||||
required: false
|
||||
default: 'latest'
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
publish:
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
id-token: write # OIDC token for npm trusted publishing
|
||||
contents: read
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
package:
|
||||
- '@officecli/officecli'
|
||||
- '@aionui/officecli'
|
||||
steps:
|
||||
- uses: actions/checkout@v5
|
||||
|
||||
- uses: actions/setup-node@v6
|
||||
with:
|
||||
node-version: '24'
|
||||
registry-url: 'https://registry.npmjs.org'
|
||||
|
||||
- name: Upgrade npm (trusted publishing + provenance need >= 11.5.1)
|
||||
# Pinned to 11.x: npm 12.0.0 ships a broken provenance path
|
||||
# ("Cannot find module 'sigstore'" in libnpmpublish). Unpin once fixed.
|
||||
run: npm install -g npm@11
|
||||
|
||||
- name: Resolve version
|
||||
id: ver
|
||||
run: |
|
||||
if [ "${{ github.event_name }}" = "release" ]; then
|
||||
V="${{ github.event.release.tag_name }}"
|
||||
else
|
||||
V="${{ github.event.inputs.version }}"
|
||||
fi
|
||||
V="${V#v}"
|
||||
if ! printf '%s' "$V" | grep -Eq '^[0-9]+\.[0-9]+\.[0-9]+([.-].*)?$'; then
|
||||
echo "Invalid or missing version: '$V'"
|
||||
exit 1
|
||||
fi
|
||||
echo "version=$V" >> "$GITHUB_OUTPUT"
|
||||
echo "Publishing ${{ matrix.package }}@$V"
|
||||
|
||||
- name: Set package name, version, and match the README to this package
|
||||
id: pkg
|
||||
working-directory: npm
|
||||
run: |
|
||||
npm pkg set name='${{ matrix.package }}'
|
||||
npm pkg set version='${{ steps.ver.outputs.version }}'
|
||||
# Only the package name differs per scope; links stay officecli.ai.
|
||||
# Rewrite the install/npx commands to this package's name. No-op for
|
||||
# @officecli/officecli.
|
||||
sed -i "s|@officecli/officecli|${{ matrix.package }}|g" README.md
|
||||
# A brand-new package can't be created by trusted publishing (OIDC) —
|
||||
# skip (green) until its one-time manual first publish creates it.
|
||||
if npm view '${{ matrix.package }}' version >/dev/null 2>&1; then
|
||||
echo "exists=true" >> "$GITHUB_OUTPUT"
|
||||
else
|
||||
echo "exists=false" >> "$GITHUB_OUTPUT"
|
||||
echo "::notice::${{ matrix.package }} does not exist on npm yet — first publish must be manual; skipping."
|
||||
fi
|
||||
|
||||
- name: Publish to npm
|
||||
if: steps.pkg.outputs.exists == 'true'
|
||||
working-directory: npm
|
||||
run: |
|
||||
TAG='${{ github.event.inputs.dist_tag }}'
|
||||
[ -z "$TAG" ] && TAG='latest'
|
||||
npm publish --provenance --access public --tag "$TAG"
|
||||
@@ -0,0 +1,63 @@
|
||||
name: Publish SDK (PyPI)
|
||||
|
||||
# Publishes officecli-sdk (sdk/python) to PyPI on its OWN cadence — same model as
|
||||
# publish-sdk.yml for npm. Triggers on a push touching sdk/python/** (or manual
|
||||
# dispatch); a guard skips when that version is already on PyPI, so only a
|
||||
# version bump in pyproject.toml actually publishes. A CLI release does NOT
|
||||
# republish the SDK.
|
||||
#
|
||||
# Auth: PyPI Trusted Publishing (OIDC), no token / no API key. Configure the
|
||||
# trusted publisher for the officecli-sdk project on pypi.org:
|
||||
# owner: iOfficeAI repo: OfficeCLI workflow: publish-pypi.yml
|
||||
# (officecli-sdk already exists on PyPI, so the publisher can be added directly.)
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
paths:
|
||||
- 'sdk/python/**'
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
publish:
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
id-token: write # OIDC token for PyPI trusted publishing
|
||||
contents: read
|
||||
steps:
|
||||
- uses: actions/checkout@v5
|
||||
|
||||
- uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: '3.12'
|
||||
|
||||
- name: Resolve version and check if already on PyPI
|
||||
id: ver
|
||||
working-directory: sdk/python
|
||||
run: |
|
||||
NAME=$(python -c "import tomllib;print(tomllib.load(open('pyproject.toml','rb'))['project']['name'])")
|
||||
VERSION=$(python -c "import tomllib;print(tomllib.load(open('pyproject.toml','rb'))['project']['version'])")
|
||||
echo "Publishing candidate: $NAME==$VERSION"
|
||||
CODE=$(curl -s -o /dev/null -w '%{http_code}' "https://pypi.org/pypi/$NAME/$VERSION/json")
|
||||
if [ "$CODE" = "200" ]; then
|
||||
echo "already=true" >> "$GITHUB_OUTPUT"
|
||||
echo "$NAME==$VERSION is already on PyPI — nothing to publish (bump the version to release)."
|
||||
else
|
||||
echo "already=false" >> "$GITHUB_OUTPUT"
|
||||
fi
|
||||
|
||||
- name: Build sdist + wheel
|
||||
if: steps.ver.outputs.already == 'false'
|
||||
working-directory: sdk/python
|
||||
run: |
|
||||
python -m pip install --upgrade build
|
||||
python -m build
|
||||
|
||||
- name: Publish to PyPI
|
||||
if: steps.ver.outputs.already == 'false'
|
||||
uses: pypa/gh-action-pypi-publish@release/v1
|
||||
with:
|
||||
packages-dir: sdk/python/dist
|
||||
@@ -0,0 +1,82 @@
|
||||
name: Publish SDK (npm)
|
||||
|
||||
# Publishes @officecli/sdk (sdk/node) on its OWN cadence — decoupled from the
|
||||
# CLI release. The SDK depends on @officecli/officecli via a semver range
|
||||
# (^1.0.0), so a CLI version bump flows to users automatically (fresh installs
|
||||
# resolve the newest CLI; existing installs auto-update the bundled binary)
|
||||
# WITHOUT republishing the SDK. The SDK is republished only when its own source
|
||||
# changes — i.e. when sdk/node/package.json's version is bumped.
|
||||
#
|
||||
# Trigger: a push touching sdk/node/** (or manual dispatch). A guard skips the
|
||||
# publish when that version is already on npm, so only a version bump actually
|
||||
# publishes — pushes that don't change the version are no-ops.
|
||||
#
|
||||
# The same SDK is published under four names (one canonical + mirrors/aliases).
|
||||
# The version is shared (sdk/node/package.json); the name is swapped per leg.
|
||||
#
|
||||
# Auth: npm Trusted Publishing (OIDC), no token. Configure a trusted publisher
|
||||
# for EACH of the four packages on npmjs.com:
|
||||
# org/user: iOfficeAI repo: OfficeCLI workflow: publish-sdk.yml action: npm publish
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
paths:
|
||||
- 'sdk/node/**'
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
publish:
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
id-token: write
|
||||
contents: read
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
package:
|
||||
- '@officecli/sdk'
|
||||
- '@officecli/officecli-sdk'
|
||||
- '@aionui/officecli-sdk'
|
||||
- 'officecli-sdk'
|
||||
steps:
|
||||
- uses: actions/checkout@v5
|
||||
|
||||
- uses: actions/setup-node@v6
|
||||
with:
|
||||
node-version: '24'
|
||||
registry-url: 'https://registry.npmjs.org'
|
||||
|
||||
- name: Upgrade npm (trusted publishing + provenance need >= 11.5.1)
|
||||
run: npm install -g npm@latest
|
||||
|
||||
- name: Set package name and check if already published
|
||||
id: ver
|
||||
working-directory: sdk/node
|
||||
run: |
|
||||
npm pkg set name='${{ matrix.package }}'
|
||||
# Only the package name differs per scope; links stay officecli.ai.
|
||||
# Rewrite install/require examples to this package's name.
|
||||
sed -i "s|@officecli/sdk|${{ matrix.package }}|g" README.md
|
||||
VERSION=$(node -p "require('./package.json').version")
|
||||
echo "Publishing candidate: ${{ matrix.package }}@$VERSION"
|
||||
if ! npm view "${{ matrix.package }}" version >/dev/null 2>&1; then
|
||||
# A brand-new package can't be created by trusted publishing (OIDC) —
|
||||
# it has no package to attach the publisher config to, so the PUT 404s.
|
||||
# Skip (green) until the one-time MANUAL first publish creates it.
|
||||
echo "already=true" >> "$GITHUB_OUTPUT"
|
||||
echo "::notice::${{ matrix.package }} does not exist on npm yet — first publish must be manual; skipping."
|
||||
elif npm view "${{ matrix.package }}@$VERSION" version >/dev/null 2>&1; then
|
||||
echo "already=true" >> "$GITHUB_OUTPUT"
|
||||
echo "${{ matrix.package }}@$VERSION is already on npm — nothing to publish (bump the version to release)."
|
||||
else
|
||||
echo "already=false" >> "$GITHUB_OUTPUT"
|
||||
fi
|
||||
|
||||
- name: Publish to npm
|
||||
if: steps.ver.outputs.already == 'false'
|
||||
working-directory: sdk/node
|
||||
run: npm publish --provenance --access public
|
||||
@@ -0,0 +1,50 @@
|
||||
name: SDK smoke
|
||||
|
||||
# End-to-end smoke for both SDKs on all three OSes. The runners have no officecli
|
||||
# on PATH, so create() exercises the FULL auto-install path — install.sh on
|
||||
# unix, install.ps1 (irm | iex via PowerShell) on Windows — then a real pipe
|
||||
# round-trip. This is the only place the Windows installer path is exercised, and
|
||||
# it runs against the SDK source directly (no bundled dependency installed), so
|
||||
# the install.sh/install.ps1 fallback is what gets tested.
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
paths:
|
||||
- 'sdk/**'
|
||||
- '.github/workflows/sdk-smoke.yml'
|
||||
pull_request:
|
||||
paths:
|
||||
- 'sdk/**'
|
||||
- '.github/workflows/sdk-smoke.yml'
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
smoke:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
os: [ubuntu-latest, macos-latest, windows-latest]
|
||||
runs-on: ${{ matrix.os }}
|
||||
defaults:
|
||||
run:
|
||||
shell: bash
|
||||
steps:
|
||||
- uses: actions/checkout@v5
|
||||
|
||||
- uses: actions/setup-node@v6
|
||||
with:
|
||||
node-version: '20'
|
||||
|
||||
- uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: '3.12'
|
||||
|
||||
- name: Node SDK auto-install + round-trip
|
||||
run: node sdk/node/smoke.js
|
||||
|
||||
- name: Python SDK auto-install + round-trip
|
||||
run: python sdk/python/smoke.py
|
||||
@@ -0,0 +1,41 @@
|
||||
name: Skill parity
|
||||
|
||||
# Root SKILL.md is the file the public URL serves
|
||||
# (https://d.officecli.ai/SKILL.md, raw GitHub URL) and is what
|
||||
# `curl ... | bash` consumers fetch. skills/officecli/SKILL.md is a
|
||||
# symlink to it — the spec-conforming location that `gh skill install`
|
||||
# and `npx skills add` discover, and what the binary embeds.
|
||||
#
|
||||
# On macOS / Linux the symlink resolves transparently and this diff
|
||||
# always passes. The check exists for the Windows case: git on Windows
|
||||
# without core.symlinks=true checks out symlinks as plain text files
|
||||
# containing the link target path (e.g. literal "../../SKILL.md"), so
|
||||
# diff catches that corruption before it ships in a release build.
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
pull_request:
|
||||
paths:
|
||||
- 'SKILL.md'
|
||||
- 'skills/officecli/SKILL.md'
|
||||
- '.github/workflows/skill-parity.yml'
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
diff:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v5
|
||||
- name: Diff root SKILL.md vs skills/officecli/SKILL.md
|
||||
run: |
|
||||
if ! diff -q SKILL.md skills/officecli/SKILL.md; then
|
||||
echo "::error::SKILL.md and skills/officecli/SKILL.md are out of sync."
|
||||
echo "The two files must be byte-identical. The binary embeds skills/officecli/SKILL.md;"
|
||||
echo "the public URL (d.officecli.ai/SKILL.md, raw GitHub) serves the root copy."
|
||||
echo "Fix: cp SKILL.md skills/officecli/SKILL.md (or the reverse) and commit."
|
||||
exit 1
|
||||
fi
|
||||
echo "OK: SKILL.md == skills/officecli/SKILL.md"
|
||||
Reference in New Issue
Block a user