efficient-gitlab-mcp-server 2.4.0 → 2.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/dist/index.js +78 -23
  2. package/package.json +1 -1
package/dist/index.js CHANGED
@@ -53886,6 +53886,17 @@ var UpdateIssueNoteSchema = exports_external.object({
53886
53886
  note_id: exports_external.number().describe("Note ID"),
53887
53887
  body: exports_external.string().describe("New note body")
53888
53888
  });
53889
+ var GetIssueLinkSchema = exports_external.object({
53890
+ project_id: exports_external.string().describe("Project ID or URL-encoded path"),
53891
+ issue_iid: exports_external.number().describe("Issue IID"),
53892
+ issue_link_id: exports_external.number().describe("ID of the issue relationship")
53893
+ });
53894
+ var CreateNoteSchema = exports_external.object({
53895
+ project_id: exports_external.string().describe("Project ID or URL-encoded path"),
53896
+ notable_type: exports_external.enum(["issue", "merge_request"]).describe("Type of notable (issue or merge_request)"),
53897
+ notable_iid: exports_external.string().describe("IID of the issue or merge request"),
53898
+ body: exports_external.string().describe("Note content")
53899
+ });
53889
53900
  function registerIssueTools(server, logger2) {
53890
53901
  logger2.debug("Registering issue tools");
53891
53902
  const tools = new Map;
@@ -54119,10 +54130,66 @@ function registerIssueTools(server, logger2) {
54119
54130
  });
54120
54131
  toolRef12.disable();
54121
54132
  tools.set("update_issue_note", toolRef12);
54133
+ const toolRef13 = server.registerTool("get_issue_link", {
54134
+ title: "Get Issue Link",
54135
+ description: "Get a single issue link/relationship by ID",
54136
+ inputSchema: {
54137
+ project_id: exports_external.string().describe("Project ID or URL-encoded path"),
54138
+ issue_iid: exports_external.number().describe("Issue IID"),
54139
+ issue_link_id: exports_external.number().describe("ID of the issue relationship")
54140
+ },
54141
+ annotations: { readOnlyHint: true }
54142
+ }, async (params) => {
54143
+ const args = GetIssueLinkSchema.parse(params);
54144
+ const projectId = encodeProjectId(args.project_id);
54145
+ const link = await defaultClient.get(`/projects/${projectId}/issues/${args.issue_iid}/links/${args.issue_link_id}`);
54146
+ return { content: [{ type: "text", text: JSON.stringify(link, null, 2) }] };
54147
+ });
54148
+ toolRef13.disable();
54149
+ tools.set("get_issue_link", toolRef13);
54150
+ const toolRef14 = server.registerTool("create_note", {
54151
+ title: "Create Note",
54152
+ description: "Create a note/comment on an issue or merge request. Use notable_type to specify which.",
54153
+ inputSchema: {
54154
+ project_id: exports_external.string().describe("Project ID or URL-encoded path"),
54155
+ notable_type: exports_external.enum(["issue", "merge_request"]).describe("Type of notable (issue or merge_request)"),
54156
+ notable_iid: exports_external.string().describe("IID of the issue or merge request"),
54157
+ body: exports_external.string().describe("Note content")
54158
+ }
54159
+ }, async (params) => {
54160
+ const args = CreateNoteSchema.parse(params);
54161
+ const projectId = encodeProjectId(args.project_id);
54162
+ const notablePlural = args.notable_type === "issue" ? "issues" : "merge_requests";
54163
+ const note = await defaultClient.post(`/projects/${projectId}/${notablePlural}/${args.notable_iid}/notes`, { body: args.body });
54164
+ return { content: [{ type: "text", text: JSON.stringify(note, null, 2) }] };
54165
+ });
54166
+ toolRef14.disable();
54167
+ tools.set("create_note", toolRef14);
54122
54168
  logger2.debug("Issue tools registered", { count: tools.size });
54123
54169
  return tools;
54124
54170
  }
54125
54171
  // src/tools/merge-requests.ts
