Skip to content

feat: add --json and --since flags to jilog review nightly#1

Merged
Joi merged 1 commit into
Joi:mainfrom
mvanhorn:feat/review-nightly-json-since
May 11, 2026
Merged

feat: add --json and --since flags to jilog review nightly#1
Joi merged 1 commit into
Joi:mainfrom
mvanhorn:feat/review-nightly-json-since

Conversation

@mvanhorn
Copy link
Copy Markdown
Contributor

Summary

jilog review nightly --json and jilog review nightly --dry-run --since 24h now run as documented in the README.

Why this matters

The README's Quick Start shows jilog review nightly --json | your-agent synthesize-suggestions (line 52) and the dry-run example shows jilog review nightly --dry-run --since 24h (line 57), but NightlyArgs only exposes --days, --digest-dir, --dry-run, --create-issues, --date, --processed-file. Anyone copy-pasting from the README hits an unknown-flag error.

This PR closes that drift in code rather than walking the README back, so the documented agent-synthesis pipe works end to end.

Changes

  • --json (boolean): emit a single JSON object to stdout and suppress the human summary lines so the output is one parseable document. The query subcommand already accepts --format json, so the JSON path is consistent with existing precedent inside the same binary.
  • --since <duration>: accepts Nh, Nd, Nw, or YYYY-MM-DD. Reuses pub(crate) fn parse_since from commands::query. parse_since is extended with an hour suffix so --since 24h from the README example works as written.
  • --days is retained for back-compat. --since and --days conflict only when both are user-supplied (clap v4 evaluates conflicts_with via ValueSource::CommandLine, so --since 24h alone with the default --days 1 does not raise).
  • DigestReport is left non-Serialize. The JSON output is hand-built as a serde_json::Value inside commands/review.rs, so this PR stays in the jilog crate.

JSON shape

{
  "schema_version": 1,
  "sessions_scanned": 0,
  "corrections": 0,
  "errors": 0,
  "workarounds": 0,
  "p0_alerts": { "<tool_name>": ["<session_id>", ...] },
  "digest_path": "/abs/path/learning-digest-2026-05-10.md",
  "created_issues": [{"id": "...", "backend": "...", "title": "...", "url": "..."}]
}

schema_version: 1 reserves room for additive evolution. p0_alerts is the structured tool-to-sessions map (not a count) so a downstream agent can synthesize from the JSON alone without re-parsing the markdown digest. created_issues carries the IssueRef fields the markdown digest does not expose. digest_path is null under --dry-run. Happy to adjust the shape if you had something different in mind for v1.

Testing

  • cargo build --workspace passes
  • cargo test --workspace passes
  • Smoke-tested jilog review nightly --dry-run --since 24h and jilog review nightly --dry-run --json | jq .
  • 6 new unit tests cover: --since alone with default --days does not conflict, --since + user --days does conflict, --since 24h matches --days 1 window within 2s, --since parser error path, JSON output keys present, --json --dry-run emits digest_path: null.

Closes README/code drift: the README documents 'jilog review nightly --json'
and '--since 24h' but neither flag was implemented (only --days existed).

- --json emits a single JSON object to stdout with schema_version: 1 and
  the documented keys (counts plus structured p0_alerts and created_issues),
  suppressing the human summary lines so output is one parseable document.
- --since accepts the same forms as 'jilog query --since' (Nh, Nd, Nw,
  YYYY-MM-DD); reuses pub(crate) parse_since from commands::query.
  parse_since extended to accept hour suffix.
- --since conflicts with --days only when both are user-supplied (clap v4
  ValueSource::CommandLine semantics); --days default of 1 stays.
- DigestReport stays non-Serialize; JSON is hand-built from a serde_json::Value
  in commands/review.rs.
@Joi
Copy link
Copy Markdown
Owner

Joi commented May 11, 2026

Hi Mvan — thanks for the first PR! Both of these are excellent. Reading through them is a pleasure: sharp motivation, careful scoping, tests that exercise the subtle behavior (the clap conflicts_with quirk here, the workaround/deferral overlap in #2).

This one I'm merging as-is. schema_version: 1 is exactly the right move, p0_alerts as a structured map (not a count) is the right design, and the reuse of parse_since keeps the parser unified. One micro-thought for a future PR if you ever want to revisit: serde_json::to_string_pretty is friendly for inspection but jq/JSONL pipelines tend to prefer compact one-line output. Not a blocker for this one.

Thanks again — looking forward to more.

— Joi

@Joi Joi merged commit 674d54e into Joi:main May 11, 2026
1 check passed
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