feat: search_by_ioc(with_artifacts=) returns artifact metadata rows - #329
Conversation
The reverse IOC search answers bare sha256s, so a caller that wants to show the matching artifacts has to fan out one metadata search per hash. The server gains an opt-in `with_artifacts` that returns each artifact's metadata-search row instead; this exposes it on both clients as an optional keyword. - Absent or False sends nothing new: every existing call, including one with no search term, builds exactly the request it did before and yields the same IOC/sha256 items. - True sends `with_artifacts=1` and parses the rows with `Metadata`, the resource `search_by_metadata` already yields. An int, not a bool: the session renders bools as 'True', which the server's boolean parser refuses. The row parse is covered by a respx body on both transports because the e2e stack does not serve the parameter yet; recording the live pass is parked in specs/99-open-questions.md. Builder and pass-through tests pin the request shape on both clients, including that a bare call is still sent unchanged.
… 400 rule The with_artifacts rows carry the server's include set, which also keeps scan.first_scan.created and hash.ssdeep/tlsh, so first_seen, ssdeep and tlsh are populated. The endpoint table and docstring now list that set as the server's, and state the refusal precisely: with_artifacts=True and no term is a 400; without the flag a bare call behaves as before. The respx fixture mirrors the set exactly and asserts the populated fields plus one that falls outside it. The new test module is listed in the testing spec.
The CLI client adopts `search_by_ioc(with_artifacts=)` in the paired change set and expresses that as `polyswarm_api>=4.7.0`. develop already declares 4.6.0 for a surface that does not include this keyword, so the floor needs the next version up; a floor cannot name a version this repo has not declared, so the bump lands here, in the feature PR (AGENTS.md's standing exception). Minor: one new optional keyword whose default preserves today's request, so no existing call changes behaviour. Bumped with bump-my-version; the emitted string is a clean `4.7.0`. The `with_artifacts=True` path needs a server that supports the parameter, so this repo releases only after that server leg is deployed, and before the CLI.
|
Code, codegen mirror, tests and the 03/04/99 spec updates look correct. The base is Spec drift: |
…t invariant 6 Invariant 6 said version bumps never go in feature PRs, which contradicts AGENTS.md's standing exception and the bump this change carries. It now names the exception: when a sibling resolves this repo from source by branch name and raises its floor to the new surface's version, the clean X.Y.0 bump lands in the feature PR.
|
Checked against AGENTS.md and specs/02, 03, 04, 05 and 99. I found no correctness or spec-drift issues:
One small thing (gitflow/hygiene): the head branch |
|
Clean against AGENTS.md and specs: the builder and parser change is correct on both transports, the sync mirror is regenerated, specs 03/04/05/99 are updated, the base is One gitflow nit: the head branch |
Summary
search_by_ioc(...)(sync and async) gains an optionalwith_artifacts=Falsekeyword. When it isTrue, the SDK sendswith_artifacts=1and parses each result row as aMetadataresource instead of a sha256 string. That exposes the server's new IOC → artifacts rows.Semantics
The default path is unchanged. Without the keyword, the request and the parsed results are exactly as before, including a call with no IOC term. The SDK adds no client-side validation.
The field set is owned by the server:
artifact.*scan.first_scan.created(sofirst_seenis populated)hash.ssdeepandhash.tlshpolyunite.malware_familyFields outside that set, such as the
strings.*lists, come back asNone.Errors. With
with_artifacts=Trueand no IOC term, the server answers 400, which the caller sees as the usual typed exception.Encoding. The flag is sent as
1because the server's boolean parser accepts0/1/true/false, and the SDK would otherwise stringifyTrue. A test pins this.Version
This PR bumps the version to 4.7.0 (develop already declares 4.6.0 for unreleased work). That is the standing exception in AGENTS.md: the CLI's CI installs this SDK from the same-named branch, so the CLI's
polyswarm_api>=4.7.0floor must name a version this branch declares.specs/05-downstream-contract.mdinvariant 6 predates that exception, which 4.4.0, 4.5.0 and 4.6.0 already used.Requires / deploy order
with_artifacts. A server that ignores the flag returns sha256 strings, and theMetadataparse then fails loudly.>=4.7.0.Tests
test/ioc_search_test.pyuses respx and runs against both the sync and async clients:Metadata, with a fixture that mirrors the server's field set;specs/99-open-questions.md.