@@ -41,6 +41,7 @@ const (
4141 actionsActionTypeRerunWorkflowRun
4242 actionsActionTypeRerunFailedJobs
4343 actionsActionTypeCancelWorkflowRun
44+ actionsActionTypeDeleteWorkflowRunLogs
4445)
4546
4647var actionsResourceTypes = map [actionsActionType ]string {
@@ -59,6 +60,7 @@ var actionsResourceTypes = map[actionsActionType]string{
5960 actionsActionTypeRerunWorkflowRun : "rerun_workflow_run" ,
6061 actionsActionTypeRerunFailedJobs : "rerun_failed_jobs" ,
6162 actionsActionTypeCancelWorkflowRun : "cancel_workflow_run" ,
63+ actionsActionTypeDeleteWorkflowRunLogs : "delete_workflow_run_logs" ,
6264}
6365
6466func (r actionsActionType ) String () string {
@@ -406,24 +408,23 @@ Use this tool to get details about individual workflows, workflow runs, jobs, an
406408
407409func ActionsRunTrigger (getClient GetClientFn , t translations.TranslationHelperFunc ) (tool mcp.Tool , handler server.ToolHandlerFunc ) {
408410 return mcp .NewTool ("actions_run_trigger" ,
409- mcp .WithDescription (t ("TOOL_ACTIONS_TRIGGER_DESCRIPTION" , "Trigger GitHub Actions workflow actions for a specific workflow run ." )),
411+ mcp .WithDescription (t ("TOOL_ACTIONS_TRIGGER_DESCRIPTION" , "Trigger GitHub Actions workflow actions, including running, re-running, cancelling, and deleting workflow runs ." )),
410412 mcp .WithToolAnnotation (mcp.ToolAnnotation {
411- Title : t ("TOOL_ACTIONS_TRIGGER_USER_TITLE" , "Trigger GitHub Actions workflow actions for a specific workflow run." ),
412- ReadOnlyHint : ToBoolPtr (false ),
413+ Title : t ("TOOL_ACTIONS_TRIGGER_USER_TITLE" , "Trigger GitHub Actions workflow actions" ),
414+ ReadOnlyHint : ToBoolPtr (false ),
415+ DestructiveHint : ToBoolPtr (false ),
413416 }),
414417 mcp .WithString ("action" ,
415418 mcp .Required (),
416419 mcp .Description ("The action to trigger" ),
417420 mcp .Enum (
421+ actionsActionTypeRunWorkflow .String (),
418422 actionsActionTypeRerunWorkflowRun .String (),
419423 actionsActionTypeRerunFailedJobs .String (),
420424 actionsActionTypeCancelWorkflowRun .String (),
425+ actionsActionTypeDeleteWorkflowRunLogs .String (),
421426 ),
422427 ),
423- mcp .WithNumber ("run_id" ,
424- mcp .Required (),
425- mcp .Description ("The ID of the workflow run to trigger" ),
426- ),
427428 mcp .WithString ("owner" ,
428429 mcp .Required (),
429430 mcp .Description (DescriptionRepositoryOwner ),
@@ -432,6 +433,18 @@ func ActionsRunTrigger(getClient GetClientFn, t translations.TranslationHelperFu
432433 mcp .Required (),
433434 mcp .Description (DescriptionRepositoryName ),
434435 ),
436+ mcp .WithString ("workflow_id" ,
437+ mcp .Description ("The workflow ID (numeric) or workflow file name (e.g., main.yml, ci.yaml). Required for 'run_workflow' action." ),
438+ ),
439+ mcp .WithString ("ref" ,
440+ mcp .Description ("The git reference for the workflow. The reference can be a branch or tag name. Required for 'run_workflow' action." ),
441+ ),
442+ mcp .WithObject ("inputs" ,
443+ mcp .Description ("Inputs the workflow accepts. Only used for 'run_workflow' action." ),
444+ ),
445+ mcp .WithNumber ("run_id" ,
446+ mcp .Description ("The ID of the workflow run. Required for all actions except 'run_workflow'." ),
447+ ),
435448 ),
436449 func (ctx context.Context , request mcp.CallToolRequest ) (* mcp.CallToolResult , error ) {
437450 owner , err := RequiredParam [string ](request , "owner" )
@@ -452,9 +465,29 @@ func ActionsRunTrigger(getClient GetClientFn, t translations.TranslationHelperFu
452465 return mcp .NewToolResultError (fmt .Sprintf ("unknown action: %s" , actionTypeStr )), nil
453466 }
454467
455- runID , err := RequiredInt (request , "run_id" )
456- if err != nil {
457- return mcp .NewToolResultError (err .Error ()), nil
468+ // Get optional parameters
469+ workflowID , _ := OptionalParam [string ](request , "workflow_id" )
470+ ref , _ := OptionalParam [string ](request , "ref" )
471+ runID , _ := OptionalIntParam (request , "run_id" )
472+
473+ // Get optional inputs parameter
474+ var inputs map [string ]interface {}
475+ if requestInputs , ok := request .GetArguments ()["inputs" ]; ok {
476+ if inputsMap , ok := requestInputs .(map [string ]interface {}); ok {
477+ inputs = inputsMap
478+ }
479+ }
480+
481+ // Validate required parameters based on action type
482+ if resourceType == actionsActionTypeRunWorkflow {
483+ if workflowID == "" {
484+ return mcp .NewToolResultError ("workflow_id is required for run_workflow action" ), nil
485+ }
486+ if ref == "" {
487+ return mcp .NewToolResultError ("ref is required for run_workflow action" ), nil
488+ }
489+ } else if runID == 0 {
490+ return mcp .NewToolResultError ("run_id is required for this action" ), nil
458491 }
459492
460493 client , err := getClient (ctx )
@@ -463,12 +496,16 @@ func ActionsRunTrigger(getClient GetClientFn, t translations.TranslationHelperFu
463496 }
464497
465498 switch resourceType {
499+ case actionsActionTypeRunWorkflow :
500+ return runWorkflow (ctx , client , request , owner , repo , workflowID , ref , inputs )
466501 case actionsActionTypeRerunWorkflowRun :
467502 return rerunWorkflowRun (ctx , client , request , owner , repo , int64 (runID ))
468503 case actionsActionTypeRerunFailedJobs :
469504 return rerunFailedJobs (ctx , client , request , owner , repo , int64 (runID ))
470505 case actionsActionTypeCancelWorkflowRun :
471506 return cancelWorkflowRun (ctx , client , request , owner , repo , int64 (runID ))
507+ case actionsActionTypeDeleteWorkflowRunLogs :
508+ return deleteWorkflowRunLogs (ctx , client , request , owner , repo , int64 (runID ))
472509 case actionsActionTypeUnknown :
473510 return mcp .NewToolResultError (fmt .Sprintf ("unknown action: %s" , actionTypeStr )), nil
474511 default :
@@ -684,103 +721,46 @@ func listWorkflows(ctx context.Context, client *github.Client, _ mcp.CallToolReq
684721 return mcp .NewToolResultText (string (r )), nil
685722}
686723
687- // RunWorkflow creates a tool to run an Actions workflow
688- func RunWorkflow (getClient GetClientFn , t translations.TranslationHelperFunc ) (tool mcp.Tool , handler server.ToolHandlerFunc ) {
689- return mcp .NewTool ("run_workflow" ,
690- mcp .WithDescription (t ("TOOL_RUN_WORKFLOW_DESCRIPTION" , "Run an Actions workflow by workflow ID or filename" )),
691- mcp .WithToolAnnotation (mcp.ToolAnnotation {
692- Title : t ("TOOL_RUN_WORKFLOW_USER_TITLE" , "Run workflow" ),
693- ReadOnlyHint : ToBoolPtr (false ),
694- }),
695- mcp .WithString ("owner" ,
696- mcp .Required (),
697- mcp .Description (DescriptionRepositoryOwner ),
698- ),
699- mcp .WithString ("repo" ,
700- mcp .Required (),
701- mcp .Description (DescriptionRepositoryName ),
702- ),
703- mcp .WithString ("workflow_id" ,
704- mcp .Required (),
705- mcp .Description ("The workflow ID (numeric) or workflow file name (e.g., main.yml, ci.yaml)" ),
706- ),
707- mcp .WithString ("ref" ,
708- mcp .Required (),
709- mcp .Description ("The git reference for the workflow. The reference can be a branch or tag name." ),
710- ),
711- mcp .WithObject ("inputs" ,
712- mcp .Description ("Inputs the workflow accepts" ),
713- ),
714- ),
715- func (ctx context.Context , request mcp.CallToolRequest ) (* mcp.CallToolResult , error ) {
716- owner , err := RequiredParam [string ](request , "owner" )
717- if err != nil {
718- return mcp .NewToolResultError (err .Error ()), nil
719- }
720- repo , err := RequiredParam [string ](request , "repo" )
721- if err != nil {
722- return mcp .NewToolResultError (err .Error ()), nil
723- }
724- workflowID , err := RequiredParam [string ](request , "workflow_id" )
725- if err != nil {
726- return mcp .NewToolResultError (err .Error ()), nil
727- }
728- ref , err := RequiredParam [string ](request , "ref" )
729- if err != nil {
730- return mcp .NewToolResultError (err .Error ()), nil
731- }
732-
733- // Get optional inputs parameter
734- var inputs map [string ]interface {}
735- if requestInputs , ok := request .GetArguments ()["inputs" ]; ok {
736- if inputsMap , ok := requestInputs .(map [string ]interface {}); ok {
737- inputs = inputsMap
738- }
739- }
740-
741- client , err := getClient (ctx )
742- if err != nil {
743- return nil , fmt .Errorf ("failed to get GitHub client: %w" , err )
744- }
724+ // runWorkflow runs an Actions workflow by workflow ID or filename
725+ func runWorkflow (ctx context.Context , client * github.Client , _ mcp.CallToolRequest , owner , repo , workflowID , ref string , inputs map [string ]interface {}) (* mcp.CallToolResult , error ) {
726+ event := github.CreateWorkflowDispatchEventRequest {
727+ Ref : ref ,
728+ Inputs : inputs ,
729+ }
745730
746- event := github.CreateWorkflowDispatchEventRequest {
747- Ref : ref ,
748- Inputs : inputs ,
749- }
731+ var resp * github.Response
732+ var err error
733+ var workflowType string
750734
751- var resp * github.Response
752- var workflowType string
735+ if workflowIDInt , parseErr := strconv .ParseInt (workflowID , 10 , 64 ); parseErr == nil {
736+ resp , err = client .Actions .CreateWorkflowDispatchEventByID (ctx , owner , repo , workflowIDInt , event )
737+ workflowType = "workflow_id"
738+ } else {
739+ resp , err = client .Actions .CreateWorkflowDispatchEventByFileName (ctx , owner , repo , workflowID , event )
740+ workflowType = "workflow_file"
741+ }
753742
754- if workflowIDInt , parseErr := strconv .ParseInt (workflowID , 10 , 64 ); parseErr == nil {
755- resp , err = client .Actions .CreateWorkflowDispatchEventByID (ctx , owner , repo , workflowIDInt , event )
756- workflowType = "workflow_id"
757- } else {
758- resp , err = client .Actions .CreateWorkflowDispatchEventByFileName (ctx , owner , repo , workflowID , event )
759- workflowType = "workflow_file"
760- }
743+ if err != nil {
744+ return ghErrors .NewGitHubAPIErrorResponse (ctx , "failed to run workflow" , resp , err ), nil
745+ }
746+ defer func () { _ = resp .Body .Close () }()
761747
762- if err != nil {
763- return nil , fmt .Errorf ("failed to run workflow: %w" , err )
764- }
765- defer func () { _ = resp .Body .Close () }()
766-
767- result := map [string ]any {
768- "message" : "Workflow run has been queued" ,
769- "workflow_type" : workflowType ,
770- "workflow_id" : workflowID ,
771- "ref" : ref ,
772- "inputs" : inputs ,
773- "status" : resp .Status ,
774- "status_code" : resp .StatusCode ,
775- }
748+ result := map [string ]any {
749+ "message" : "Workflow run has been queued" ,
750+ "workflow_type" : workflowType ,
751+ "workflow_id" : workflowID ,
752+ "ref" : ref ,
753+ "inputs" : inputs ,
754+ "status" : resp .Status ,
755+ "status_code" : resp .StatusCode ,
756+ }
776757
777- r , err := json .Marshal (result )
778- if err != nil {
779- return nil , fmt .Errorf ("failed to marshal response: %w" , err )
780- }
758+ r , err := json .Marshal (result )
759+ if err != nil {
760+ return nil , fmt .Errorf ("failed to marshal response: %w" , err )
761+ }
781762
782- return mcp .NewToolResultText (string (r )), nil
783- }
763+ return mcp .NewToolResultText (string (r )), nil
784764}
785765
786766// GetWorkflowRunLogs creates a tool to download logs for a specific workflow run
@@ -1060,68 +1040,27 @@ func cancelWorkflowRun(ctx context.Context, client *github.Client, _ mcp.CallToo
10601040 return mcp .NewToolResultText (string (r )), nil
10611041}
10621042
1063- // DeleteWorkflowRunLogs creates a tool to delete logs for a workflow run
1064- func DeleteWorkflowRunLogs (getClient GetClientFn , t translations.TranslationHelperFunc ) (tool mcp.Tool , handler server.ToolHandlerFunc ) {
1065- return mcp .NewTool ("delete_workflow_run_logs" ,
1066- mcp .WithDescription (t ("TOOL_DELETE_WORKFLOW_RUN_LOGS_DESCRIPTION" , "Delete logs for a workflow run" )),
1067- mcp .WithToolAnnotation (mcp.ToolAnnotation {
1068- Title : t ("TOOL_DELETE_WORKFLOW_RUN_LOGS_USER_TITLE" , "Delete workflow logs" ),
1069- ReadOnlyHint : ToBoolPtr (false ),
1070- DestructiveHint : ToBoolPtr (true ),
1071- }),
1072- mcp .WithString ("owner" ,
1073- mcp .Required (),
1074- mcp .Description (DescriptionRepositoryOwner ),
1075- ),
1076- mcp .WithString ("repo" ,
1077- mcp .Required (),
1078- mcp .Description (DescriptionRepositoryName ),
1079- ),
1080- mcp .WithNumber ("run_id" ,
1081- mcp .Required (),
1082- mcp .Description ("The unique identifier of the workflow run" ),
1083- ),
1084- ),
1085- func (ctx context.Context , request mcp.CallToolRequest ) (* mcp.CallToolResult , error ) {
1086- owner , err := RequiredParam [string ](request , "owner" )
1087- if err != nil {
1088- return mcp .NewToolResultError (err .Error ()), nil
1089- }
1090- repo , err := RequiredParam [string ](request , "repo" )
1091- if err != nil {
1092- return mcp .NewToolResultError (err .Error ()), nil
1093- }
1094- runIDInt , err := RequiredInt (request , "run_id" )
1095- if err != nil {
1096- return mcp .NewToolResultError (err .Error ()), nil
1097- }
1098- runID := int64 (runIDInt )
1099-
1100- client , err := getClient (ctx )
1101- if err != nil {
1102- return nil , fmt .Errorf ("failed to get GitHub client: %w" , err )
1103- }
1104-
1105- resp , err := client .Actions .DeleteWorkflowRunLogs (ctx , owner , repo , runID )
1106- if err != nil {
1107- return ghErrors .NewGitHubAPIErrorResponse (ctx , "failed to delete workflow run logs" , resp , err ), nil
1108- }
1109- defer func () { _ = resp .Body .Close () }()
1043+ // deleteWorkflowRunLogs deletes logs for a workflow run
1044+ func deleteWorkflowRunLogs (ctx context.Context , client * github.Client , _ mcp.CallToolRequest , owner , repo string , runID int64 ) (* mcp.CallToolResult , error ) {
1045+ resp , err := client .Actions .DeleteWorkflowRunLogs (ctx , owner , repo , runID )
1046+ if err != nil {
1047+ return ghErrors .NewGitHubAPIErrorResponse (ctx , "failed to delete workflow run logs" , resp , err ), nil
1048+ }
1049+ defer func () { _ = resp .Body .Close () }()
11101050
1111- result := map [string ]any {
1112- "message" : "Workflow run logs have been deleted" ,
1113- "run_id" : runID ,
1114- "status" : resp .Status ,
1115- "status_code" : resp .StatusCode ,
1116- }
1051+ result := map [string ]any {
1052+ "message" : "Workflow run logs have been deleted" ,
1053+ "run_id" : runID ,
1054+ "status" : resp .Status ,
1055+ "status_code" : resp .StatusCode ,
1056+ }
11171057
1118- r , err := json .Marshal (result )
1119- if err != nil {
1120- return nil , fmt .Errorf ("failed to marshal response: %w" , err )
1121- }
1058+ r , err := json .Marshal (result )
1059+ if err != nil {
1060+ return nil , fmt .Errorf ("failed to marshal response: %w" , err )
1061+ }
11221062
1123- return mcp .NewToolResultText (string (r )), nil
1124- }
1063+ return mcp .NewToolResultText (string (r )), nil
11251064}
11261065
11271066// GetWorkflowRunUsage creates a tool to get usage metrics for a workflow run
0 commit comments