Skip to main content
Glama
tiovikram

Linear MCP Server

by tiovikram

get_issue

Retrieve detailed information about a specific Linear issue by providing its ID to access status, assignees, and related project data.

Instructions

Get detailed information about a specific issue

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
issueIdYesIssue ID

Implementation Reference

  • The main handler for the 'get_issue' tool. It retrieves the issue by ID using LinearClient, fetches related entities (state, assignee, etc.), constructs a detailed issue object, extracts embedded images and image attachments, and returns a formatted JSON response.
    case "get_issue": {
      const args = request.params.arguments as unknown as GetIssueArgs;
      if (!args?.issueId) {
        throw new Error("Issue ID is required");
      }
    
      const issue = await linearClient.issue(args.issueId);
      if (!issue) {
        throw new Error(`Issue ${args.issueId} not found`);
      }
    
      try {
        const [
          state,
          assignee,
          creator,
          team,
          project,
          parent,
          cycle,
          labels,
          comments,
          attachments,
        ] = await Promise.all([
          issue.state,
          issue.assignee,
          issue.creator,
          issue.team,
          issue.project,
          issue.parent,
          issue.cycle,
          issue.labels(),
          issue.comments(),
          issue.attachments(),
        ]);
    
        const issueDetails: {
          id: string;
          identifier: string;
          title: string;
          description: string | undefined;
          priority: number;
          priorityLabel: string;
          status: string;
          url: string;
          createdAt: Date;
          updatedAt: Date;
          startedAt: Date | null;
          completedAt: Date | null;
          canceledAt: Date | null;
          dueDate: string | null;
          assignee: { id: string; name: string; email: string } | null;
          creator: { id: string; name: string; email: string } | null;
          team: { id: string; name: string; key: string } | null;
          project: { id: string; name: string; state: string } | null;
          parent: { id: string; title: string; identifier: string } | null;
          cycle: { id: string; name: string; number: number } | null;
          labels: Array<{ id: string; name: string; color: string }>;
          comments: Array<{ id: string; body: string; createdAt: Date }>;
          attachments: Array<{ id: string; title: string; url: string }>;
          embeddedImages: Array<{ url: string; analysis: string }>;
          estimate: number | null;
          customerTicketCount: number;
          previousIdentifiers: string[];
          branchName: string;
          archivedAt: Date | null;
          autoArchivedAt: Date | null;
          autoClosedAt: Date | null;
          trashed: boolean;
        } = {
          id: issue.id,
          identifier: issue.identifier,
          title: issue.title,
          description: issue.description,
          priority: issue.priority,
          priorityLabel: issue.priorityLabel,
          status: state ? await state.name : "Unknown",
          url: issue.url,
          createdAt: issue.createdAt,
          updatedAt: issue.updatedAt,
          startedAt: issue.startedAt || null,
          completedAt: issue.completedAt || null,
          canceledAt: issue.canceledAt || null,
          dueDate: issue.dueDate,
          assignee: assignee
            ? {
                id: assignee.id,
                name: assignee.name,
                email: assignee.email,
              }
            : null,
          creator: creator
            ? {
                id: creator.id,
                name: creator.name,
                email: creator.email,
              }
            : null,
          team: team
            ? {
                id: team.id,
                name: team.name,
                key: team.key,
              }
            : null,
          project: project
            ? {
                id: project.id,
                name: project.name,
                state: project.state,
              }
            : null,
          parent: parent
            ? {
                id: parent.id,
                title: parent.title,
                identifier: parent.identifier,
              }
            : null,
          cycle:
            cycle && cycle.name
              ? {
                  id: cycle.id,
                  name: cycle.name,
                  number: cycle.number,
                }
              : null,
          labels: await Promise.all(
            labels.nodes.map(async (label: any) => ({
              id: label.id,
              name: label.name,
              color: label.color,
            }))
          ),
          comments: await Promise.all(
            comments.nodes.map(async (comment: any) => ({
              id: comment.id,
              body: comment.body,
              createdAt: comment.createdAt,
            }))
          ),
          attachments: await Promise.all(
            attachments.nodes.map(async (attachment: any) => ({
              id: attachment.id,
              title: attachment.title,
              url: attachment.url,
            }))
          ),
          embeddedImages: [],
          estimate: issue.estimate || null,
          customerTicketCount: issue.customerTicketCount || 0,
          previousIdentifiers: issue.previousIdentifiers || [],
          branchName: issue.branchName || "",
          archivedAt: issue.archivedAt || null,
          autoArchivedAt: issue.autoArchivedAt || null,
          autoClosedAt: issue.autoClosedAt || null,
          trashed: issue.trashed || false,
        };
    
        // Extract embedded images from description
        const imageMatches =
          issue.description?.match(/!\[.*?\]\((.*?)\)/g) || [];
        if (imageMatches.length > 0) {
          issueDetails.embeddedImages = imageMatches.map((match) => {
            const url = (match as string).match(/\((.*?)\)/)?.[1] || "";
            return {
              url,
              analysis: "Image analysis would go here", // Replace with actual image analysis if available
            };
          });
        }
    
        // Add image analysis for attachments if they are images
        issueDetails.attachments = await Promise.all(
          attachments.nodes
            .filter((attachment: any) =>
              attachment.url.match(/\.(jpg|jpeg|png|gif|webp)$/i)
            )
            .map(async (attachment: any) => ({
              id: attachment.id,
              title: attachment.title,
              url: attachment.url,
              analysis: "Image analysis would go here", // Replace with actual image analysis if available
            }))
        );
    
        return {
          content: [
            {
              type: "text",
              text: JSON.stringify(issueDetails, null, 2),
            },
          ],
        };
      } catch (error: any) {
        console.error("Error processing issue details:", error);
        throw new Error(`Failed to process issue details: ${error.message}`);
      }
    }
  • TypeScript type definition for the input arguments of the get_issue tool.
    type GetIssueArgs = {
      issueId: string;
    };
  • JSON schema definition for the input parameters of the get_issue tool, as exposed in the listTools response.
    inputSchema: {
      type: "object",
      properties: {
        issueId: {
          type: "string",
          description: "Issue ID",
        },
      },
      required: ["issueId"],
    },
  • src/index.ts:204-217 (registration)
    Registration of the get_issue tool in the listTools handler response, including name, description, and input schema.
    {
      name: "get_issue",
      description: "Get detailed information about a specific issue",
      inputSchema: {
        type: "object",
        properties: {
          issueId: {
            type: "string",
            description: "Issue ID",
          },
        },
        required: ["issueId"],
      },
    },
  • src/index.ts:46-54 (registration)
    Server capabilities declaration indicating support for the get_issue tool.
    tools: {
      create_issue: true,
      list_issues: true,
      update_issue: true,
      list_teams: true,
      list_projects: true,
      search_issues: true,
      get_issue: true,
    },

Tool Definition Quality

Score is being calculated. Check back soon.

Install Server

Other Tools

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/tiovikram/linear-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server