54172
+ var MAX_PATTERN_LENGTH = 200;
54173
+ var NESTED_QUANTIFIER_RE = /(\+|\*|\{)\s*(\+|\*|\{)/;
54174
+ function safeCompilePatterns(patterns) {
54175
+ return patterns.map((p) => {
54176
+ if (p.length > MAX_PATTERN_LENGTH || NESTED_QUANTIFIER_RE.test(p))
54177
+ return null;
54178
+ try {
54179
+ return new RegExp(p);
54180
+ } catch {
54181
+ return null;
54182
+ }
54183
+ }).filter((re) => re !== null);
54184
+ }
54185
+ function filterDiffsByPatterns(diffs, patterns) {
54186
+ if (!patterns?.length)
54187
+ return diffs;
54188
+ const regexes = safeCompilePatterns(patterns);
54189
+ if (regexes.length === 0)
54190
+ return diffs;
54191
+ return diffs.filter((d) => !regexes.some((re) => re.test(d.new_path) || (d.old_path ? re.test(d.old_path) : false)));
54192
+ }
54126
54193
  var GetMergeRequestSchema = exports_external.object({
54127
54194
  project_id: exports_external.string().describe("Project ID or URL-encoded path"),
54128
54195
  merge_request_iid: exports_external.number().optional().describe("Merge request IID"),
@@ -54177,7 +54244,8 @@ var GetMergeRequestDiffsSchema = exports_external.object({
54177
54244
  project_id: exports_external.string().describe("Project ID or URL-encoded path"),
54178
54245
  merge_request_iid: exports_external.number().describe("Merge request IID"),
54179
54246
  page: exports_external.number().optional().describe("Page number"),
54180
- per_page: exports_external.number().optional().describe("Results per page")
54247
+ per_page: exports_external.number().optional().describe("Results per page"),
54248
+ excluded_file_patterns: exports_external.array(exports_external.string()).optional().describe('Array of regex patterns to exclude files. Examples: ["^vendor/", "\\.pb\\.go$"]')
54181
54249
  });
54182
54250
  var ListMergeRequestDiscussionsSchema = exports_external.object({
54183
54251
  project_id: exports_external.string().describe("Project ID or URL-encoded path"),
@@ -54465,20 +54533,24 @@ function registerMergeRequestTools(server, logger2) {
54465
54533
  tools.set("merge_merge_request", toolRef5);
54466
54534
  const toolRef6 = server.registerTool("get_merge_request_diffs", {
54467
54535
  title: "Get Merge Request Diffs",
54468
- description: "Get the changes/diffs of a merge request",
54536
+ description: "Get the changes/diffs of a merge request. Supports excluded_file_patterns filtering using regex.",
54469
54537
  inputSchema: {
54470
54538
  project_id: exports_external.string().describe("Project ID or URL-encoded path"),
54471
54539
  merge_request_iid: exports_external.number().describe("Merge request IID"),
54472
54540
  page: exports_external.number().optional().describe("Page number"),
54473
- per_page: exports_external.number().optional().describe("Results per page")
54541
+ per_page: exports_external.number().optional().describe("Results per page"),
54542
+ excluded_file_patterns: exports_external.array(exports_external.string()).optional().describe('Array of regex patterns to exclude files. Examples: ["^vendor/", "\\.pb\\.go$"]')
54474
54543
  },
54475
54544
  annotations: { readOnlyHint: true }
54476
54545
  }, async (params) => {
54477
54546
  const args = GetMergeRequestDiffsSchema.parse(params);
54478
54547
  const projectId = encodeProjectId(args.project_id);
54479
54548
  const query = buildQueryString({ page: args.page, per_page: args.per_page });
54480
- const diffs = await defaultClient.get(`/projects/${projectId}/merge_requests/${args.merge_request_iid}/changes${query}`);
54481
- return { content: [{ type: "text", text: JSON.stringify(diffs, null, 2) }] };
54549
+ const mr = await defaultClient.get(`/projects/${projectId}/merge_requests/${args.merge_request_iid}/changes${query}`);
54550
+ const changes = filterDiffsByPatterns(mr.changes ?? [], args.excluded_file_patterns);
54551
+ return {
54552
+ content: [{ type: "text", text: JSON.stringify({ ...mr, changes }, null, 2) }]
54553
+ };
54482
54554
  });
54483
54555
  toolRef6.disable();
54484
54556
  tools.set("get_merge_request_diffs", toolRef6);
@@ -54708,24 +54780,7 @@ function registerMergeRequestTools(server, logger2) {
54708
54780
  renamed_file: c.renamed_file,
54709
54781
  deleted_file: c.deleted_file
54710
54782
  }));
54711
- if (args.excluded_file_patterns && args.excluded_file_patterns.length > 0) {
54712
- const patterns = [];
54713
- for (const p of args.excluded_file_patterns) {
54714
- try {
54715
- patterns.push(new RegExp(p));
54716
- } catch {
54717
- return {
54718
- content: [
54719
- {
54720
- type: "text",
54721
- text: JSON.stringify({ error: `Invalid regex pattern: ${p}` }, null, 2)
54722
- }
54723
- ]
54724
- };
54725
- }
54726
- }
54727
- files = files.filter((f) => !patterns.some((re) => re.test(f.new_path) || re.test(f.old_path)));
54728
- }
54783
+ files = filterDiffsByPatterns(files, args.excluded_file_patterns);
54729
54784
  return { content: [{ type: "text", text: JSON.stringify(files, null, 2) }] };
54730
54785
  });
54731
54786
  toolRef18.disable();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "efficient-gitlab-mcp-server",
3
- "version": "2.4.0",
3
+ "version": "2.6.0",
4
4
  "mcpName": "io.github.detailobsessed/efficient-gitlab",
5
5
  "description": "Production-ready GitLab MCP Server with progressive disclosure pattern",
6
6
  "license": "MIT",