Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 35 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,41 @@

## Unreleased

### Investigation Engine — `limacharlie investigate` (experimental)

- New `investigate` command group and `limacharlie.sdk.investigation.Investigation`
SDK class to build, test and tune Investigation Engine templates and to run
investigations, so a person or an AI agent can drive the whole loop from the
CLI: `kit` (authoring kit, fetched in sections), `operators`, `packs`,
`templates list|get|validate|test|save|promote|delete|install-defaults`,
`runs start|get|list|events|steps|case|cancel`, `wave`,
`actions list|approve|deny` and `policy get|status|pause|resume`. See
`doc/cli/investigation-engine.md`.
- `templates save` always writes a DRAFT (a source that says `status: active`
is refused; only a person's explicit `--status active` activates), never
overwrites a record without `--overwrite`, and never replaces an active
template with a draft. `templates test` dry-runs a template on real past
detections or cases and prints per-sample verdicts and the agreement summary.
- Engine failures keep the engine's coded issues (`code`, `path`, `message`,
`suggestion`) and error code verbatim, and say when the feature is not
enabled for the deployment or the permissions are missing.
- `wave` and `templates test --samples-file` read YAML with 1.2 scalar rules (`off`/`yes`
stay text, an unquoted date stays a string) so values reach the engine as written;
unreadable or malformed input files and every Hive/API failure are reported as
structured JSON (with the backend's `error_code`) in a structured output format.
- `templates install-defaults` reads the authoring kit's `library` section; it
needs an engine version that serves it.
- The typed 401/403/404/422/429 errors raised for an HTTP error answer now carry
the parsed answer as `response_body`, as `ApiError` already did.
- The `investigate` flags and help match the engine: `runs start --urgency` is
`low|medium|high|critical` (default derived from the alert, else medium);
`--auto` sends no plan (the engine refuses `plan.auto` for a person's run) so
the engine picks the active template by `applies_to`, with new `--category`,
`--severity`, `--priority` and `--tag` to say what the alert looks like;
`templates test --strict` refuses overrides that would loosen the policy;
`runs list --trigger` takes the trigger kind (detection, message, entity, case,
question) and `--verdict` also takes `undecided`; `policy get` takes `--template`.

### Sync — `sync push` no longer turns quoted strings into numbers

- `sync push` (and `Configs.push` / `Configs.push_from_file`) stored some
Expand Down
1 change: 1 addition & 0 deletions doc/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
| [Hive & Data Stores](cli/hive-data.md) | hive, secret, lookup, playbook, note, sop, app-control, adapter, cloud-sensor, extension |
| [Infrastructure](cli/infrastructure.md) | sync, output, artifact, payload, yara, integrity, logging, exfil |
| [Cloud Security & Code Security](cli/cloud-security.md) | cloudsec (findings, inventory, graph, compliance, CAASM, code lane, container images, fleet, exports) |
| [Investigation Engine](cli/investigation-engine.md) | investigate (authoring kit, templates, dry runs on past alerts, runs, waves, approvals, policy) |
| [Email Security](cli/email-security.md) | mailsec (onboarding, coverage, triage, EML, remediation, campaigns, reports, sample submission, rules, tenant purge) |
| [Other Commands](cli/other-commands.md) | api, arl, usp, spotcheck, job, schema, completion, help/discover |

Expand Down
1 change: 1 addition & 0 deletions doc/cli/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -162,6 +162,7 @@ limacharlie schema dr create
| [Infrastructure](infrastructure.md) | sync, output, artifact, payload, yara, integrity, logging, exfil |
| [Cloud Security & Code Security](cloud-security.md) | cloudsec (findings, inventory, graph, compliance, CAASM, code lane, container images, fleet, exports) |
| [Email Security](email-security.md) | mailsec (onboarding, coverage, triage, EML, remediation, campaigns, reports, sample submission, rules, tenant purge) |
| [Investigation Engine](investigation-engine.md) | investigate (authoring kit, templates, dry runs on past alerts, runs, waves, approvals, policy) |
| [Other Commands](other-commands.md) | api, arl, usp, spotcheck, job, schema, completion, help/discover, case |

## See Also
Expand Down
235 changes: 235 additions & 0 deletions doc/cli/investigation-engine.md

Large diffs are not rendered by default.

4 changes: 4 additions & 0 deletions doc/sdk/other-classes.md
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,10 @@ The Cloud Security (CNAPP) surface also includes Code Security: repository and c

`limacharlie.sdk.mailsec.Mailsec` wraps Email Security onboarding, provider tests, coverage, messages, justified EML downloads, verdict revisions, campaigns, remediation, and user reports. See [Security Products](security-products.md#email-security) for setup, examples, and pagination, and [CLI: mailsec](../cli/email-security.md) for complete workflows.

## Investigation

`limacharlie.sdk.investigation.Investigation` wraps the Investigation Engine (experimental): the authoring kit, plan validation and dry runs on past alerts, template records (saved as drafts unless a person passes `status="active"`), runs, waves, the approvals inbox and the autonomy switch. Failures raise `InvestigationError`, which keeps the engine's `error_code` and coded `issues`. See [CLI: investigate](../cli/investigation-engine.md) for the workflow and permissions.

## See Also

- [CLI: case](../cli/other-commands.md#case) — Case CLI commands
Expand Down
1 change: 1 addition & 0 deletions limacharlie/cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -147,6 +147,7 @@ def _wants_help() -> bool:
"hive": ("hive", "group"),
"ingestion-key": ("ingestion_key", "group"),
"installation-key": ("installation_key", "group"),
"investigate": ("investigate", "group"),
"integrity": ("integrity", "group"),
"ioc": ("ioc", "group"),
"job": ("job", "group"),
Expand Down
4 changes: 3 additions & 1 deletion limacharlie/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -872,11 +872,13 @@ def request(self, verb: str, url: str, params: dict[str, Any] | None = None, alt
self._debug(f"Rate limited, waiting {wait}s before retry...")
time.sleep(wait)
continue
raise RateLimitError(
rate_err = RateLimitError(
f"Rate limit exceeded: {data}",
retry_after=parse_retry_after(error_headers.get("retry-after")),
code=code,
)
rate_err.response_body = data
raise rate_err

if code == HTTP_SERVICE_UNAVAILABLE:
if retry_service_unavailable and not has_unavailable_retried and retries < max_retries:
Expand Down
Loading
Loading