opencode-gitlab-plugin 3.1.0 → 3.2.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.
@@ -29275,9 +29275,22 @@ var MergeRequestsClient = class _MergeRequestsClient extends GitLabApiClient {
29275
29275
  requestBody
29276
29276
  );
29277
29277
  }
29278
- async createMrNote(projectId, mrIid, body, discussionId) {
29278
+ /**
29279
+ * Create a note on a merge request.
29280
+ *
29281
+ * When `discussionId` is set the note is a reply on that discussion thread, which the
29282
+ * GitLab Notes API does not allow to be internal. Passing `internal=true` together with a
29283
+ * `discussionId` therefore throws (fail-closed) rather than silently dropping the
29284
+ * confidentiality flag. Post a standalone internal note (omit `discussionId`) instead.
29285
+ */
29286
+ async createMrNote(projectId, mrIid, body, discussionId, internal) {
29279
29287
  const encodedProject = this.encodeProjectId(projectId);
29280
29288
  if (discussionId) {
29289
+ if (internal) {
29290
+ throw new Error(
29291
+ "internal=true is not supported when replying to a discussion. The GitLab Notes API does not accept an internal flag on discussion replies, so honouring it silently would drop a confidentiality flag. Post a standalone internal note (omit discussionId) instead."
29292
+ );
29293
+ }
29281
29294
  return this.fetch(
29282
29295
  "POST",
29283
29296
  `/projects/${encodedProject}/merge_requests/${mrIid}/discussions/${discussionId}/notes`,
@@ -29287,7 +29300,7 @@ var MergeRequestsClient = class _MergeRequestsClient extends GitLabApiClient {
29287
29300
  return this.fetch(
29288
29301
  "POST",
29289
29302
  `/projects/${encodedProject}/merge_requests/${mrIid}/notes`,
29290
- { body }
29303
+ internal ? { body, internal: true } : { body }
29291
29304
  );
29292
29305
  }
29293
29306
  async updateMrNote(projectId, mrIid, noteId, body) {
@@ -29753,9 +29766,22 @@ var IssuesClient = class extends GitLabApiClient {
29753
29766
  `/projects/${encodedProject}/issues/${issueIid}/discussions/${discussionId}`
29754
29767
  );
29755
29768
  }
29756
- async createIssueNote(projectId, issueIid, body, discussionId) {
29769
+ /**
29770
+ * Create a note on an issue.
29771
+ *
29772
+ * When `discussionId` is set the note is a reply on that discussion thread, which the
29773
+ * GitLab Notes API does not allow to be internal. Passing `internal=true` together with a
29774
+ * `discussionId` therefore throws (fail-closed) rather than silently dropping the
29775
+ * confidentiality flag. Post a standalone internal note (omit `discussionId`) instead.
29776
+ */
29777
+ async createIssueNote(projectId, issueIid, body, discussionId, internal) {
29757
29778
  const encodedProject = this.encodeProjectId(projectId);
29758
29779
  if (discussionId) {
29780
+ if (internal) {
29781
+ throw new Error(
29782
+ "internal=true is not supported when replying to a discussion. The GitLab Notes API does not accept an internal flag on discussion replies, so honouring it silently would drop a confidentiality flag. Post a standalone internal note (omit discussionId) instead."
29783
+ );
29784
+ }
29759
29785
  return this.fetch(
29760
29786
  "POST",
29761
29787
  `/projects/${encodedProject}/issues/${issueIid}/discussions/${discussionId}/notes`,
@@ -29765,7 +29791,7 @@ var IssuesClient = class extends GitLabApiClient {
29765
29791
  return this.fetch(
29766
29792
  "POST",
29767
29793
  `/projects/${encodedProject}/issues/${issueIid}/notes`,
29768
- { body }
29794
+ internal ? { body, internal: true } : { body }
29769
29795
  );
29770
29796
  }
29771
29797
  async resolveIssueDiscussion(projectId, issueIid, discussionId) {
@@ -31096,9 +31122,22 @@ var EpicsClient = class extends GitLabApiClient {
31096
31122
  `/groups/${encodedGroup}/epics/${epicIid}/discussions/${discussionId}`
31097
31123
  );
31098
31124
  }
31099
- async createEpicNote(groupId, epicIid, body, discussionId) {
31125
+ /**
31126
+ * Create a note on an epic.
31127
+ *
31128
+ * When `discussionId` is set the note is a reply on that discussion thread, which the
31129
+ * GitLab Notes API does not allow to be internal. Passing `internal=true` together with a
31130
+ * `discussionId` therefore throws (fail-closed) rather than silently dropping the
31131
+ * confidentiality flag. Post a standalone internal note (omit `discussionId`) instead.
31132
+ */
31133
+ async createEpicNote(groupId, epicIid, body, discussionId, internal) {
31100
31134
  const encodedGroup = encodeURIComponent(groupId);
31101
31135
  if (discussionId) {
31136
+ if (internal) {
31137
+ throw new Error(
31138
+ "internal=true is not supported when replying to a discussion. The GitLab Notes API does not accept an internal flag on discussion replies, so honouring it silently would drop a confidentiality flag. Post a standalone internal note (omit discussionId) instead."
31139
+ );
31140
+ }
31102
31141
  return this.fetch(
31103
31142
  "POST",
31104
31143
  `/groups/${encodedGroup}/epics/${epicIid}/discussions/${discussionId}/notes`,
@@ -31108,7 +31147,7 @@ var EpicsClient = class extends GitLabApiClient {
31108
31147
  return this.fetch(
31109
31148
  "POST",
31110
31149
  `/groups/${encodedGroup}/epics/${epicIid}/notes`,
31111
- { body }
31150
+ internal ? { body, internal: true } : { body }
31112
31151
  );
31113
31152
  }
31114
31153
  async getEpicNote(groupId, epicIid, noteId) {
@@ -33659,9 +33698,14 @@ Creates a standalone comment (not part of a thread).
33659
33698
  For replying to existing discussion threads, use gitlab_create_discussion
33660
33699
  with discussion_id parameter instead.
33661
33700
 
33701
+ Set internal=true to post a confidential/internal note visible only to project members
33702
+ (supported for merge requests, issues, and epics; not supported for snippets, where passing
33703
+ internal=true raises an error rather than silently posting a public note).
33704
+
33662
33705
  Examples:
33663
33706
  - MR comment: resource_type="merge_request", project_id="group/project", iid=123, body="LGTM!"
33664
33707
  - Issue comment: resource_type="issue", project_id="group/project", iid=456, body="Working on this"
33708
+ - Internal issue note: resource_type="issue", project_id="group/project", iid=456, body="Internal only", internal=true
33665
33709
  - Epic comment: resource_type="epic", group_id="my-group", iid=1, body="Planning complete"
33666
33710
  - Snippet comment: resource_type="snippet", project_id="group/project", snippet_id=789, body="Nice code!"`,
33667
33711
  args: {
@@ -33670,27 +33714,53 @@ Examples:
33670
33714
  project_id: z14.string().optional().describe("Project ID or path. Required for merge_request, issue, snippet"),
33671
33715
  group_id: z14.string().optional().describe("Group ID or path. Required for epic"),
33672
33716
  iid: z14.number().optional().describe("Internal ID of the resource (for merge_request, issue, epic)"),
33673
- snippet_id: z14.number().optional().describe("Snippet ID (required for snippet)")
33717
+ snippet_id: z14.number().optional().describe("Snippet ID (required for snippet)"),
33718
+ internal: z14.boolean().optional().describe(
33719
+ "Post as a confidential/internal note visible only to project members (merge requests, issues, and epics; not supported for snippets, where passing true raises an error). Defaults to false (public note)."
33720
+ )
33674
33721
  },
33675
33722
  execute: async (args, _ctx) => {
33676
33723
  validateNoteParams(args.resource_type, args, { allowedTypes: NOTE_RESOURCE_TYPES });
33724
+ if (args.internal && args.resource_type === "snippet") {
33725
+ throw new Error(
33726
+ `internal=true is not supported for snippet notes. Refusing to post a note that was intended to be confidential as a public note.`
33727
+ );
33728
+ }
33677
33729
  const client = getGitLabClient();
33678
33730
  switch (args.resource_type) {
33679
33731
  case "merge_request":
33680
33732
  return JSON.stringify(
33681
- await client.createMrNote(args.project_id, args.iid, args.body),
33733
+ await client.createMrNote(
33734
+ args.project_id,
33735
+ args.iid,
33736
+ args.body,
33737
+ void 0,
33738
+ args.internal
33739
+ ),
33682
33740
  null,
33683
33741
  2
33684
33742
  );
33685
33743
  case "issue":
33686
33744
  return JSON.stringify(
33687
- await client.createIssueNote(args.project_id, args.iid, args.body),
33745
+ await client.createIssueNote(
33746
+ args.project_id,
33747
+ args.iid,
33748
+ args.body,
33749
+ void 0,
33750
+ args.internal
33751
+ ),
33688
33752
  null,
33689
33753
  2
33690
33754
  );
33691
33755
  case "epic":
33692
33756
  return JSON.stringify(
33693
- await client.createEpicNote(args.group_id, args.iid, args.body),
33757
+ await client.createEpicNote(
33758
+ args.group_id,
33759
+ args.iid,
33760
+ args.body,
33761
+ void 0,
33762
+ args.internal
33763
+ ),
33694
33764
  null,
33695
33765
  2
33696
33766
  );
@@ -34727,7 +34797,7 @@ async function main() {
34727
34797
  `);
34728
34798
  process.exit(1);
34729
34799
  }
34730
- const version2 = true ? "3.1.0" : "0.0.0";
34800
+ const version2 = true ? "3.2.0" : "0.0.0";
34731
34801
  const server = new McpServer({ name: "gitlab", version: version2 });
34732
34802
  adaptToolsToMcp(server, mcpTools);
34733
34803
  const transport = new StdioServerTransport();