# EVA CLI **LLM-ready financial data for AI agents and automation.** [![CI](https://github.com/xiaochaohit/evatick-cli/actions/workflows/ci.yml/badge.svg)](https://github.com/xiaochaohit/evatick-cli/actions/workflows/ci.yml) [![npm CLI](https://img.shields.io/npm/v/@evatick/cli?label=npm%20CLI&logo=npm)](https://www.npmjs.com/package/@evatick/cli) [![npm Skill](https://img.shields.io/npm/v/@evatick/skill?label=npm%20Skill&logo=npm)](https://www.npmjs.com/package/@evatick/skill) [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](LICENSE) [![Python](https://img.shields.io/badge/Python-3.11--3.14-3776AB?logo=python&logoColor=white)](https://www.python.org/) [简体中文](README.md) · English
EVA CLI gives large language models a stable command-line interface for discovering financial instruments and querying normalized market data through the versioned EVA HTTP API. Canonical identifiers, consistent JSON responses, explicit errors, and deterministic commands make financial data easier for models to understand, compose, and use without relying on provider-specific conventions. The current release covers mainland China A-shares and indices published by the Shanghai Stock Exchange, Shenzhen Stock Exchange, and China Securities Index. ![Codex queries Ping An Bank market data through EVA Tick](docs/assets/eva-tick-codex-demo.gif) *Codex selects the EVA commands from a natural-language request, resolves the canonical instrument, and queries bars. Commands and values were verified against a local EVA Tick service; the service address and credentials are hidden.* ## Why EVA CLI? - **Built for LLMs and AI agents** — predictable schemas, canonical identifiers, and structured errors reduce ambiguity and avoid parsing presentation-oriented text. - **One stable interface** — work with canonical instruments instead of provider-specific function names and identifiers. - **Automation-friendly output** — successful results are emitted as compact JSON; errors are structured JSON on standard error. - **Explicit instrument resolution** — search, inspect, and resolve ambiguous codes before requesting data. - **Resilient requests** — configure total timeouts and retries for transient service or network failures. - **Safe file exports** — export JSON, JSONL, CSV, or Parquet without silently overwriting existing files. - **Small client footprint** — the npm CLI uses only Node.js standard-library APIs; the Python distribution depends only on Click by default. > [!IMPORTANT] > EVA CLI is the client only. Market data is supplied by a running [EVA service](https://github.com/xiaochaohit/evatick-server); the service and its OpenAPI contract live in a separate repository. ## Quick start ### Recommended: install with npm For most users, npm is the recommended installation method. It installs the pure Node.js CLI, so Python and platform-specific native executables are not required. Choose the package that matches your use case: | Use case | What gets installed | Command | | --- | --- | --- | | Use EVA in a terminal, script, or another agent | CLI only | `npm install --global @evatick/cli` | | Use EVA in Codex | Skill and the matching CLI | `npm install --global @evatick/skill` | For the CLI only: ```shell npm install --global @evatick/cli eva version ``` For Codex, install the Skill. `@evatick/skill` automatically installs the matching CLI version, so you do not need to install `@evatick/cli` separately: ```shell npm install --global @evatick/skill eva-skill install eva version ``` Restart Codex after installing or updating the Skill. Run `eva-skill status` to check the installation. For temporary CLI use, you can also run `npx @evatick/cli health`. > [!NOTE] > npm installation requires Node.js 18 or newer and access to an EVA service. The > npm distribution supports JSON, JSONL, and CSV exports. For Parquet, use the > Python developer installation below. ### Developers: install from Python source This path is intended for contributors, source-level debugging, or users who need the optional Parquet dependency. Most users should choose npm above. A source installation requires 64-bit CPython 3.11–3.14. ```shell git clone https://github.com/xiaochaohit/evatick-cli.git cd evatick-cli python -m pip install . eva version ``` To enable Parquet exports: ```shell python -m pip install '.[parquet]' ``` ### Connect to EVA The client connects to the hosted service at `https://api.evatick.com` by default. To use another EVA service, override the service URL: ```shell eva config set --base-url https://api.example.com eva config show eva health ``` The API key is optional. If the service requires authentication, save it with `eva config set --api-key 'eva_...'`. Without a configured key, the client omits the `Authorization` header. When a key is configured, the client sends it as usual, so an open-access service can accept requests with or without a key. `eva config show` masks the stored API key. On macOS and Linux, EVA also requires the configuration file to be readable only by its owner. ### Make your first query ```shell # Find a stock by name. eva instrument search --query 平安银行 --type equity # Resolve a trading code to one canonical instrument. eva instrument resolve --query 000001 --type equity # Query its latest quote and daily bars. eva stock quotes --symbol 000001 eva stock bars --symbol 000001 --start 2026-08-01 --limit 5 ``` ## Command overview | Command | Purpose | | --- | --- | | `eva health` | Check EVA service health | | `eva version` | Show CLI, API contract, and current CLI runtime versions | | `eva config set` | Save a service URL or API key | | `eva config show` | Show the active configuration with a masked key | | `eva instrument list` | List canonical instruments with optional filters | | `eva instrument search` | Search instruments by name, identifier, or alias | | `eva instrument resolve` | Resolve user input to a canonical instrument | | `eva instrument show` | Inspect a canonical instrument by ID | | `eva stock quotes` | Query the latest A-share quote | | `eva stock bars` | Query A-share OHLCV bars | | `eva index quotes` | Query the latest index quote | | `eva index bars` | Query index OHLCV bars | | `eva index constituents` | Query index constituents for an optional effective date | Run `eva COMMAND --help` or `eva GROUP COMMAND --help` for all supported options. ## Usage examples ### Discover instruments ```shell eva instrument list --type equity --venue XSHE --limit 20 eva instrument search --query 000300 --type index eva instrument show --id cn:index:CSI:000300 ``` ### Query market data ```shell eva stock quotes --symbol 600000 eva stock bars --symbol 000001 \ --interval 1d \ --start 2026-01-01 \ --end 2026-06-30 \ --adjustment forward eva index bars --symbol 000300 \ --interval 15m \ --start 2026-08-14 \ --end 2026-08-14 eva index constituents --symbol 000300 --as-of 2026-08-15 --limit 20 ``` Supported bar intervals are `1m`, `5m`, `15m`, `30m`, `60m`, `1d`, `1w`, and `1mo`. Adjustment modes are `none`, `forward`, and `backward`. ### Export results Sequence results can be exported as JSON, JSONL, CSV, or Parquet: ```shell eva stock bars --symbol 000001 \ --start 2026-01-01 \ --output bars.csv \ --format csv ``` The format is inferred from a recognized file extension when `--format` is omitted. Use `--overwrite` to replace an existing regular file and `--limit` to keep only the first N records. CSV requires flat records with consistent fields; Parquet requires the optional `evatick[parquet]` dependency. ## Configuration Configuration precedence is explicit and predictable: ```text command-line option > environment variable > configuration file > built-in default ``` | Setting | Command-line option | Environment variable | Default | | --- | --- | --- | --- | | Configuration file | `--config PATH` | `EVA_CONFIG` | `~/.config/eva/config.json` on macOS/Linux | | Service URL | `--server-url URL` | `EVA_SERVER_URL` | `https://api.evatick.com` | | API key (optional) | `--api-key KEY` | `EVA_API_KEY` | Not set | Use environment variables for temporary overrides and secret injection in CI: ```shell EVA_SERVER_URL=https://api.example.com \ EVA_API_KEY="$EVA_CI_API_KEY" \ eva health ``` Do not commit configuration files containing real API keys. ## Scripting and errors EVA keeps machine-readable data separate from diagnostics: - successful results: compact JSON on standard output, exit code `0`; - invalid arguments: structured JSON on standard error, exit code `2`; - service, configuration, or serialization failures: structured JSON on standard error, exit code `1`. An error includes a stable code, a message, and whether retrying may succeed: ```json {"code":"SERVER_UNAVAILABLE","message":"EVA service is unavailable","retryable":true} ``` This makes the CLI safe to compose with tools such as `jq`: ```shell eva instrument search --query 平安银行 --type equity | jq '.[0].instrument_id' ``` ## Development ```shell git clone https://github.com/xiaochaohit/evatick-cli.git cd evatick-cli python -m venv .venv source .venv/bin/activate # Windows PowerShell: .venv\Scripts\Activate.ps1 python -m pip install -e '.[test,parquet]' python -m pytest -q python -m build ``` CI tests Python 3.11–3.14 across Linux, macOS, and Windows, and validates the npm CLI on the minimum supported Node.js 18 runtime. Architectural decisions and compatibility rules are documented in [`docs/adr`](docs/adr). Contributions are welcome. Please open an issue before proposing a major behavior or contract change, keep changes focused, and include tests for user-visible behavior. ## License EVA CLI is available under the [MIT License](LICENSE). Third-party attributions are listed in [THIRD_PARTY_NOTICES.md](THIRD_PARTY_NOTICES.md). Market data is provided for research and reference only and does not constitute investment advice.