@zereight/mcp-gitlab 2.3.7 → 2.3.8-next.143
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.
- package/README.ko.md +1 -1
- package/README.md +1 -1
- package/README.pt-BR.md +1 -1
- package/README.zh-CN.md +1 -1
- package/build/index.js +5 -92
- package/build/utils/merge-request-summary.js +94 -0
- package/package.json +1 -1
package/README.ko.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# GitLab MCP Server
|
|
2
2
|
|
|
3
3
|
[](https://www.npmjs.com/package/@zereight/mcp-gitlab)
|
|
4
|
-
[](https://vscode.dev/redirect/mcp/install?name=zereight.gitlab-mcp&config=%7B%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40zereight%2Fmcp-gitlab%40latest%22%5D%2C%22env%22%3A%7B%22GITLAB_PERSONAL_ACCESS_TOKEN%22%3A%22%24%7Binput%3Agitlab-token%7D%22%2C%22GITLAB_API_URL%22%3A%22https%3A%2F%2Fgitlab.com%2Fapi%2Fv4%22%2C%22GITLAB_PERMISSION_MODE%22%3A%22full%22%7D%7D)
|
|
4
|
+
[](https://vscode.dev/redirect/mcp/install?name=zereight.gitlab-mcp&inputs=%5B%7B%22type%22%3A%22promptString%22%2C%22id%22%3A%22gitlab-token%22%2C%22description%22%3A%22GitLab%20Personal%20Access%20Token%22%2C%22password%22%3Atrue%7D%5D&config=%7B%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40zereight%2Fmcp-gitlab%40latest%22%5D%2C%22env%22%3A%7B%22GITLAB_PERSONAL_ACCESS_TOKEN%22%3A%22%24%7Binput%3Agitlab-token%7D%22%2C%22GITLAB_API_URL%22%3A%22https%3A%2F%2Fgitlab.com%2Fapi%2Fv4%22%2C%22GITLAB_PERMISSION_MODE%22%3A%22full%22%7D%7D)
|
|
5
5
|
[](https://cursor.com/en/install-mcp?name=zereight.gitlab-mcp&config=eyJ0eXBlIjoic3RkaW8iLCJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkB6ZXJlaWdodC9tY3AtZ2l0bGFiQGxhdGVzdCJdLCJlbnYiOnsiR0lUTEFCX1BFUlNPTkFMX0FDQ0VTU19UT0tFTiI6IiR7ZW52OkdJVExBQl9QRVJTT05BTF9BQ0NFU1NfVE9LRU59IiwiR0lUTEFCX0FQSV9VUkwiOiJodHRwczovL2dpdGxhYi5jb20vYXBpL3Y0IiwiR0lUTEFCX1BFUk1JU1NJT05fTU9ERSI6ImZ1bGwifX0%3D)
|
|
6
6
|
|
|
7
7
|
[English](./README.md) | [한국어](./README.ko.md) | [简体中文](./README.zh-CN.md) | [Português (Brasil)](./README.pt-BR.md)
|
package/README.md
CHANGED
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
[](https://www.npmjs.com/package/@zereight/mcp-gitlab)
|
|
5
5
|
[](https://www.npmjs.com/package/@zereight/mcp-gitlab)
|
|
6
6
|
[](https://github.com/zereight/gitlab-mcp/blob/main/LICENSE)
|
|
7
|
-
[](https://vscode.dev/redirect/mcp/install?name=zereight.gitlab-mcp&config=%7B%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40zereight%2Fmcp-gitlab%40latest%22%5D%2C%22env%22%3A%7B%22GITLAB_PERSONAL_ACCESS_TOKEN%22%3A%22%24%7Binput%3Agitlab-token%7D%22%2C%22GITLAB_API_URL%22%3A%22https%3A%2F%2Fgitlab.com%2Fapi%2Fv4%22%2C%22GITLAB_PERMISSION_MODE%22%3A%22full%22%7D%7D)
|
|
7
|
+
[](https://vscode.dev/redirect/mcp/install?name=zereight.gitlab-mcp&inputs=%5B%7B%22type%22%3A%22promptString%22%2C%22id%22%3A%22gitlab-token%22%2C%22description%22%3A%22GitLab%20Personal%20Access%20Token%22%2C%22password%22%3Atrue%7D%5D&config=%7B%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40zereight%2Fmcp-gitlab%40latest%22%5D%2C%22env%22%3A%7B%22GITLAB_PERSONAL_ACCESS_TOKEN%22%3A%22%24%7Binput%3Agitlab-token%7D%22%2C%22GITLAB_API_URL%22%3A%22https%3A%2F%2Fgitlab.com%2Fapi%2Fv4%22%2C%22GITLAB_PERMISSION_MODE%22%3A%22full%22%7D%7D)
|
|
8
8
|
[](https://cursor.com/en/install-mcp?name=zereight.gitlab-mcp&config=eyJ0eXBlIjoic3RkaW8iLCJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkB6ZXJlaWdodC9tY3AtZ2l0bGFiQGxhdGVzdCJdLCJlbnYiOnsiR0lUTEFCX1BFUlNPTkFMX0FDQ0VTU19UT0tFTiI6IiR7ZW52OkdJVExBQl9QRVJTT05BTF9BQ0NFU1NfVE9LRU59IiwiR0lUTEFCX0FQSV9VUkwiOiJodHRwczovL2dpdGxhYi5jb20vYXBpL3Y0IiwiR0lUTEFCX1BFUk1JU1NJT05fTU9ERSI6ImZ1bGwifX0%3D)
|
|
9
9
|
[](https://deepwiki.com/zereight/gitlab-mcp)
|
|
10
10
|
[](https://mcptoplist.com/server/io.github.zereight%2Fgitlab-mcp) [](https://mcpindex.ai/server/io-github-zereight-gitlab-mcp)
|
package/README.pt-BR.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# GitLab MCP Server
|
|
2
2
|
|
|
3
3
|
[](https://www.npmjs.com/package/@zereight/mcp-gitlab)
|
|
4
|
-
[](https://vscode.dev/redirect/mcp/install?name=zereight.gitlab-mcp&config=%7B%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40zereight%2Fmcp-gitlab%40latest%22%5D%2C%22env%22%3A%7B%22GITLAB_PERSONAL_ACCESS_TOKEN%22%3A%22%24%7Binput%3Agitlab-token%7D%22%2C%22GITLAB_API_URL%22%3A%22https%3A%2F%2Fgitlab.com%2Fapi%2Fv4%22%2C%22GITLAB_PERMISSION_MODE%22%3A%22full%22%7D%7D)
|
|
4
|
+
[](https://vscode.dev/redirect/mcp/install?name=zereight.gitlab-mcp&inputs=%5B%7B%22type%22%3A%22promptString%22%2C%22id%22%3A%22gitlab-token%22%2C%22description%22%3A%22GitLab%20Personal%20Access%20Token%22%2C%22password%22%3Atrue%7D%5D&config=%7B%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40zereight%2Fmcp-gitlab%40latest%22%5D%2C%22env%22%3A%7B%22GITLAB_PERSONAL_ACCESS_TOKEN%22%3A%22%24%7Binput%3Agitlab-token%7D%22%2C%22GITLAB_API_URL%22%3A%22https%3A%2F%2Fgitlab.com%2Fapi%2Fv4%22%2C%22GITLAB_PERMISSION_MODE%22%3A%22full%22%7D%7D)
|
|
5
5
|
[](https://cursor.com/en/install-mcp?name=zereight.gitlab-mcp&config=eyJ0eXBlIjoic3RkaW8iLCJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkB6ZXJlaWdodC9tY3AtZ2l0bGFiQGxhdGVzdCJdLCJlbnYiOnsiR0lUTEFCX1BFUlNPTkFMX0FDQ0VTU19UT0tFTiI6IiR7ZW52OkdJVExBQl9QRVJTT05BTF9BQ0NFU1NfVE9LRU59IiwiR0lUTEFCX0FQSV9VUkwiOiJodHRwczovL2dpdGxhYi5jb20vYXBpL3Y0IiwiR0lUTEFCX1BFUk1JU1NJT05fTU9ERSI6ImZ1bGwifX0%3D)
|
|
6
6
|
|
|
7
7
|
[English](./README.md) | [한국어](./README.ko.md) | [简体中文](./README.zh-CN.md) | [Português (Brasil)](./README.pt-BR.md)
|
package/README.zh-CN.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# GitLab MCP Server
|
|
2
2
|
|
|
3
3
|
[](https://www.npmjs.com/package/@zereight/mcp-gitlab)
|
|
4
|
-
[](https://vscode.dev/redirect/mcp/install?name=zereight.gitlab-mcp&config=%7B%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40zereight%2Fmcp-gitlab%40latest%22%5D%2C%22env%22%3A%7B%22GITLAB_PERSONAL_ACCESS_TOKEN%22%3A%22%24%7Binput%3Agitlab-token%7D%22%2C%22GITLAB_API_URL%22%3A%22https%3A%2F%2Fgitlab.com%2Fapi%2Fv4%22%2C%22GITLAB_PERMISSION_MODE%22%3A%22full%22%7D%7D)
|
|
4
|
+
[](https://vscode.dev/redirect/mcp/install?name=zereight.gitlab-mcp&inputs=%5B%7B%22type%22%3A%22promptString%22%2C%22id%22%3A%22gitlab-token%22%2C%22description%22%3A%22GitLab%20Personal%20Access%20Token%22%2C%22password%22%3Atrue%7D%5D&config=%7B%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40zereight%2Fmcp-gitlab%40latest%22%5D%2C%22env%22%3A%7B%22GITLAB_PERSONAL_ACCESS_TOKEN%22%3A%22%24%7Binput%3Agitlab-token%7D%22%2C%22GITLAB_API_URL%22%3A%22https%3A%2F%2Fgitlab.com%2Fapi%2Fv4%22%2C%22GITLAB_PERMISSION_MODE%22%3A%22full%22%7D%7D)
|
|
5
5
|
[](https://cursor.com/en/install-mcp?name=zereight.gitlab-mcp&config=eyJ0eXBlIjoic3RkaW8iLCJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkB6ZXJlaWdodC9tY3AtZ2l0bGFiQGxhdGVzdCJdLCJlbnYiOnsiR0lUTEFCX1BFUlNPTkFMX0FDQ0VTU19UT0tFTiI6IiR7ZW52OkdJVExBQl9QRVJTT05BTF9BQ0NFU1NfVE9LRU59IiwiR0lUTEFCX0FQSV9VUkwiOiJodHRwczovL2dpdGxhYi5jb20vYXBpL3Y0IiwiR0lUTEFCX1BFUk1JU1NJT05fTU9ERSI6ImZ1bGwifX0%3D)
|
|
6
6
|
|
|
7
7
|
[English](./README.md) | [한국어](./README.ko.md) | [简体中文](./README.zh-CN.md) | [Português (Brasil)](./README.pt-BR.md)
|
package/build/index.js
CHANGED
|
@@ -107,6 +107,7 @@ import { checkForNewVersion } from "./utils/version-check.js";
|
|
|
107
107
|
import { assertGitLabVersionAtLeast } from "./utils/gitlab-version-gate.js";
|
|
108
108
|
import { fetchWithValidatedRedirects } from "./utils/safe-redirect-fetch.js";
|
|
109
109
|
import { fetchStatusBeforeDeadline } from "./utils/poll-deadline.js";
|
|
110
|
+
import { getUniqueApprovalUsers, inferMergeRequestApproved, MERGE_REQUEST_DEPLOYMENT_SUMMARY_LIMIT, parseApprovalsResponse, sortDeploymentsByCreatedAtDesc, toMergeRequestDeploymentSummaryRecord, } from "./utils/merge-request-summary.js";
|
|
110
111
|
import { parseGitLabVersionApiResponse, } from "./utils/gitlab-instance-version.js";
|
|
111
112
|
import { buildBulkPublishDraftNotesBody, needsGitLab19_2BulkPublish, } from "./utils/bulk-publish-options.js";
|
|
112
113
|
import { appendFilterParam, appendFilterParams, cleanMutuallyExclusiveIdUsernameOptions, dropBlankArrayEntries, isBlankFilterValue, LIST_MERGE_REQUESTS_ID_USERNAME_PAIRS, sanitizeToolArguments, } from "./utils/tool-args.js";
|
|
@@ -128,7 +129,7 @@ GitLabDiscussionNoteSchema, // Added
|
|
|
128
129
|
GitLabDiscussionSchema,
|
|
129
130
|
// Draft Notes Schemas
|
|
130
131
|
GitLabDraftNoteSchema, GitLabForkSchema, GitLabBranchSchema, GitLabProtectedBranchSchema, GitLabProtectedTagSchema, GitLabGroupSchema, GitLabIssueLinkSchema, GitLabIssueSchema, GitLabIssueWithLinkDetailsSchema, GitLabMarkdownUploadSchema, GitLabMergeRequestPipelineSchema, GitLabMergeRequestSchema, GitLabMilestonesSchema, GitLabGroupMilestonesSchema, GitLabNamespaceExistsResponseSchema, GitLabNamespaceSchema, GitLabPipelineJobSchema, GitLabDeploymentSchema, GitLabEnvironmentSchema, GitLabPipelineSchema, GitLabPipelineScheduleSchema, GitLabPipelineScheduleVariableSchema, GitLabPipelineSchedulePlayResultSchema, ListPipelineSchedulesSchema, GetPipelineScheduleSchema, ListPipelineSchedulePipelinesSchema, CreatePipelineScheduleSchema, UpdatePipelineScheduleSchema, DeletePipelineScheduleSchema, PlayPipelineScheduleSchema, TakeOwnershipPipelineScheduleSchema, GetPipelineScheduleVariableSchema, CreatePipelineScheduleVariableSchema, UpdatePipelineScheduleVariableSchema, DeletePipelineScheduleVariableSchema, GitLabPipelineTriggerJobSchema, GitLabProjectMemberSchema, GitLabProjectSchema, GitLabTodoSchema, GitLabReferenceSchema, GitLabRepositorySchema, GitLabSearchBlobResultSchema, GitLabSearchResponseSchema, GitLabTreeItemSchema, GitLabUserSchema, GitLabUsersResponseSchema, GitLabWikiPageSchema, GroupIteration, ListCommitStatusesSchema, ListBranchesSchema, ListCommitsSchema, ListDraftNotesSchema, ListGroupIterationsSchema, ListGroupProjectsSchema, GitLabCiVariableSchema, ListProjectVariablesSchema, GetProjectVariableSchema, CreateProjectVariableSchema, UpdateProjectVariableSchema, DeleteProjectVariableSchema, ListGroupVariablesSchema, GetGroupVariableSchema, CreateGroupVariableSchema, UpdateGroupVariableSchema, DeleteGroupVariableSchema, GitLabDependencyProxySchema, GitLabDependencyProxyBlobSchema, GetDependencyProxySettingsSchema, UpdateDependencyProxySettingsSchema, ListDependencyProxyBlobsSchema, PurgeDependencyProxyCacheSchema, ListProjectVulnerabilitiesSchema, GetVulnerabilitySchema, DismissVulnerabilitySchema, ConfirmVulnerabilitySchema, ListIssueDiscussionsSchema, ListIssueLinksSchema, ListIssuesSchema, ListTodosSchema, ListLabelsSchema, ListMergeRequestDiffsSchema, // Added
|
|
131
|
-
GetMergeRequestFileDiffSchema, ListMergeRequestChangedFilesSchema, ListMergeRequestDiscussionsSchema, ListMergeRequestPipelinesSchema, ListMergeRequestsSchema, ListGroupMergeRequestsSchema, ListMergeRequestVersionsSchema, GetMergeRequestVersionSchema, GitLabMergeRequestVersionSchema, GitLabMergeRequestVersionDetailSchema, ListNamespacesSchema, ListPipelineJobsSchema, ListPipelinesSchema, ListDeploymentsSchema, ListEnvironmentsSchema, ListProjectRunnersSchema, GetRunnerSchema, ListPipelineTriggerJobsSchema, ValidateCiLintSchema, ValidateProjectCiLintSchema, ListCiCatalogResourcesSchema, GetCiCatalogResourceSchema, ListProjectMembersSchema, ListGroupMembersSchema, ListProjectMilestonesSchema, ListGroupMilestonesSchema, ListProjectsSchema, ListWikiPagesSchema, GetGroupWikiPageSchema, ListGroupWikiPagesSchema, UpdateGroupWikiPageSchema, MarkdownUploadSchema, MarkdownUploadRemoteSchema, DownloadAttachmentSchema, DownloadJobArtifactsSchema, GetJobArtifactFileSchema, GitLabArtifactEntrySchema, ListJobArtifactsSchema, MergeMergeRequestSchema, ApproveMergeRequestSchema, UnapproveMergeRequestSchema, RebaseMergeRequestSchema, GetMergeRequestApprovalStateSchema, GetMergeRequestConflictsSchema,
|
|
132
|
+
GetMergeRequestFileDiffSchema, ListMergeRequestChangedFilesSchema, ListMergeRequestDiscussionsSchema, ListMergeRequestPipelinesSchema, ListMergeRequestsSchema, ListGroupMergeRequestsSchema, ListMergeRequestVersionsSchema, GetMergeRequestVersionSchema, GitLabMergeRequestVersionSchema, GitLabMergeRequestVersionDetailSchema, ListNamespacesSchema, ListPipelineJobsSchema, ListPipelinesSchema, ListDeploymentsSchema, ListEnvironmentsSchema, ListProjectRunnersSchema, GetRunnerSchema, ListPipelineTriggerJobsSchema, ValidateCiLintSchema, ValidateProjectCiLintSchema, ListCiCatalogResourcesSchema, GetCiCatalogResourceSchema, ListProjectMembersSchema, ListGroupMembersSchema, ListProjectMilestonesSchema, ListGroupMilestonesSchema, ListProjectsSchema, ListWikiPagesSchema, GetGroupWikiPageSchema, ListGroupWikiPagesSchema, UpdateGroupWikiPageSchema, MarkdownUploadSchema, MarkdownUploadRemoteSchema, DownloadAttachmentSchema, DownloadJobArtifactsSchema, GetJobArtifactFileSchema, GitLabArtifactEntrySchema, ListJobArtifactsSchema, MergeMergeRequestSchema, ApproveMergeRequestSchema, UnapproveMergeRequestSchema, RebaseMergeRequestSchema, GetMergeRequestApprovalStateSchema, GetMergeRequestConflictsSchema, GitLabMergeRequestApprovalStateSchema, MyIssuesSchema, OrbitQuerySchema, OrbitSchemaSchema, OrbitStatusSchema, OrbitToolsSchema, MarkAllTodosDoneSchema, MarkTodoDoneSchema, PaginatedDiscussionsResponseSchema, PromoteProjectMilestoneSchema, PublishDraftNoteSchema, PlayPipelineJobSchema, PushFilesSchema, RetryPipelineJobSchema, RetryPipelineSchema, SearchCodeSchema, SearchGroupCodeSchema, SearchProjectCodeSchema, SearchRepositoriesSchema, UpdateDraftNoteSchema, UpdateIssueNoteSchema, UpdateIssueSchema, UpdateIssueDescriptionPatchSchema, UpdateLabelSchema, UpdateProjectSchema, UpdateMergeRequestNoteSchema, UpdateMergeRequestDiscussionNoteSchema, UpdateMergeRequestSchema, UpdateWikiPageSchema, VerifyNamespaceSchema, GitLabEventSchema, ListEventsSchema, GetProjectEventsSchema, ExecuteGraphQLSchema, GitLabReleaseSchema, ListReleasesSchema, GetReleaseSchema, CreateReleaseSchema, UpdateReleaseSchema, DeleteReleaseSchema, CreateReleaseEvidenceSchema, DownloadReleaseAssetSchema, ListTagsSchema, GetTagSchema, CreateTagSchema, DeleteTagSchema, GetTagSignatureSchema, ListProtectedTagsSchema, GetProtectedTagSchema, ProtectTagSchema, UnprotectTagSchema, GitLabTagSchema, GitLabTagSignatureSchema, ListSnippetsSchema, GetSnippetSchema, CreateSnippetSchema, UpdateSnippetSchema, DeleteSnippetSchema, GitLabSnippetSchema, GetMergeRequestNotesSchema, GetMergeRequestNoteSchema, GetMergeRequestDiscussionSchema, DeleteMergeRequestDiscussionNoteSchema, ResolveMergeRequestThreadSchema, GetWorkItemSchema, ListWorkItemsSchema, CreateWorkItemSchema, UpdateWorkItemSchema, ConvertWorkItemTypeSchema, ListWorkItemStatusesSchema, ListWorkItemNotesSchema, CreateWorkItemNoteSchema, CreateWorkItemEmojiReactionSchema, CreateWorkItemNoteEmojiReactionSchema, ListWorkItemEmojiReactionsSchema, ListWorkItemNoteEmojiReactionsSchema, DeleteWorkItemEmojiReactionSchema, DeleteWorkItemNoteEmojiReactionSchema, MoveWorkItemSchema, ListCustomFieldDefinitionsSchema, GetTimelineEventsSchema, CreateTimelineEventSchema, ListWebhooksSchema, CreateWebhookSchema, UpdateWebhookSchema, DeleteWebhookSchema, ListWebhookEventsSchema, GetWebhookEventSchema, HealthCheckSchema, } from "./schemas.js";
|
|
132
133
|
import { createHash, randomUUID, timingSafeEqual } from "node:crypto";
|
|
133
134
|
import { createLogger, flushBufferedLogs, flushStartupLogs } from "./utils/logger.js";
|
|
134
135
|
const logger = createLogger();
|
|
@@ -1265,7 +1266,6 @@ const ignoredExplicitTools = [...individuallyEnabledTools].filter(name => isExpl
|
|
|
1265
1266
|
if (ignoredExplicitTools.length > 0) {
|
|
1266
1267
|
logger.warn(`GITLAB_TOOLS names ${ignoredExplicitTools.join(", ")}, but that tool is enabled only when its toolset is listed in GITLAB_TOOLSETS. The GITLAB_TOOLS entry is ignored.`);
|
|
1267
1268
|
}
|
|
1268
|
-
const MERGE_REQUEST_DEPLOYMENT_SUMMARY_LIMIT = 10;
|
|
1269
1269
|
function toAllowedGitLabApiUrl(value) {
|
|
1270
1270
|
const trimmed = value.trim();
|
|
1271
1271
|
if (!trimmed)
|
|
@@ -1376,7 +1376,9 @@ if (!isCliInvocation(process.argv) &&
|
|
|
1376
1376
|
// This exit runs before runServer(), so warnings have to be printed here too.
|
|
1377
1377
|
emitDeprecatedEnvWarnings();
|
|
1378
1378
|
logger.error("GITLAB_PERSONAL_ACCESS_TOKEN environment variable is not set");
|
|
1379
|
-
logger.info("Either set GITLAB_PERSONAL_ACCESS_TOKEN or
|
|
1379
|
+
logger.info("Either set GITLAB_PERSONAL_ACCESS_TOKEN (or --token, or GITLAB_PERSONAL_ACCESS_TOKEN_FILE), " +
|
|
1380
|
+
"GITLAB_JOB_TOKEN, or GITLAB_AUTH_COOKIE_PATH, or enable OAuth with GITLAB_USE_OAUTH=true. " +
|
|
1381
|
+
`Setup guide: ${SERVER_WEBSITE_URL}getting-started/`);
|
|
1380
1382
|
exitAfterFlush(1);
|
|
1381
1383
|
}
|
|
1382
1384
|
class GitLabApiError extends Error {
|
|
@@ -4072,58 +4074,6 @@ async function buildMergeRequestApprovalSummary(projectId, mergeRequestIid) {
|
|
|
4072
4074
|
};
|
|
4073
4075
|
}
|
|
4074
4076
|
}
|
|
4075
|
-
function toMergeRequestDeploymentSummaryRecord(deployment) {
|
|
4076
|
-
return {
|
|
4077
|
-
id: deployment.id,
|
|
4078
|
-
status: deployment.status,
|
|
4079
|
-
ref: deployment.ref,
|
|
4080
|
-
sha: deployment.sha,
|
|
4081
|
-
created_at: deployment.created_at,
|
|
4082
|
-
updated_at: deployment.updated_at,
|
|
4083
|
-
finished_at: deployment.finished_at,
|
|
4084
|
-
web_url: deployment.web_url,
|
|
4085
|
-
environment: deployment.environment
|
|
4086
|
-
? {
|
|
4087
|
-
id: deployment.environment.id,
|
|
4088
|
-
name: deployment.environment.name,
|
|
4089
|
-
slug: deployment.environment.slug,
|
|
4090
|
-
external_url: deployment.environment.external_url,
|
|
4091
|
-
state: deployment.environment.state,
|
|
4092
|
-
tier: deployment.environment.tier,
|
|
4093
|
-
}
|
|
4094
|
-
: undefined,
|
|
4095
|
-
deployable: deployment.deployable === null
|
|
4096
|
-
? null
|
|
4097
|
-
: deployment.deployable
|
|
4098
|
-
? {
|
|
4099
|
-
id: deployment.deployable.id,
|
|
4100
|
-
name: deployment.deployable.name,
|
|
4101
|
-
status: deployment.deployable.status,
|
|
4102
|
-
stage: deployment.deployable.stage,
|
|
4103
|
-
web_url: deployment.deployable.web_url,
|
|
4104
|
-
pipeline: deployment.deployable.pipeline
|
|
4105
|
-
? {
|
|
4106
|
-
id: deployment.deployable.pipeline.id,
|
|
4107
|
-
status: deployment.deployable.pipeline.status,
|
|
4108
|
-
ref: deployment.deployable.pipeline.ref,
|
|
4109
|
-
sha: deployment.deployable.pipeline.sha,
|
|
4110
|
-
web_url: deployment.deployable.pipeline.web_url,
|
|
4111
|
-
}
|
|
4112
|
-
: undefined,
|
|
4113
|
-
}
|
|
4114
|
-
: undefined,
|
|
4115
|
-
};
|
|
4116
|
-
}
|
|
4117
|
-
function sortDeploymentsByCreatedAtDesc(deployments) {
|
|
4118
|
-
return [...deployments].sort((a, b) => {
|
|
4119
|
-
const aTime = Date.parse(a.created_at);
|
|
4120
|
-
const bTime = Date.parse(b.created_at);
|
|
4121
|
-
if (Number.isNaN(aTime) || Number.isNaN(bTime)) {
|
|
4122
|
-
return b.created_at.localeCompare(a.created_at);
|
|
4123
|
-
}
|
|
4124
|
-
return bTime - aTime;
|
|
4125
|
-
});
|
|
4126
|
-
}
|
|
4127
4077
|
async function buildMergeRequestDeploymentSummary(projectId, mergeRequest) {
|
|
4128
4078
|
const lookupSha = mergeRequest.merge_commit_sha ?? mergeRequest.diff_refs?.head_sha ?? null;
|
|
4129
4079
|
if (!lookupSha) {
|
|
@@ -4566,43 +4516,6 @@ async function getMergeRequestApprovalsFallback(projectId, mergeRequestIid) {
|
|
|
4566
4516
|
await handleGitLabError(approvalsResponse);
|
|
4567
4517
|
return parseApprovalsResponse(await approvalsResponse.json());
|
|
4568
4518
|
}
|
|
4569
|
-
/**
|
|
4570
|
-
* Parse the response from POST /approve and POST /unapprove endpoints.
|
|
4571
|
-
* These endpoints return the approvals format (approved_by contains nested
|
|
4572
|
-
* { user: {...} } objects), which must be converted to the flat format
|
|
4573
|
-
* used by GitLabMergeRequestApprovalStateSchema.
|
|
4574
|
-
*/
|
|
4575
|
-
function parseApprovalsResponse(responseJson) {
|
|
4576
|
-
const parsedApprovals = GitLabMergeRequestApprovalsResponseSchema.parse(responseJson);
|
|
4577
|
-
const approvedByUsers = getUniqueApprovalUsers((parsedApprovals.approved_by || []).map(approvedByEntry => approvedByEntry.user));
|
|
4578
|
-
const approvedByUsernames = approvedByUsers.map(user => user.username);
|
|
4579
|
-
return GitLabMergeRequestApprovalStateSchema.parse({
|
|
4580
|
-
approved: parsedApprovals.approved,
|
|
4581
|
-
user_has_approved: parsedApprovals.user_has_approved,
|
|
4582
|
-
user_can_approve: parsedApprovals.user_can_approve,
|
|
4583
|
-
approved_by: approvedByUsers,
|
|
4584
|
-
approved_by_usernames: approvedByUsernames,
|
|
4585
|
-
source_endpoint: "approvals",
|
|
4586
|
-
});
|
|
4587
|
-
}
|
|
4588
|
-
function getUniqueApprovalUsers(users) {
|
|
4589
|
-
const uniqueUsers = new Map();
|
|
4590
|
-
for (const user of users) {
|
|
4591
|
-
if (!uniqueUsers.has(user.id)) {
|
|
4592
|
-
uniqueUsers.set(user.id, user);
|
|
4593
|
-
}
|
|
4594
|
-
}
|
|
4595
|
-
return [...uniqueUsers.values()];
|
|
4596
|
-
}
|
|
4597
|
-
function inferMergeRequestApproved(rules) {
|
|
4598
|
-
if (!rules || rules.length === 0) {
|
|
4599
|
-
return null;
|
|
4600
|
-
}
|
|
4601
|
-
if (rules.some(rule => typeof rule.approved !== "boolean")) {
|
|
4602
|
-
return null;
|
|
4603
|
-
}
|
|
4604
|
-
return rules.every(rule => rule.approved === true);
|
|
4605
|
-
}
|
|
4606
4519
|
/**
|
|
4607
4520
|
* Create a new note (comment) on an issue or merge request
|
|
4608
4521
|
* 📦 새로운 함수: createNote - 이슈 또는 병합 요청에 노트(댓글)를 추가하는 함수
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
// Pure helpers for the get_merge_request summaries (include_summaries) and the
|
|
2
|
+
// approve/unapprove/approval state results. The functions that call GitLab
|
|
3
|
+
// stay in index.ts.
|
|
4
|
+
import { GitLabMergeRequestApprovalsResponseSchema, GitLabMergeRequestApprovalStateSchema, } from "../schemas.js";
|
|
5
|
+
export const MERGE_REQUEST_DEPLOYMENT_SUMMARY_LIMIT = 10;
|
|
6
|
+
export function toMergeRequestDeploymentSummaryRecord(deployment) {
|
|
7
|
+
return {
|
|
8
|
+
id: deployment.id,
|
|
9
|
+
status: deployment.status,
|
|
10
|
+
ref: deployment.ref,
|
|
11
|
+
sha: deployment.sha,
|
|
12
|
+
created_at: deployment.created_at,
|
|
13
|
+
updated_at: deployment.updated_at,
|
|
14
|
+
finished_at: deployment.finished_at,
|
|
15
|
+
web_url: deployment.web_url,
|
|
16
|
+
environment: deployment.environment
|
|
17
|
+
? {
|
|
18
|
+
id: deployment.environment.id,
|
|
19
|
+
name: deployment.environment.name,
|
|
20
|
+
slug: deployment.environment.slug,
|
|
21
|
+
external_url: deployment.environment.external_url,
|
|
22
|
+
state: deployment.environment.state,
|
|
23
|
+
tier: deployment.environment.tier,
|
|
24
|
+
}
|
|
25
|
+
: undefined,
|
|
26
|
+
deployable: deployment.deployable === null
|
|
27
|
+
? null
|
|
28
|
+
: deployment.deployable
|
|
29
|
+
? {
|
|
30
|
+
id: deployment.deployable.id,
|
|
31
|
+
name: deployment.deployable.name,
|
|
32
|
+
status: deployment.deployable.status,
|
|
33
|
+
stage: deployment.deployable.stage,
|
|
34
|
+
web_url: deployment.deployable.web_url,
|
|
35
|
+
pipeline: deployment.deployable.pipeline
|
|
36
|
+
? {
|
|
37
|
+
id: deployment.deployable.pipeline.id,
|
|
38
|
+
status: deployment.deployable.pipeline.status,
|
|
39
|
+
ref: deployment.deployable.pipeline.ref,
|
|
40
|
+
sha: deployment.deployable.pipeline.sha,
|
|
41
|
+
web_url: deployment.deployable.pipeline.web_url,
|
|
42
|
+
}
|
|
43
|
+
: undefined,
|
|
44
|
+
}
|
|
45
|
+
: undefined,
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
export function sortDeploymentsByCreatedAtDesc(deployments) {
|
|
49
|
+
return [...deployments].sort((a, b) => {
|
|
50
|
+
const aTime = Date.parse(a.created_at);
|
|
51
|
+
const bTime = Date.parse(b.created_at);
|
|
52
|
+
if (Number.isNaN(aTime) || Number.isNaN(bTime)) {
|
|
53
|
+
return b.created_at.localeCompare(a.created_at);
|
|
54
|
+
}
|
|
55
|
+
return bTime - aTime;
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Parse the response from POST /approve and POST /unapprove endpoints.
|
|
60
|
+
* These endpoints return the approvals format (approved_by contains nested
|
|
61
|
+
* { user: {...} } objects), which must be converted to the flat format
|
|
62
|
+
* used by GitLabMergeRequestApprovalStateSchema.
|
|
63
|
+
*/
|
|
64
|
+
export function parseApprovalsResponse(responseJson) {
|
|
65
|
+
const parsedApprovals = GitLabMergeRequestApprovalsResponseSchema.parse(responseJson);
|
|
66
|
+
const approvedByUsers = getUniqueApprovalUsers((parsedApprovals.approved_by || []).map(approvedByEntry => approvedByEntry.user));
|
|
67
|
+
const approvedByUsernames = approvedByUsers.map(user => user.username);
|
|
68
|
+
return GitLabMergeRequestApprovalStateSchema.parse({
|
|
69
|
+
approved: parsedApprovals.approved,
|
|
70
|
+
user_has_approved: parsedApprovals.user_has_approved,
|
|
71
|
+
user_can_approve: parsedApprovals.user_can_approve,
|
|
72
|
+
approved_by: approvedByUsers,
|
|
73
|
+
approved_by_usernames: approvedByUsernames,
|
|
74
|
+
source_endpoint: "approvals",
|
|
75
|
+
});
|
|
76
|
+
}
|
|
77
|
+
export function getUniqueApprovalUsers(users) {
|
|
78
|
+
const uniqueUsers = new Map();
|
|
79
|
+
for (const user of users) {
|
|
80
|
+
if (!uniqueUsers.has(user.id)) {
|
|
81
|
+
uniqueUsers.set(user.id, user);
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
return [...uniqueUsers.values()];
|
|
85
|
+
}
|
|
86
|
+
export function inferMergeRequestApproved(rules) {
|
|
87
|
+
if (!rules || rules.length === 0) {
|
|
88
|
+
return null;
|
|
89
|
+
}
|
|
90
|
+
if (rules.some(rule => typeof rule.approved !== "boolean")) {
|
|
91
|
+
return null;
|
|
92
|
+
}
|
|
93
|
+
return rules.every(rule => rule.approved === true);
|
|
94
|
+
}
|
package/package.json
CHANGED