description: Manage Linear issues, projects, and teams via the GraphQL API. Create, update, search, and organize issues. Uses API key auth (no OAuth needed). All operations via curl — no dependencies.
- **Auth header:** `Authorization: $LINEAR_API_KEY` (no "Bearer" prefix for API keys)
- **All requests are POST** with `Content-Type: application/json`
- **Both UUIDs and short identifiers** (e.g., `ENG-123`) work for `issue(id:)`
Base curl pattern:
```bash
curl -s -X POST https://api.linear.app/graphql \
-H "Authorization: $LINEAR_API_KEY"\
-H "Content-Type: application/json"\
-d '{"query": "{ viewer { id name } }"}'| python3 -m json.tool
```
## Workflow States
Linear uses `WorkflowState` objects with a `type` field. **6 state types:**
| Type | Description |
|------|-------------|
| `triage` | Incoming issues needing review |
| `backlog` | Acknowledged but not yet planned |
| `unstarted` | Planned/ready but not started |
| `started` | Actively being worked on |
| `completed` | Done |
| `canceled` | Won't do |
Each team has its own named states (e.g., "In Progress" is type `started`). To change an issue's status, you need the `stateId` (UUID) of the target state — query workflow states first.
-d '{"query": "{ viewer { id name email } }"}'| python3 -m json.tool
```
### List teams
```bash
curl -s -X POST https://api.linear.app/graphql \
-H "Authorization: $LINEAR_API_KEY"\
-H "Content-Type: application/json"\
-d '{"query": "{ teams { nodes { id name key } } }"}'| python3 -m json.tool
```
### List workflow states for a team
```bash
curl -s -X POST https://api.linear.app/graphql \
-H "Authorization: $LINEAR_API_KEY"\
-H "Content-Type: application/json"\
-d '{"query": "{ workflowStates(filter: { team: { key: { eq: \"ENG\" } } }) { nodes { id name type } } }"}'| python3 -m json.tool
```
### List issues (first 20)
```bash
curl -s -X POST https://api.linear.app/graphql \
-H "Authorization: $LINEAR_API_KEY"\
-H "Content-Type: application/json"\
-d '{"query": "{ issues(first: 20) { nodes { identifier title priority state { name type } assignee { name } team { key } url } pageInfo { hasNextPage endCursor } } }"}'| python3 -m json.tool
```
### List my assigned issues
```bash
curl -s -X POST https://api.linear.app/graphql \
-H "Authorization: $LINEAR_API_KEY"\
-H "Content-Type: application/json"\
-d '{"query": "{ viewer { assignedIssues(first: 25) { nodes { identifier title state { name type } priority url } } } }"}'| python3 -m json.tool
```
### Get a single issue (by identifier like ENG-123)
```bash
curl -s -X POST https://api.linear.app/graphql \
-H "Authorization: $LINEAR_API_KEY"\
-H "Content-Type: application/json"\
-d '{"query": "{ issue(id: \"ENG-123\") { id identifier title description priority state { id name type } assignee { id name } team { key } project { name } labels { nodes { name } } comments { nodes { body user { name } createdAt } } url } }"}'| python3 -m json.tool
```
### Search issues by text
```bash
curl -s -X POST https://api.linear.app/graphql \
-H "Authorization: $LINEAR_API_KEY"\
-H "Content-Type: application/json"\
-d '{"query": "{ issueSearch(query: \"bug login\", first: 10) { nodes { identifier title state { name } assignee { name } url } } }"}'| python3 -m json.tool
```
### Filter issues by state type
```bash
curl -s -X POST https://api.linear.app/graphql \
-H "Authorization: $LINEAR_API_KEY"\
-H "Content-Type: application/json"\
-d '{"query": "{ issues(filter: { state: { type: { in: [\"started\"] } } }, first: 20) { nodes { identifier title state { name } assignee { name } } } }"}'| python3 -m json.tool