From bac1f6669fb670ea3c1c231616df5daae8052a1c Mon Sep 17 00:00:00 2001 From: Sawyer Cutler Date: Fri, 25 Sep 2026 20:02:32 -0700 Subject: [PATCH 1/4] chore: add the CLA --- .github/workflows/cla.yml | 53 ++++++++++++++++++++++++++++++++ CLA.md | 64 +++++++++++++++++++++++++++++++++++++++ 2 files changed, 117 insertions(+) create mode 100644 .github/workflows/cla.yml create mode 100644 CLA.md diff --git a/.github/workflows/cla.yml b/.github/workflows/cla.yml new file mode 100644 index 0000000..a03ad39 --- /dev/null +++ b/.github/workflows/cla.yml @@ -0,0 +1,53 @@ +name: CLA Assistant + +on: + issue_comment: + types: [created] + pull_request_target: + types: [opened, synchronize] + +permissions: + actions: write + contents: write + pull-requests: write + statuses: write + +concurrency: + group: cla-${{ github.event.pull_request.number || github.event.issue.number || github.run_id }} + cancel-in-progress: true + +jobs: + cla: + runs-on: ubuntu-latest + timeout-minutes: 10 + steps: + - name: Maintainer fast path + if: >- + github.event_name == 'pull_request_target' && + (contains(fromJSON('["TheGreatAxios","brianjfox"]'), github.event.pull_request.user.login) || + endsWith(github.event.pull_request.user.login, '[bot]')) + run: echo "Maintainer or bot pull request; CLA not required." + - name: CLA Assistant + if: >- + ((github.event.comment.body == 'recreate-signatures' || + github.event.comment.body == 'I have read the CLA Document and I hereby sign the CLA') || + github.event_name == 'pull_request_target') && + !(github.event_name == 'pull_request_target' && + (contains(fromJSON('["TheGreatAxios","brianjfox"]'), github.event.pull_request.user.login) || + endsWith(github.event.pull_request.user.login, '[bot]'))) + # corbitsdev/cla-assistant-action v2.6.1-node24: upstream v2.6.1 on node24. + uses: corbitsdev/cla-assistant-action@ef6d3e51db8232fe93090810f13bde30497c1d74 + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + with: + path-to-document: "https://github.com/${{ github.repository }}/blob/main/CLA.md" + path-to-signatures: "signatures/version1/cla.json" + branch: "cla-signatures" + allowlist: TheGreatAxios,brianjfox,*[bot] + custom-notsigned-prcomment: >- + Thank you for your contribution. Before it can be merged, please read our + [Contributor License Agreement](https://github.com/${{ github.repository }}/blob/main/CLA.md) + and sign it by posting a new comment on this pull request containing + exactly the line below (nothing else): + custom-pr-sign-comment: "I have read the CLA Document and I hereby sign the CLA" + custom-allsigned-prcomment: "All contributors have signed the CLA." diff --git a/CLA.md b/CLA.md new file mode 100644 index 0000000..201eec8 --- /dev/null +++ b/CLA.md @@ -0,0 +1,64 @@ +# Contributor License Agreement (CLA) + +Version 1.0 + +This Contributor License Agreement ("Agreement") is entered into between the contributor ("Contributor") and ABK Labs, Inc. ("Maintainer"). + +By submitting any Contribution to a project maintained by Maintainer, the Contributor agrees to the following terms. + +## 1. Definitions + +"Contribution" means any source code, object code, documentation, test cases, designs, specifications, bug fixes, enhancements, comments, pull requests, commits, issues containing code, or other materials intentionally submitted to a project maintained by Maintainer. + +## 2. Copyright Ownership + +The Contributor retains ownership of the Contributor's copyrights in the Contribution. + +No transfer of copyright ownership is required by this Agreement. + +## 3. License Grant to Maintainer + +The Contributor grants Maintainer a perpetual, worldwide, non-exclusive, irrevocable, royalty-free license to: + +- use, reproduce, modify, distribute, display, perform, and sublicense the Contribution; +- combine the Contribution with other software and works; +- distribute the Contribution under the project's current license; +- distribute the Contribution under future versions of the project's license; +- distribute the Contribution under alternative open-source, source-available, commercial, proprietary, or dual-license terms. + +## 4. License Grant to the Public + +The Contributor agrees that the Contribution may be distributed as part of the applicable project under the project's then-current license terms, including LGPL-2.1 or any successor license adopted by Maintainer. + +## 5. Contributor Representations + +The Contributor represents and warrants that: + +1. The Contributor created the Contribution or otherwise has sufficient rights to submit it. +2. The Contributor has the legal authority to grant the rights described in this Agreement. +3. To the best of the Contributor's knowledge, the Contribution does not knowingly infringe the intellectual property rights of any third party. +4. Any third-party material included in the Contribution has been properly disclosed and is compatible with the rights granted under this Agreement. + +## 6. Corporate Contributions + +If a Contribution is submitted on behalf of an employer or other legal entity, the person accepting this Agreement represents that they are authorized to bind that entity to this Agreement. + +## 7. No Obligation + +Maintainer is not obligated to use, distribute, maintain, support, or accept any Contribution. + +## 8. Disclaimer + +Except as expressly stated in this Agreement, the Contribution is provided "AS IS" without warranties or conditions of any kind. + +## 9. Electronic Acceptance + +The Contributor agrees that electronic acceptance of this Agreement, including acceptance through a website, source-control platform, click-through process, pull-request workflow, or similar mechanism, shall have the same force and effect as a handwritten signature. + +## 10. Governing Law + +This Agreement shall be governed by the laws of the State of California, excluding its conflict-of-law provisions. + +--- + +By submitting a Contribution, the Contributor acknowledges that they have read and agree to this Agreement. From 73c8da4098d1e4d560cb5718d2fce869bbfa929e Mon Sep 17 00:00:00 2001 From: Sawyer Cutler Date: Fri, 25 Sep 2026 20:02:33 -0700 Subject: [PATCH 2/4] build: align package.json and tsconfig with the package standard --- .gitignore | 6 ++++-- bunfig.toml | 2 -- package.json | 15 ++++++++++----- tsconfig.build.json | 8 +++----- tsconfig.json | 7 +++---- 5 files changed, 20 insertions(+), 18 deletions(-) delete mode 100644 bunfig.toml diff --git a/.gitignore b/.gitignore index 2f6a620..6f17218 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,8 @@ node_modules/ dist/ -.corbits/ -.DS_Store +*.tsbuildinfo +*.tgz +coverage/ .env .env.* +.DS_Store diff --git a/bunfig.toml b/bunfig.toml deleted file mode 100644 index 98c2e52..0000000 --- a/bunfig.toml +++ /dev/null @@ -1,2 +0,0 @@ -[test] -root = "." diff --git a/package.json b/package.json index 511b861..d46ba8a 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,14 @@ "name": "@corbits/openai-responses", "version": "0.2.0", "description": "Interchange ProviderAdapter for the OpenAI Responses API wire protocol with quirks-based vendor configuration, SSE and non-streaming parsing, and reasoning signature replay.", - "homepage": "https://github.com/corbitsdev/corbits-openai-responses", + "keywords": [ + "corbits", + "inference", + "interchange", + "openai", + "responses" + ], + "homepage": "https://github.com/corbitsdev/corbits-openai-responses#readme", "bugs": { "url": "https://github.com/corbitsdev/corbits-openai-responses/issues" }, @@ -19,8 +26,6 @@ ], "type": "module", "sideEffects": false, - "main": "./dist/index.js", - "types": "./dist/index.d.ts", "exports": { ".": { "types": "./dist/index.d.ts", @@ -31,13 +36,13 @@ "access": "public" }, "scripts": { - "build": "tsc -p tsconfig.build.json", + "build": "rm -rf dist && tsc -p tsconfig.build.json", "prepack": "bun run build", "typecheck": "tsc --noEmit", "lint": "oxlint", "format": "oxfmt", "format:check": "oxfmt --check", - "test": "bun test", + "test": "bun test src --pass-with-no-tests", "test:e2e": "bun test e2e", "check": "bun run typecheck && bun run lint && bun run format:check && bun run test" }, diff --git a/tsconfig.build.json b/tsconfig.build.json index f01ffe4..af6694f 100644 --- a/tsconfig.build.json +++ b/tsconfig.build.json @@ -1,14 +1,12 @@ { "extends": "./tsconfig.json", "compilerOptions": { - "module": "NodeNext", - "moduleResolution": "NodeNext", - "allowImportingTsExtensions": false, - "composite": false, + "noEmit": false, "declaration": true, "declarationMap": false, "sourceMap": false, - "noEmit": false, + "module": "NodeNext", + "moduleResolution": "NodeNext", "outDir": "dist", "rootDir": "src" }, diff --git a/tsconfig.json b/tsconfig.json index b883ac9..dda942c 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -3,17 +3,16 @@ "esModuleInterop": true, "skipLibCheck": true, "target": "ESNext", - "allowJs": true, - "resolveJsonModule": true, + "module": "ESNext", + "moduleResolution": "bundler", "moduleDetection": "force", "isolatedModules": true, "verbatimModuleSyntax": true, - "moduleResolution": "bundler", + "resolveJsonModule": true, "strict": true, "noUncheckedIndexedAccess": true, "noImplicitOverride": true, "exactOptionalPropertyTypes": true, - "module": "ESNext", "noEmit": true, "lib": ["ESNext"], "types": ["bun"] From f88b25cddfc4b4bc780936ed4f079e729493805e Mon Sep 17 00:00:00 2001 From: Sawyer Cutler Date: Fri, 25 Sep 2026 20:02:33 -0700 Subject: [PATCH 3/4] ci: run check and a Node pack smoke --- .github/workflows/ci.yml | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index f8ee24c..2f02d6f 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -7,20 +7,22 @@ on: jobs: check: - name: check (node ${{ matrix.node-version }}) runs-on: ubuntu-latest timeout-minutes: 15 - strategy: - fail-fast: false - matrix: - node-version: [24] steps: - uses: actions/checkout@v5 - uses: actions/setup-node@v4 with: - node-version: ${{ matrix.node-version }} + node-version: 24 - uses: oven-sh/setup-bun@v2 - with: - bun-version: latest - run: bun install --frozen-lockfile - run: bun run check + - run: bun run test:e2e + - name: node consumer smoke + run: | + set -euo pipefail + TARBALL="$PWD/$(npm pack --silent)" + mkdir -p "$RUNNER_TEMP/c" && cd "$RUNNER_TEMP/c" + npm init -y >/dev/null && npm pkg set type=module >/dev/null + npm install "$TARBALL" + node -e 'import("@corbits/openai-responses").then((m) => { for (const n of ["createOpenAIResponsesAdapter", "responsesAdapterFactory"]) if (typeof m[n] !== "function") throw new Error("missing export: " + n); })' From f26b965ab44ed6dcb28aa67cb7a135ba213c923d Mon Sep 17 00:00:00 2001 From: Sawyer Cutler Date: Fri, 25 Sep 2026 20:02:33 -0700 Subject: [PATCH 4/4] docs: trim CONTRIBUTING and AGENTS.md --- AGENTS.md | 15 ++------------- CONTRIBUTING.md | 36 ++++++++++++++++++++++++------------ 2 files changed, 26 insertions(+), 25 deletions(-) diff --git a/AGENTS.md b/AGENTS.md index e0522ba..fd1b7c7 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -56,17 +56,6 @@ re-exports plus the provider ids and factory record: ## Local development +```sh +bun install && bun run check ``` -bun install -bun run check # typecheck + lint + format:check + test -``` - -## Distribution - -The package ships compiled `dist/` on npm as `@corbits/openai-responses`: -`main`/`types` and `exports` point at `dist/index.js` / `dist/index.d.ts` -(built with `bun run build`, i.e. `tsc -p tsconfig.build.json`). -Consumers install it with `bun add @corbits/openai-responses` and Bun or -Node loads the built output. It requires Node >=24 and Bun >=1.2.0 per the -`engines` field. To -publish, bump the version and run `npm publish --access public`. diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 6e118f2..150c606 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -1,24 +1,15 @@ # Contributing -## How it works - -`quirks` are JSON on `InferenceSource` (persisted, sent over the wire). -`hooks` are code, applied once at `responsesAdapterFactory` construction. -Defaults are protocol-native: system prompt, `maxTokens`, and `temperature` -go through unless a quirk opts a backend out. The host owns provider ids; a -reasoning signature is tagged with the id in effect when it was issued. - ## Development ```sh -git clone https://github.com/corbitsdev/corbits-openai-responses.git -cd corbits-openai-responses bun install bun run check ``` -`bun run check` is typecheck + lint + format:check + test. `bun run format` -rewrites the tree. +`bun run check` runs typecheck, lint, format check and unit tests. `bun run format` rewrites the tree. + +Contributors sign the [CLA](CLA.md) on their first PR; the CLA bot explains how. Unit tests sit next to the code in `src/`; end-to-end tests live in `e2e/`. `e2e/live.test.ts` calls a real Responses API and runs only when @@ -31,9 +22,30 @@ OPENAI_RESPONSES_LIVE_MODEL=gpt-oss:20b bun run test:e2e `OPENAI_RESPONSES_LIVE_KEY` is optional. +## How it works + +`quirks` are JSON on `InferenceSource` (persisted, sent over the wire). +`hooks` are code, applied once at `responsesAdapterFactory` construction. +Defaults are protocol-native: system prompt, `maxTokens`, and `temperature` +go through unless a quirk opts a backend out. The host owns provider ids; a +reasoning signature is tagged with the id in effect when it was issued. + ## Commit messages Commit subjects and PR titles follow [Conventional Commits](https://www.conventionalcommits.org): `feat`, `fix`, `refactor`, `test`, `docs`, `build`, `ci`, `perf`, and `chore(release): x.y.z` for releases. Add `!` only for public API breaks: removed or renamed exports, changed signatures, newly required params. Peer and dependency range changes are `build(deps):` with no `!`. Keep subjects imperative, lowercase after the colon, 72 characters or less, and free of ticket IDs. Every PR links its issue with a `Closes ` line in the PR body. + +## Releasing + +Releases are manual. On a clean, up-to-date `main`: + +```sh +npm version -m "chore(release): %s" +git push --follow-tags +gh release create "v$(node -p 'require("./package.json").version')" --generate-notes +npm publish +``` + +Bump minor only for breaking API changes; everything else is a patch. `prepack` builds `dist/` from the tagged commit.