Linear is the project management tool that developers actually like using. Fast, keyboard-driven, opinionated about workflow. The API follows the same philosophy: clean GraphQL, consistent conventions, and almost no gotchas.
Almost.
This guide covers the complete OpenClaw-Linear integration: API key setup, label-based triage automation, auto-linking to GitHub PRs, and the daily standup digest that saves 10 minutes every morning.
API Key Setup
Linear uses API keys for personal access and OAuth for team applications. For OpenClaw, use a personal API key unless you’re setting this up for a shared team workflow.
Generate an API key:
- Go to Linear → Settings → Security & Access → Personal API Keys
- Click Create key
- Name it “OpenClaw”
- Copy the key immediately — Linear only shows it once
# OpenClaw config
linear_api_key: "lin_api_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
Or environment variable:
export LINEAR_API_KEY="lin_api_xxxx..."
Verify the connection:
@openclaw check linear connection
Expected: “Linear connected. Found X teams: [team names].”
Linear’s API base URL is https://api.linear.app/graphql. Everything is GraphQL — there are no REST endpoints. If you’re building custom skills, every request is a POST to that URL with a GraphQL query in the body and your API key in the Authorization header.
Understanding Linear’s Data Model
Before building automations, the data model matters:
- Organization — your workspace
- Teams — groups within the organization (Engineering, Design, etc.)
- Projects — collections of issues with a goal and timeline
- Issues — individual work items (have states, labels, assignees, priorities)
- Cycles — sprints (time-boxed, optional)
- Comments — on issues
The hierarchy: Organization → Teams → Projects/Cycles → Issues → Comments.
Issues have states (not just “open/closed”). States are team-specific and configurable: Todo, In Progress, In Review, Done, Cancelled are common, but teams customize these. When automating, always fetch the team’s actual states rather than assuming names.
Reading Issues: Queries That Actually Work
Fetch Issues for a Team
@openclaw show me all open issues in the Engineering team
GraphQL query behind this:
query {
issues(
filter: {
team: { key: { eq: "ENG" } }
state: { type: { in: ["triage", "backlog", "started", "unstarted"] } }
}
orderBy: updatedAt
) {
nodes {
id
title
state { name }
priority
assignee { name }
labels { nodes { name color } }
createdAt
updatedAt
}
}
}
Priority values in Linear’s API:
- 0 = No priority
- 1 = Urgent
- 2 = High
- 3 = Medium
- 4 = Low
When filtering by priority in automations, use these integers, not string names.
Fetch Issues Assigned to Me
@openclaw what are my open Linear issues?
query {
viewer {
assignedIssues(
filter: {
state: { type: { notIn: ["completed", "cancelled"] } }
}
) {
nodes {
id
title
priority
state { name }
team { name }
dueDate
}
}
}
}
Search Issues
@openclaw find Linear issues mentioning "authentication bug"
query {
issueSearch(
query: "authentication bug"
filter: {
state: { type: { notIn: ["completed", "cancelled"] } }
}
) {
nodes {
id
title
team { name }
state { name }
}
}
}
Label-Based Triage: The Core Automation
Label-based triage is where OpenClaw earns its keep in a Linear workflow. Instead of manually reviewing new issues and categorizing them, OpenClaw can do it automatically.
The Triage Workflow
@openclaw triage all issues in the Triage state for Engineering team
What OpenClaw does:
- Fetches all issues in the “Triage” state
- Reads each issue title, description, and any existing labels
- Based on content analysis:
- Sets priority (Urgent/High/Medium/Low)
- Adds labels (Bug, Feature, Improvement, Question, Documentation)
- Assigns to team members based on keywords and ownership patterns
- Moves to appropriate state (Backlog or directly to In Progress for urgent items)
- Adds a triage comment explaining its reasoning
Setting Up Triage Rules
Configure triage rules in your OpenClaw skill config:
linear_triage_rules:
labels:
Bug:
keywords: ["error", "crash", "broken", "not working", "fails", "exception", "500", "null pointer"]
priority: high
Security:
keywords: ["vulnerability", "CVE", "SQL injection", "XSS", "auth bypass", "exposed"]
priority: urgent
Performance:
keywords: ["slow", "timeout", "latency", "memory leak", "CPU", "optimization"]
priority: medium
assignments:
- if_label: Security
assign_to: "[email protected]"
- if_label: Bug
if_mentions: ["payment", "billing", "invoice"]
assign_to: "[email protected]"
Running Triage Automatically
The most useful pattern: run triage on a schedule.
@openclaw every morning at 9am, triage new issues added to Engineering Triage since yesterday
OpenClaw sets up the scheduled job. Every morning it:
- Fetches issues created since yesterday with no labels
- Applies triage rules
- Sends you a summary: “Triaged 7 issues: 2 Urgent, 3 High, 2 Medium”
Manual Triage Override
Automations make mistakes. When OpenClaw mis-labels an issue:
@openclaw that issue #ENG-341 isn't a bug, it's a feature request, update it
OpenClaw updates the label via API and adjusts its triage model to improve future classifications.
Auto-Linking to GitHub PRs
This is the integration most Linear+GitHub teams want and not enough people set up.
How Linear-GitHub Linking Works
Linear has native GitHub integration, but it requires GitHub access in Linear’s settings. There’s also an API approach that works regardless:
Option 1: Linear’s native GitHub integration
In Linear: Settings → Integrations → GitHub → Connect
This automatically links PRs to issues when the PR title or branch contains the issue identifier (e.g., ENG-341).
Option 2: OpenClaw as the bridge
If you want more control or the native integration isn’t available:
@openclaw link PR #847 in github.com/org/repo to Linear issue ENG-341
OpenClaw:
- Fetches PR details from GitHub API
- Creates an attachment on the Linear issue linking to the PR
- Adds a comment to the Linear issue with PR status
- Optionally moves the Linear issue to “In Review” state
The Branch Naming Convention
The simplest auto-linking approach: require branch names to include the Linear issue ID.
# Good branch names that auto-link
feat/ENG-341-user-auth-redesign
fix/ENG-292-payment-null-pointer
chore/ENG-400-update-dependencies
When OpenClaw monitors your GitHub repo for new PRs, it extracts the Linear issue ID from the branch name and links them automatically.
PR Status → Linear State Updates
# OpenClaw config: PR events → Linear state changes
github_to_linear_state_map:
pr_opened: "In Review"
pr_merged: "Done"
pr_closed_unmerged: "Cancelled"
pr_review_requested: "In Review"
When a PR is merged:
@openclaw a PR was merged for ENG-341, update Linear accordingly
OpenClaw moves the Linear issue to Done, adds the PR merge link as a comment, and closes any related sub-issues.
The Daily Standup Digest
This is the highest-value, lowest-effort automation for Linear users.
Setup
@openclaw every weekday at 8:45am, generate my standup digest
OpenClaw fetches:
- Issues you completed yesterday (moved to Done)
- Issues currently In Progress
- Issues blocked (waiting on someone else)
- Issues due this week
Output:
? Standup Digest — Tuesday, May 19, 2026
✅ DONE YESTERDAY
• ENG-341: User auth redesign — merged to main
• ENG-329: Fix payment null pointer — deployed to staging
? IN PROGRESS
• ENG-355: API rate limiting — implementation 60% done, PR tomorrow
• ENG-360: Dashboard performance — blocked on design review
⏳ BLOCKED
• ENG-360: Waiting for design approval from @sarah
? DUE THIS WEEK
• ENG-371: Migration script (due Thursday)
• ENG-380: Security audit response (due Friday)
You can paste this directly into Slack, edit as needed, and you’re done.
Team Standup Digest
If you run standups for a team:
@openclaw generate the Engineering team standup for today
OpenClaw groups the digest by assignee, giving you a per-person view across the team. Each person’s section shows what they completed, what they’re working on, and what’s blocked.
Sprint Planning Automation
Capacity Planning
@openclaw how much capacity does the Engineering team have for the next cycle?
OpenClaw:
- Fetches the current cycle’s completion rate (points completed / points committed)
- Fetches team members’ current issue load
- Calculates available capacity for the next cycle based on historical velocity
This is useful as a sanity check before committing to a sprint.
Issue Prioritization for Sprint
@openclaw help me fill the next Engineering cycle with high-priority backlog issues
OpenClaw:
- Fetches unassigned backlog issues sorted by priority
- Estimates effort based on issue descriptions (if estimates are in the description or comments)
- Suggests a set of issues that fits the team’s average velocity
- Explains its reasoning for each selection
Velocity Reporting
@openclaw what's the Engineering team's velocity for the last 4 cycles?
query {
cycles(
filter: { team: { key: { eq: "ENG" } } }
orderBy: createdAt
last: 4
) {
nodes {
number
startsAt
endsAt
completedAt
issues {
nodes {
estimate
state { type }
}
}
}
}
}
OpenClaw calculates points completed per cycle and surfaces the trend.
Roadmap and Project Tracking
Project Status Summary
@openclaw summarize the status of the "Mobile Redesign" project
OpenClaw fetches the project and its issues, calculates completion percentage, identifies blockers, and highlights overdue items.
Cross-Team Dependencies
@openclaw find issues in the Mobile project that are blocked on Backend team issues
OpenClaw searches for issues with “blocked” labels or comments mentioning blockers, cross-references with other teams’ issue lists, and surfaces dependency chains.
Webhooks vs. Polling: A Practical Note
Linear supports webhooks for real-time events. For automations that need to react immediately (like auto-triaging new issues the moment they’re created), webhooks are better than polling.
Setting up Linear webhooks:
In Linear: Settings → API → Webhooks → Create webhook
Point it to your OpenClaw server’s webhook endpoint. Linear sends events for issue creation, updates, state changes, and comment additions.
The polling alternative: For most personal use, polling every 5-15 minutes is good enough. The standup digest doesn’t need real-time data. Triage can run on a 15-minute polling cycle without meaningful delay. Only automated workflows that need to react within seconds (like auto-assigning urgent issues) need webhooks.
PaioClaw handles webhook receipt and routing without requiring you to expose a public endpoint — it manages the webhook receiver and forwards events to your OpenClaw instance.
Common Linear API Patterns
Get team ID by key:
query { team(key: "ENG") { id name } }
Get states for a team:
query { team(key: "ENG") { states { nodes { id name type } } } }
Create an issue:
mutation {
issueCreate(input: {
teamId: "team-id"
title: "Issue title"
description: "Description in markdown"
priority: 2
labelIds: ["label-id"]
}) {
issue { id identifier title }
}
}
Update issue state:
mutation {
issueUpdate(id: "issue-id", input: { stateId: "state-id" }) {
issue { id state { name } }
}
}
Add comment:
mutation {
commentCreate(input: {
issueId: "issue-id"
body: "Comment in markdown"
}) {
comment { id }
}
}
Error Handling
| Error | Cause | Fix |
|---|---|---|
UNAUTHENTICATED | Invalid or missing API key | Regenerate API key in Linear settings |
FORBIDDEN | Key lacks permission for the operation | Check key scope in Linear settings |
NOT_FOUND | Invalid issue/team ID | Verify ID by fetching the resource first |
| Rate limit (429) | Too many requests | Linear allows ~1,500 requests/hour; add delays |
GRAPHQL_PARSE_FAILED | Malformed query | Validate query in Linear’s GraphQL playground |
PaioClaw vs. Self-Hosted
The Linear API is one of the cleanest to work with. Self-hosting the integration is genuinely viable.
Where PaioClaw adds value:
Webhook management: Receiving webhooks requires a public HTTPS endpoint. PaioClaw provides this, so you get real-time triage without running a server.
Cross-tool workflows: The standup digest is more useful if it combines Linear data with GitHub PR status, Slack messages, and calendar events. PaioClaw orchestrates cross-tool workflows without custom code.
Team sharing: If multiple team members want to run standup digests and triage automations, PaioClaw handles multi-user API key management. Self-hosting requires each person to configure their own instance.
PaioClaw starts free, with Smart at $15/mo and Genius at $25/mo.
Summary
Linear’s GraphQL API is clean, well-documented, and consistent. The main gotchas: state names are team-specific (always fetch them rather than assuming), priority is an integer (not a string), and the branch naming convention (TEAM-123 in branch names) is the simplest path to auto-linking PRs.
The two highest-value automations are label-based triage (saves 20-30 minutes of manual triage per week) and the daily standup digest (saves 10 minutes every morning). Set those up first. Sprint planning automation and velocity reporting are useful but optional — add them once the core automations are running reliably.

