Skip to content

feat(import): add codex adapter for native rollout logs - #27

Merged
takashi-matsuyama merged 1 commit into
mainfrom
feat/import-codex
Jun 1, 2026
Merged

takashi-matsuyama merged 1 commit into
mainfrom
feat/import-codex

Conversation

@takashi-matsuyama

Copy link
Copy Markdown
Member

What

Adds basou import codex, the second import adapter, deriving Basou sessions from OpenAI Codex native rollout logs (~/.codex/sessions/<date>/rollout-*.jsonl). This is the multi-vendor follow-up to basou import claude-code (#16) and makes the vendor-neutral provenance schema concrete across two tools.

Event mapping

Each rollout becomes one imported session:

  • session_started / session_ended from the first / last timestamped record.
  • command_executed from each exec_command function call, recorded as bash -c "<line>" (command + workdir from the call's JSON arguments), with the real exit_code and duration_ms parsed from the paired function_call_output (Process exited with code N, Wall time: X seconds).

File changes and decisions are deferred: Codex applies edits inside exec_command (no dedicated edit tool) and records an approval_policy rather than per-action approvals, so neither has a clean signal to map.

Discovery

Codex stores rollouts by date, not per project, so discovery walks the sessions tree and matches each rollout's recorded session_meta.cwd against --project (default: the repository root). Only sessions started in that project are imported; the exact-match is the safety boundary. --all, --session <id>, --force, --dry-run, and --json behave as for import claude-code.

Refactor

The claude-code and codex paths now share a vendor-neutral commit loop, importDerivedSessions(paths, manifest, options, candidates). Each adapter builds a list of { externalId, toPayload } candidates from its own discovery and funnels them through the shared core, which dedups, validates, force-replaces, and writes. Re-using the existing importSessionFromJson pipeline keeps path sanitization and id minting unchanged.

Adds codex-import to the source.kind enum (additive) and documents it in the schema spec and CHANGELOG.

Verification

  • pnpm -r build && pnpm typecheck && pnpm test && pnpm lint all green. Tests: core 665 (+8), cli 386 (+9).
  • Real-data dry-run + import in a throwaway workspace: 38 sessions / 1451 events imported from 45 basou-workspace rollouts (7 skipped as no-action). Exit codes (1372 real / 3 null), working-directory sanitization (~/projects/...), and session list / handoff generate all confirmed; no raw operator paths in tracked artifacts.

🤖 Generated with Claude Code

Add `basou import codex`, the second import adapter, deriving Basou
sessions from OpenAI Codex native rollout logs
(~/.codex/sessions/<date>/rollout-*.jsonl). Each rollout becomes one
imported session carrying session_started / session_ended and
command_executed from exec_command calls (bash -c "<line>"), with the
real exit_code and duration_ms parsed from the paired command output.

Codex stores rollouts by date rather than per project, so discovery
walks the tree and matches each rollout's recorded working directory
against --project (default: the repository root); only sessions started
in that project are imported. File changes and decisions are not
derived: Codex applies edits inside exec_command and has no structured
question / answer record, so neither has a clean signal to map.

The claude-code and codex commands now share a vendor-neutral commit
loop (importDerivedSessions): discovery builds the candidates, the
shared core dedups, validates, force-replaces, and writes. Adds
codex-import to the session source.kind enum.

Verified on real data: 38 sessions / 1451 events imported from 45
basou-workspace rollouts (7 skipped as no-action), with exit codes and
working-directory sanitization intact.
@takashi-matsuyama
takashi-matsuyama merged commit 50c81f6 into main Jun 1, 2026
7 checks passed
@takashi-matsuyama
takashi-matsuyama deleted the feat/import-codex branch June 1, 2026 09:30
takashi-matsuyama added a commit that referenced this pull request Jun 1, 2026
…on (#28)

Two refinements to the import adapters surfaced by an adversarial
review of the codex adapter (#27):

- Scope re-import dedup to the session source kind.
  loadExistingByExternalId now indexes only sessions whose source.kind
  matches the adapter being imported, so a Codex import can no longer
  dedup against (or, under --force, delete) a Claude-derived session
  that happens to share an id string. The id namespaces stay separate
  as more adapters are added.
- `basou import codex --session <id>` now errors when no rollout in the
  project matches the id, instead of reporting a silent success. This
  mirrors the Claude path, which fails on a missing --session transcript.

Adds tests for both: cross-kind isolation under --force, and the
missing --session error.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant