lex-velociraptor
Velociraptor DFIR automation for LegionIO.
lex-velociraptor gives Legion a clean control surface for Velociraptor operations:
run server-side VQL, search enrolled clients, launch artifact collections, read
flow results, cancel flows, and create hunts. It intentionally uses
Velociraptor's supported API-client CLI path instead of binding Ruby directly to
Velociraptor's Go protobufs, so it stays aligned with the interface Velocidex
documents for external automation.
Why This Exists
Velociraptor is excellent at endpoint collection, live response, and DFIR investigation. Legion is excellent at coordinating work across tools, agents, queues, and policy boundaries. This extension connects the two:
- Let Legion agents ask targeted endpoint questions through VQL.
- Trigger Velociraptor artifact collections from Legion workflows.
- Pull completed flow or hunt results back into downstream automation.
- Keep Velociraptor credentials outside prompts and task payloads.
- Avoid unstable GUI/REST internals by using the API-config CLI route.
Installation
gem install lex-velociraptorFor local development:
bundle install
bundle exec rspec
bundle exec rubocopRequirements
- Ruby >= 3.4
- A Velociraptor binary available on
PATH, orVELOCIRAPTOR_BINset - A Velociraptor API client config generated from the server configuration
- API roles that match the operations you plan to run
Create the API client config from a Velociraptor server:
velociraptor \
--config server.config.yaml \
config api_client \
--name legion \
--role investigator,api \
api.config.yamlStore api.config.yaml like a secret. It contains client key material and can
run whatever the assigned Velociraptor roles allow.
Configuration
You can pass connection settings directly:
require 'legion/extensions/velociraptor'
client = Legion::Extensions::Velociraptor::Client.new(
api_config: '/secure/path/api.config.yaml',
binary: '/usr/local/bin/velociraptor'
)Or configure the process environment:
export VELOCIRAPTOR_BIN=/usr/local/bin/velociraptor
export VELOCIRAPTOR_API_CONFIG=/secure/path/api.config.yamlclient = Legion::Extensions::Velociraptor::Client.newOptional settings:
| Option | Environment | Default | Purpose |
|---|---|---|---|
api_config |
VELOCIRAPTOR_API_CONFIG |
nil |
Path to Velociraptor API client config |
binary |
VELOCIRAPTOR_BIN |
velociraptor |
Velociraptor executable |
timeout |
none | nil |
Ruby-side command timeout in seconds |
Quick Start
Run server info:
client.server_infoRun raw VQL:
client.query(vql: 'SELECT * FROM info()')Find clients the same way the Velociraptor GUI search bar does:
client.search_clients(query: 'host:workstation')
client.search_clients(query: 'label:servers')Schedule a collection:
client.collect_artifact(
client_id: 'C.1234abcd',
artifacts: ['Generic.Client.Info']
)Schedule a collection, wait for completion, and read a result source:
client.collect_artifact_and_wait(
client_id: 'C.1234abcd',
artifacts: ['Generic.Client.Info'],
result_artifact: 'Generic.Client.Info/BasicInformation'
)Read flow results later:
client.flow_results(
client_id: 'C.1234abcd',
flow_id: 'F.5678efgh',
artifact: 'Generic.Client.Info/BasicInformation'
)Launch a hunt:
client.launch_hunt(
artifacts: ['Generic.Client.Info'],
description: 'inventory sweep'
)Read hunt results:
client.hunt_results(
hunt_id: 'H.1234abcd',
artifact: 'Generic.Client.Info/BasicInformation'
)Runner Reference
Query
query(vql:, env: {}, format: :jsonl, **opts)
Runs server-side VQL through:
velociraptor --api_config api.config.yaml query "<VQL>" --format jsonlReturns:
{ rows: [...], stderr: "..." }env is passed as Velociraptor VQL environment variables using repeated
--env Name=value arguments.
server_info(**opts)
Runs:
SELECT * FROM info()search_clients(query: nil, **opts)
Runs:
SELECT * FROM clients()
SELECT * FROM clients(search=ClientQuery)Use Velociraptor client search syntax such as host:... and label:....
Collections
collect_artifact(client_id:, artifacts:, env: {}, **opts)
Launches a Velociraptor flow using collect_client. Returns the collection
metadata emitted by Velociraptor.
collect_artifact_and_wait(client_id:, artifacts:, result_artifact:, env: {}, **opts)
Launches a collection, waits for System.Flow.Completion, then reads the named
result source with source(...).
This can block until the client returns. Prefer collect_artifact plus
flow_results for long-running or offline endpoint workflows.
flow_results(client_id:, flow_id:, artifact:, **opts)
Reads rows from a completed flow using Velociraptor's source(...) plugin.
cancel_flow(client_id:, flow_id:, **opts)
Cancels an outstanding flow.
Hunts
launch_hunt(artifacts:, description: nil, env: {}, **opts)
Creates a Velociraptor hunt. Velociraptor hunts created through VQL are active by default unless the VQL includes pause semantics.
hunt_results(hunt_id:, artifact:, **opts)
Reads rows from a hunt result source.
list_hunts(**opts)
Runs:
SELECT * FROM hunts()Data Handling
The helper parses jsonl output into Ruby hashes with string keys. Blank output
lines are ignored. Command failures raise:
Legion::Extensions::Velociraptor::Helpers::Cli::CommandErrorThe error object exposes:
exit_statusstderrstdout
Safety Boundaries
Velociraptor VQL is powerful. Treat this extension as a privileged DFIR control plane, not as a generic shell helper.
- Use least-privilege Velociraptor API roles.
- Store
api.config.yamlin a secrets-managed path. - Do not pass API config content through Legion prompts, queue payloads, or logs.
- Prefer VQL environment variables for dynamic values.
- Validate or constrain user-provided artifact names, client IDs, flow IDs, and hunt IDs before exposing workflows to untrusted callers.
- Use asynchronous collection patterns for clients that may be offline.
The extension validates common Velociraptor identifiers before interpolating
them into generated VQL and passes dynamic query values through --env where
practical.
Development
Run the full suite:
bundle exec rspec --format json --out tmp/rspec_results.json --format progress --out tmp/rspec_progress.txtRun style checks:
bundle exec rubocop -AProject Links
- LegionIO: https://github.com/LegionIO/LegionIO
- Velociraptor docs: https://docs.velociraptor.app/
- Velociraptor source: https://github.com/Velocidex/velociraptor
License
MIT