jira-cli 0.3.1

Agent-friendly Jira CLI with JSON output, structured exit codes, and schema introspection
Documentation

jira

CI

An agent-friendly Jira CLI for Jira Cloud and Jira Data Center / Server.

  • Auto-JSON when stdout is not a TTY — pipe it anywhere, get structured data
  • jira schema dumps every command, flag, and JSON shape as machine-readable JSON for agent introspection
  • Structured exit codes — agents can branch on auth failures, rate limits, not-found, and input errors without parsing text
  • Clean stdout/stderr split — data on stdout, messages on stderr, --quiet suppresses all non-data output
$ jira issues list --project MYAPP --status "In Progress"
KEY          SUMMARY                        STATUS       ASSIGNEE
MYAPP-42     Fix login redirect loop        In Progress  Alice
MYAPP-38     Update password reset flow     In Progress  Bob

$ jira issues list --project MYAPP --json
{"total": 2, "issues": [...]}

Installation

cargo install jira-cli

Or build from source:

git clone https://github.com/rvben/jira-cli
cd jira-cli
make install          # runs check + release build, copies to ~/.local/bin/jira

Configuration

Run jira init for a guided setup, or create the config file manually.

Default locations:

Platform Path
Linux / macOS ~/.config/jira/config.toml (or $XDG_CONFIG_HOME/jira/config.toml)
[default]
host  = "mycompany.atlassian.net"
email = "me@example.com"
token = "your-api-token"

Get a Jira Cloud API token at: https://id.atlassian.com/manage-profile/security/api-tokens

chmod 600 ~/.config/jira/config.toml

Run jira config show to confirm the resolved path and active credentials (token is masked).

Environment variables

All credentials can be set via environment variables — useful for CI and scripts:

Variable Description
JIRA_HOST Atlassian domain (e.g. mycompany.atlassian.net)
JIRA_EMAIL Account email
JIRA_TOKEN API token or Personal Access Token
JIRA_PROFILE Config profile name
JIRA_AUTH_TYPE basic (default) or pat
JIRA_API_VERSION 3 (Cloud, default) or 2 (Data Center / Server)

Multiple profiles

[default]
host  = "mycompany.atlassian.net"
email = "me@example.com"
token = "cloud-token"

[profiles.dc]
host        = "jira.corp.com"
token       = "personal-access-token"
auth_type   = "pat"
api_version = 2

Switch with --profile dc or JIRA_PROFILE=dc jira <command>.

Jira Data Center / Server (PAT auth)

Data Center uses Personal Access Tokens instead of email + API token:

[default]
host        = "jira.corp.com"
token       = "your-personal-access-token"
auth_type   = "pat"
api_version = 2

Email is not required for PAT auth. Get your token at: https://<your-host>/secure/ViewProfile.jspa?selectedTab=com.atlassian.pats.pats-plugin:jira-user-personal-access-tokens

Usage

Issues

# List
jira issues list
jira issues list --project MYAPP --status "In Progress"
jira issues list --project MYAPP --type Bug --assignee me
jira issues list --sprint active
jira issues list --all                        # fetch every page

# Assigned to you
jira issues mine
jira issues mine --project MYAPP --status "To Do"

# Show
jira issues show MYAPP-123

# Create
jira issues create --project MYAPP --summary "Fix login bug" --type Bug
jira issues create --project MYAPP --summary "Add dark mode" --type Story \
  --description "Users want a dark mode option." --priority High --assignee me
jira issues create --project MYAPP --summary "Write unit tests" \
  --parent MYAPP-42                           # creates a subtask

# Update
jira issues update MYAPP-123 --summary "Updated title"
jira issues update MYAPP-123 --priority Low --assignee me
jira issues update MYAPP-123 --field customfield_10016=5

# Transition
jira issues list-transitions MYAPP-123
jira issues transition MYAPP-123 --to "In Review"

# Assign
jira issues assign MYAPP-123 --assignee me
jira issues assign MYAPP-123 --assignee user@example.com

# Comment
jira issues comment MYAPP-123 --body "Deployed to staging."
jira issues comments MYAPP-123

# Log work
jira issues log-work MYAPP-123 --time-spent 2h
jira issues log-work MYAPP-123 --time-spent 30m --comment "Fixed the flaky test"

# Links
jira issues link-types
jira issues link MYAPP-123 --to MYAPP-456 --type "Blocks"
jira issues unlink <link-id>

# Move to sprint
jira issues move MYAPP-123 --sprint active
jira issues move MYAPP-123 --sprint "Sprint 14"

# Bulk operations (use --dry-run to preview)
jira issues bulk-transition --jql 'project = MYAPP AND status = "To Do"' --to "In Progress"
jira issues bulk-transition --jql 'project = MYAPP AND status = "To Do"' --to "In Progress" --dry-run
jira issues bulk-assign --jql 'project = MYAPP AND sprint in openSprints()' --assignee me

Projects

jira projects list
jira projects show MYAPP

Search

jira search 'project = MYAPP AND sprint in openSprints() ORDER BY priority'
jira search 'assignee = currentUser() AND status != Done' --limit 20
jira search 'project = MYAPP' --all                       # fetch every page

Boards and sprints

jira boards list
jira sprints list
jira sprints list --board "MYAPP board"

Users and fields

jira users search --query "alice"
jira fields list
jira fields list --custom                     # custom fields only

Shell completions

# Install automatically (bash, zsh, fish)
jira completions bash --install
jira completions zsh --install
jira completions fish --install

# Or redirect manually
jira completions zsh > ~/.zsh/completions/_jira

Config

jira init                    # setup guide with example config and token URLs
jira config show             # resolved credentials (token masked)
jira config init             # same as jira init

Agent use

jira schema returns a complete, machine-readable description of all commands, flags, JSON output shapes, auth requirements, and exit codes. AI agents should call this once at the start of a session instead of relying on help text.

jira schema | jq '.commands[] | .name'
jira schema | jq '.commands[] | select(.name == "issues list")'

Exit codes

Code Meaning
0 Success
1 Unexpected error
2 Bad input or config error
3 Authentication failed
4 Resource not found
5 Jira API error
6 Rate limited

Output flags

Flag Effect
--json Force JSON output (auto when stdout is not a TTY)
--quiet Suppress counts, confirmations, and status messages

Both flags are available on every command.

Development

make build          # debug build
make check          # fmt check + clippy + tests (run before committing)
make test           # unit + integration tests (wiremock, no real Jira needed)
make lint           # fmt check + clippy
make fmt            # auto-format
make install        # check + release build + copy to ~/.local/bin/jira

Running e2e tests

The e2e test suite runs against a real Jira instance. A Jira Data Center instance is required (Data Center license needed):

make jira-start     # start local Jira via Docker
make jira-wait      # wait until Jira is ready (~2 min on first run)

JIRA_E2E_HOST=http://localhost:8080 \
JIRA_E2E_EMAIL=admin \
JIRA_E2E_TOKEN=mytoken \
JIRA_E2E_PROJECT=TST \
  make test-e2e

make jira-stop

All e2e tests tag created issues with [e2e-auto] for easy cleanup.

CI

GitHub Actions runs fmt → clippy → nextest on Ubuntu and macOS for every push and pull request. The workflow is at .github/workflows/ci.yml.

License

MIT