بنقرة واحدة
linear
// Linear issue tracker API integration. Covers first-use identity bootstrap (viewer + teams cached), raw GraphQL for list/search/create/update, and the rules for handling "my issues" / "assigned to me" requests.
// Linear issue tracker API integration. Covers first-use identity bootstrap (viewer + teams cached), raw GraphQL for list/search/create/update, and the rules for handling "my issues" / "assigned to me" requests.
One-time onboarding for the executive/manager commitment workflow — delegation-heavy, meeting prep, decision capture, morning and evening digests. Creates a `commitments` project and installs two dashboard widgets. After successful setup this skill is excluded from selection until the marker file is deleted.
Compose and deliver summaries of open commitments, deadlines, pending signals, and resolution suggestions.
One-time setup for the commitments tracking system. Creates workspace structure, schema docs, and installs triage and digest missions. Excluded from activation once `projects/commitments/README.md` exists in the workspace (the file this skill writes as its first step).
Recognize obligations in conversation, extract signals with immediacy and expiration, create and manage commitments in the workspace.
One-time onboarding for the content creator workflow — content pipeline stages, trend expiration, cross-platform cascades, heavy idea parking. After successful setup this skill is excluded from selection until the marker file is deleted.
Detect decisions in conversation and record them with rationale, alternatives, and outcome tracking.
| name | linear |
| version | 1.2.0 |
| description | Linear issue tracker API integration. Covers first-use identity bootstrap (viewer + teams cached), raw GraphQL for list/search/create/update, and the rules for handling "my issues" / "assigned to me" requests. |
| activation | {"keywords":["linear","my linear","linear issue","linear issues","linear ticket","linear tickets","linear backlog","linear assignments","my linear issues","my linear tickets","assigned in linear","linear.app"],"exclude_keywords":["jira","asana","github issue"],"patterns":["(?i)linear\\.(?:app|com)","(?i)\\blinear\\b.+(issue|ticket|task|backlog|board)","(?i)(create|show|list|close|update).+linear\\s+(issue|ticket)"],"tags":["project-management","issue-tracking"],"max_context_tokens":1600} |
| credentials | [{"name":"linear_api_key","provider":"linear","location":{"type":"header","name":"Authorization"},"hosts":["api.linear.app"],"setup_instructions":"Create an API key at https://linear.app/settings/api"}] |
You have access to the Linear GraphQL API via the http tool. Credentials are automatically injected — never construct Authorization headers manually. When the URL host is api.linear.app, the system injects Authorization: {linear_api_key} transparently (no Bearer prefix — Linear API keys are sent raw).
Linear's API key does not tell you who the user IS inside Linear. Before running any "my issues" / "assigned to me" / "my tickets" request, make sure the user's Linear identity is cached. This avoids re-fetching viewer on every request and makes filter-by-assignee queries deterministic.
Path: context/intel/linear-identity.md
Shape:
---
type: linear-identity
bootstrapped_at: 2026-04-21
refreshed_at: 2026-04-21
stale_after: 2026-05-21
---
# Linear identity
user_id: 8a7f...-uuid
display_name: Tobias Holenstein
email: tobias@...
timezone: Europe/Zurich
## Teams
- id: team-uuid-a, key: ENG, name: Engineering
- id: team-uuid-b, key: PROD, name: Product
## Default team
ENG
memory_read("context/intel/linear-identity.md"). If the file exists and stale_after is in the future, use it and stop.query { viewer { id name displayName email } teams(first: 50) { nodes { id key name } } }
memory_write with stale_after = today + 30 days.Default team. If more than one, ask the user once: "I see teams ENG, PROD, OPS. Which one do you default to for new issues?" and store the answer.AuthenticationError GraphQL error, invalidate the cache and re-prompt the user to check their API key — do not silently retry.assignee: { id: { eq: "<cached user_id>" } }, not by assignee: { isMe: true } (the isMe filter is not universally available and viewer round-trips are wasteful).Default team id without asking.Linear uses a single GraphQL endpoint: https://api.linear.app/graphql
All requests are POST with a JSON body containing query and optional variables.
http(method="POST", url="https://api.linear.app/graphql", body={"query": "{ issues(first: 20, orderBy: updatedAt) { nodes { id identifier title state { name } assignee { name } priority priorityLabel createdAt } } }"})
http(method="POST", url="https://api.linear.app/graphql", body={"query": "query($uid: ID!) { issues(filter: { assignee: { id: { eq: $uid } }, state: { type: { nin: [completed, canceled] } } }, first: 50, orderBy: updatedAt) { nodes { id identifier title state { name type } priority priorityLabel url updatedAt } } }", "variables": {"uid": "<cached user_id>"}})
Never pass viewer.id inline from a fresh round-trip when the cache is valid — consult context/intel/linear-identity.md.
http(method="POST", url="https://api.linear.app/graphql", body={"query": "query($id: String!) { issue(id: $id) { id identifier title description state { name } assignee { name } labels { nodes { name } } comments { nodes { body user { name } createdAt } } } }", "variables": {"id": "ISSUE_ID"}})
http(method="POST", url="https://api.linear.app/graphql", body={"query": "query($term: String!) { issueSearch(query: $term, first: 10) { nodes { id identifier title state { name } priorityLabel } } }", "variables": {"term": "SEARCH_TERM"}})
http(method="POST", url="https://api.linear.app/graphql", body={"query": "mutation($input: IssueCreateInput!) { issueCreate(input: $input) { success issue { id identifier title url } } }", "variables": {"input": {"title": "...", "description": "...", "teamId": "TEAM_ID", "priority": 2}}})
http(method="POST", url="https://api.linear.app/graphql", body={"query": "{ teams { nodes { id name key } } }"})
http(method="POST", url="https://api.linear.app/graphql", body={"query": "mutation($id: String!, $stateId: String!) { issueUpdate(id: $id, input: { stateId: $stateId }) { success issue { id identifier title state { name } } } }", "variables": {"id": "ISSUE_UUID", "stateId": "STATE_UUID"}})
{"data": {...}} on success, {"errors": [...]} on failure.ENG-123 (team key + number).errors in the response before processing data.message and optional extensions with error codes.Authorization header — it is injected automatically.POST method — Linear's API is GraphQL only.id field is a UUID, the identifier field is human-readable (e.g., ENG-42).issueSearch for text search, not issues with a filter (text search is separate).teamId. List teams first if unknown.