Skip to content

feat: add --text flag and auto-save for deep research output#68

Merged
NormallyGaussian merged 3 commits intomainfrom
feat/research-output-schema
May 6, 2026
Merged

feat: add --text flag and auto-save for deep research output#68
NormallyGaussian merged 3 commits intomainfrom
feat/research-output-schema

Conversation

@NormallyGaussian
Copy link
Copy Markdown
Contributor

@NormallyGaussian NormallyGaussian commented Mar 12, 2026

Summary

Adds --text to research run (and research poll) for text-schema markdown reports, plus --text-description to steer them. Always auto-saves results to ./parallel-research/<run_id>.{json,md} (override with -o BASE). Adds a --force overwrite guard, a KeyboardInterrupt resume hint, parent-dir mkdir, and a /tmp fallback so a billed API call is never lost.

Behavior changes (worth noting in release notes)

  • Default save. research run now writes a file by default (was: only on -o). The new default base is ./parallel-research/<run_id>. Pass -o BASE to override; pass --no-wait to skip saving (no result yet to save).
  • Overwrite guard. research run / research poll refuse to overwrite existing output unless --force is passed; the error lists each target with (exists) / (new).
  • --text-description requires --text — rejects with a UsageError otherwise.
  • -o suffix handling. .json / .md are stripped (so -o report and -o report.json are equivalent); other suffixes are preserved (-o report.bak produces report.bak.json). A trailing slash or an existing directory on -o appends <run_id> inside it (so -o outputs/ does the obvious thing).

Test plan

  • 676 unit tests pass (ruff, ruff format, ty, pytest); new tests cover --text / --force / mkdir / suffix-strip / dir-detection / --text-description / preview-path correctness.
  • Live pro-fast runs against the API:
    • --text produced .json (basis + citations) plus .md (markdown report with inline citations).
    • Default + --json produced structured JSON with output.type="json".
  • Saver keys off the SDK's output.type discriminator (live confirmed "json" vs "text").
  • research poll shares the same save semantics; KeyboardInterrupt and Timeout paths consolidated into shared helpers.
  • Help / dry-run / "Will save to" preview accurately reflect file paths for all -o shapes (report, report.json, report.bak, outputs/).

@NormallyGaussian NormallyGaussian force-pushed the feat/research-output-schema branch from cb6b15e to 196cb43 Compare May 6, 2026 00:11
@NormallyGaussian NormallyGaussian marked this pull request as ready for review May 6, 2026 01:15
Add output schema support (auto vs text) to the research run command.
Default uses auto schema (structured JSON), --text switches to text
schema (markdown report). Results always save to files automatically
using the run ID as filename, or a custom path via -o.

- Auto schema: saves {base}.json with full structured response
- Text schema: saves {base}.json (metadata + basis) and {base}.md
  (markdown content)
- Executive summary always printed to stdout
- New _save_and_display_research replaces old dual-purpose output fn
- 62 tests covering schema selection, file output, and display
…, --force, robustness

Builds on the --text/auto-save base added earlier in this branch with a
round of UX, accuracy, and quality fixes from review:

- Default save path is now ./parallel-research/<run_id> instead of cwd, so
  invoking from $HOME (or anywhere) doesn't litter the directory. -o still
  takes precedence; trailing slash or an existing dir on -o appends <run_id>
  inside it.
- Refuse to overwrite existing output files; pass --force to clobber. Error
  lists each target with (exists)/(new) markers.
- KeyboardInterrupt handler prints "Resume with: parallel-cli research poll
  <run_id>" and exits 130, so a Ctrl-C mid-poll never loses the run_id.
- mkdir parents for -o paths into missing dirs; on OSError write failure,
  fall back to /tmp/<run_id>.{json,md} so a billed API call isn't lost.
- --text-description steers text-schema reports (rejects without --text).
- Suffix handling: only strip .json/.md from -o; preserve other extensions
  (.bak, .v2) so -o report.bak writes report.bak.json.
- Saver keys off the SDK's output.type discriminator instead of inferring
  from isinstance(content, str). Verified live: auto returns type="json",
  text returns type="text".
- Dedupe: extracted _exit_research_interrupted / _exit_research_timeout
  helpers shared by research_run and research_poll. Moved auto-cwd-isolation
  pytest fixture into tests/conftest.py so test_cli.py is covered too.
…ture

Same effect, less foreign syntax: a single-element list captures the run_id
from the on_status callback so the KeyboardInterrupt handler can print a
'Resume with: parallel-cli research poll <run_id>' hint.
@NormallyGaussian NormallyGaussian force-pushed the feat/research-output-schema branch from da10ea5 to 20c825a Compare May 6, 2026 01:15
@NormallyGaussian NormallyGaussian merged commit cc2f470 into main May 6, 2026
7 checks passed
@NormallyGaussian NormallyGaussian deleted the feat/research-output-schema branch May 6, 2026 01:17
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.

2 participants