mastra-ai/mastra · error

Linear did not accept the issue update.

Error message

Linear did not accept the issue update.

What it means

LinearIntegration throws this when Linear's GraphQL `issueUpdate` mutation completes but reports `success: false`, meaning the API rejected the state change (target state id, permissions, or issue state) even though the HTTP request itself succeeded. The mutation returns a payload without throwing, so the integration explicitly converts a falsy `success` into a thrown error. It indicates the issue's status was NOT changed.

Source

Thrown at mastracode/factory/src/integrations/linear/integration.ts:719

      const wantedType = input.state.stateType;
      targetState = states.find(state => state.type === wantedType) ?? null;
    } else {
      const wanted = input.state.name.toLowerCase();
      targetState = states.find(state => state.name.toLowerCase() === wanted) ?? null;
    }
    if (!targetState) return null;
    if (targetState.name === issue.state) {
      return linearIssueToIntakeIssue(issue);
    }
    const data = await linearGraphql<{ issueUpdate: { success: boolean } }>(
      accessToken,
      `mutation UpdateIssueState($id: String!, $stateId: String!) {
        issueUpdate(id: $id, input: { stateId: $stateId }) { success }
      }`,
      { id: issue.id, stateId: targetState.id },
    );
    if (!data.issueUpdate.success) {
      throw new Error('Linear did not accept the issue update.');
    }
    const fresh = await this.fetchIssueDetail(accessToken, issue.id);
    if (!fresh) return null;
    return linearIssueToIntakeIssue(fresh);
  }

  async #listTeamWorkflowStates(
    accessToken: string,
    teamKey: string,
  ): Promise<Array<{ id: string; name: string; type: string }>> {
    const data = await linearGraphql<{
      team: { states: { nodes: Array<{ id: string; name: string; type: string }> } } | null;
    }>(
      accessToken,
      `query TeamStates($key: String!) {
        team(id: $key) { states(first: 100) { nodes { id name type } } }
      }`,
      { key: teamKey },

View on GitHub (pinned to 75dd419e61)

Solutions

  1. Re-fetch the issue's team workflow states via Linear's API and retry the update with a freshly resolved `stateId` for the target state name.
  2. Verify the OAuth token used has the required `write` scope (issues) in Linear developer settings.
  3. Check the issue still exists and is not archived/canceled (`issueQuery` before update).
  4. Log the raw GraphQL response for `issueUpdate.userErrors`/errors to get Linear's specific rejection reason.
  5. Retry after a short backoff if the failure followed a concurrent state change.

Example fix

// before
if (!data.issueUpdate.success) {
  throw new Error('Linear did not accept the issue update.');
}
// after
if (!data.issueUpdate.success) {
  const states = await this.fetchTeamWorkflowStates(accessToken, teamId);
  const refreshed = states.find(s => s.id === targetState.id) ?? states.find(s => s.name === targetState.name);
  if (!refreshed) throw new Error(`State "${targetState.name}" no longer exists in Linear team ${teamId}.`);
  await this.updateIssueState(accessToken, issue, refreshed);
}
Defensive patterns

Strategy: retry

Validate before calling

const states = await getTeamWorkflowStates(accessToken, issue.teamId);
const target = states.find(s => s.id === targetState.id && s.type === 'started');
if (!target) throw new Error(`State ${targetState.id} not found for team ${issue.teamId}; refresh state ids before updating.`);

Type guard

function isSuccessfulUpdate(r: { issueUpdate?: { success?: boolean } | null }): r is { issueUpdate: { success: true } } {
  return r?.issueUpdate?.success === true;
}

Try / catch

try {
  await integration.updateIssueState(issue, targetState);
} catch (e) {
  if (e.message === 'Linear did not accept the issue update.') {
    await sleep(1000);
    const fresh = await integration.fetchIssue(issue.id);
    if (fresh) await integration.updateIssueState(fresh, targetState); // retry with fresh issue/state
  } else throw e;
}

Prevention

When it happens

Trigger: Calling any LinearIntegration method that moves an issue between states (e.g. marking an issue in-progress/done) where Linear's `issueUpdate` mutation responds with `success: false` — typically because `stateId` does not belong to the issue's team, the state was deleted/renamed, the OAuth token lacks `write` scope for issues, or the issue was deleted/archived between lookup and update.

Common situations: The workflow state name lookup resolved a stale or wrong-team state id; a Linear workspace admin changed the team's workflow states; the bot token's scope was reduced; the issue was canceled or migrated while a task was running; concurrent automation already moved the issue to a state that blocks this transition.

Related errors


AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30). Data as JSON: /api/errors/b0d683c615a2e5db. Report an issue: GitHub.