package user import ( "context" "errors" "fmt" "git.lethalbits.com/lethalbits/gitea-mcp/pkg/gitea" "git.lethalbits.com/lethalbits/gitea-mcp/pkg/log" "git.lethalbits.com/lethalbits/gitea-mcp/pkg/params" "git.lethalbits.com/lethalbits/gitea-mcp/pkg/to" gitea_sdk "code.gitea.io/sdk/gitea" "github.com/mark3labs/mcp-go/mcp" "github.com/mark3labs/mcp-go/server" ) const ( ListMyBlocksToolName = "list_my_blocks" CheckUserBlockToolName = "check_user_block" BlockUserToolName = "block_user" UnblockUserToolName = "unblock_user" ) var ( ListMyBlocksTool = mcp.NewTool( ListMyBlocksToolName, mcp.WithDescription("List users blocked by the authenticated user"), mcp.WithNumber("page", mcp.Description("page number"), mcp.DefaultNumber(1)), mcp.WithNumber("pageSize", mcp.Description("page size"), mcp.DefaultNumber(100)), ) CheckUserBlockTool = mcp.NewTool( CheckUserBlockToolName, mcp.WithDescription("Check if the authenticated user has blocked a user"), mcp.WithString("username", mcp.Required(), mcp.Description("username to check")), ) BlockUserTool = mcp.NewTool( BlockUserToolName, mcp.WithDescription("Block a user"), mcp.WithString("username", mcp.Required(), mcp.Description("username to block")), ) UnblockUserTool = mcp.NewTool( UnblockUserToolName, mcp.WithDescription("Unblock a user"), mcp.WithString("username", mcp.Required(), mcp.Description("username to unblock")), ) ) func init() { Tool.RegisterRead(server.ServerTool{Tool: ListMyBlocksTool, Handler: ListMyBlocksFn}) Tool.RegisterRead(server.ServerTool{Tool: CheckUserBlockTool, Handler: CheckUserBlockFn}) Tool.RegisterWrite(server.ServerTool{Tool: BlockUserTool, Handler: BlockUserFn}) Tool.RegisterWrite(server.ServerTool{Tool: UnblockUserTool, Handler: UnblockUserFn}) } func ListMyBlocksFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) { log.Debugf("Called ListMyBlocksFn") page := params.GetOptionalInt(req.GetArguments(), "page", 1) pageSize := params.GetOptionalInt(req.GetArguments(), "pageSize", 100) client, err := gitea.ClientFromContext(ctx) if err != nil { return to.ErrorResult(fmt.Errorf("get gitea client err: %v", err)) } users, _, err := client.ListMyBlocks(gitea_sdk.ListUserBlocksOptions{ ListOptions: gitea_sdk.ListOptions{Page: int(page), PageSize: int(pageSize)}, }) if err != nil { return to.ErrorResult(fmt.Errorf("list my blocks err: %v", err)) } return to.TextResult(users) } func CheckUserBlockFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) { log.Debugf("Called CheckUserBlockFn") username, ok := req.GetArguments()["username"].(string) if !ok { return to.ErrorResult(errors.New("username is required")) } client, err := gitea.ClientFromContext(ctx) if err != nil { return to.ErrorResult(fmt.Errorf("get gitea client err: %v", err)) } isBlocked, _, err := client.CheckUserBlock(username) if err != nil { return to.ErrorResult(fmt.Errorf("check block %s err: %v", username, err)) } return to.TextResult(map[string]any{"username": username, "is_blocked": isBlocked}) } func BlockUserFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) { log.Debugf("Called BlockUserFn") username, ok := req.GetArguments()["username"].(string) if !ok { return to.ErrorResult(errors.New("username is required")) } client, err := gitea.ClientFromContext(ctx) if err != nil { return to.ErrorResult(fmt.Errorf("get gitea client err: %v", err)) } _, err = client.BlockUser(username) if err != nil { return to.ErrorResult(fmt.Errorf("block user %s err: %v", username, err)) } return to.TextResult(map[string]string{"status": "blocked", "username": username}) } func UnblockUserFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) { log.Debugf("Called UnblockUserFn") username, ok := req.GetArguments()["username"].(string) if !ok { return to.ErrorResult(errors.New("username is required")) } client, err := gitea.ClientFromContext(ctx) if err != nil { return to.ErrorResult(fmt.Errorf("get gitea client err: %v", err)) } _, err = client.UnblockUser(username) if err != nil { return to.ErrorResult(fmt.Errorf("unblock user %s err: %v", username, err)) } return to.TextResult(map[string]string{"status": "unblocked", "username": username}) }