mirror of
https://gitea.com/gitea/gitea-mcp.git
synced 2026-08-03 15:49:23 +02:00
refactor!: replace mcp-go with the official MCP Go SDK
- Swap the mark3labs MCP dependency for modelcontextprotocol/go-sdk v1.7.0 - Add a declarative tool definition and JSON Schema builder to the tool package - Adapt registered tools to the official low-level handler, recovering panics and mapping failures to JSON-RPC errors - Narrow tool handlers to take a plain argument map instead of an SDK request type - Rewire stdio and HTTP transports onto the official server, moving Authorization parsing into receiving middleware - Add a golden contract test that locks the exposed tool schemas, plus SDK integration and helper tests - Add a test target and run it in the pull request workflow BREAKING CHANGE: The exported helpers change signature. Tool.RegisterRead and Tool.RegisterWrite now take tool.ServerTool instead of server.ServerTool, and the annotation constructors return *mcp.ToolAnnotations from the official SDK. Callers must build tool definitions with tool.NewDefinition and handlers with the func(context.Context, map[string]any) signature. The 30-second SSE heartbeat is removed because the official SDK has no equivalent. ServerOptions.KeepAlive is deliberately not used as a substitute, since it sends MCP ping requests and ping is removed in protocol 2026. HTTP stays stateless=false, so new clients negotiate at most 2025-11-25. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
+27
-31
@@ -11,8 +11,7 @@ import (
|
||||
"gitea.com/gitea/gitea-mcp/pkg/tool"
|
||||
|
||||
gitea_sdk "gitea.dev/sdk"
|
||||
"github.com/mark3labs/mcp-go/mcp"
|
||||
"github.com/mark3labs/mcp-go/server"
|
||||
"github.com/modelcontextprotocol/go-sdk/mcp"
|
||||
)
|
||||
|
||||
// BranchTool holds the branch-related tools (scope "branch").
|
||||
@@ -25,53 +24,52 @@ const (
|
||||
)
|
||||
|
||||
var (
|
||||
CreateBranchTool = mcp.NewTool(
|
||||
CreateBranchTool = tool.NewDefinition(
|
||||
CreateBranchToolName,
|
||||
mcp.WithDescription("Create a new branch in a repository, optionally from a specific source branch (defaults to the repository's default branch)."),
|
||||
mcp.WithToolAnnotation(annotation.Write("Create a new branch")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("branch", mcp.Required()),
|
||||
mcp.WithString("old_branch", mcp.Description("source branch (default: repo default)")),
|
||||
"Create a new branch in a repository, optionally from a specific source branch (defaults to the repository's default branch).",
|
||||
annotation.Write("Create a new branch"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("branch", tool.Required()),
|
||||
tool.String("old_branch", tool.Description("source branch (default: repo default)")),
|
||||
)
|
||||
|
||||
DeleteBranchTool = mcp.NewTool(
|
||||
DeleteBranchTool = tool.NewDefinition(
|
||||
DeleteBranchToolName,
|
||||
mcp.WithDescription("Permanently delete a branch from a repository. This action is destructive and cannot be undone."),
|
||||
mcp.WithToolAnnotation(annotation.Destructive("Delete a branch")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("branch", mcp.Required()),
|
||||
"Permanently delete a branch from a repository. This action is destructive and cannot be undone.",
|
||||
annotation.Destructive("Delete a branch"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("branch", tool.Required()),
|
||||
)
|
||||
|
||||
ListBranchesTool = mcp.NewTool(
|
||||
ListBranchesTool = tool.NewDefinition(
|
||||
ListBranchesToolName,
|
||||
mcp.WithDescription("List all branches in a repository, paginated."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("List repository branches")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithNumber("page", mcp.Description(params.PageDesc), mcp.DefaultNumber(1)),
|
||||
mcp.WithNumber("per_page", mcp.Description(params.PaginationDesc), mcp.DefaultNumber(30)),
|
||||
"List all branches in a repository, paginated.",
|
||||
annotation.ReadOnly("List repository branches"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.Number("page", tool.Description(params.PageDesc), tool.Default(1)),
|
||||
tool.Number("per_page", tool.Description(params.PaginationDesc), tool.Default(30)),
|
||||
)
|
||||
)
|
||||
|
||||
func init() {
|
||||
BranchTool.RegisterWrite(server.ServerTool{
|
||||
BranchTool.RegisterWrite(tool.ServerTool{
|
||||
Tool: CreateBranchTool,
|
||||
Handler: CreateBranchFn,
|
||||
})
|
||||
BranchTool.RegisterWrite(server.ServerTool{
|
||||
BranchTool.RegisterWrite(tool.ServerTool{
|
||||
Tool: DeleteBranchTool,
|
||||
Handler: DeleteBranchFn,
|
||||
})
|
||||
BranchTool.RegisterRead(server.ServerTool{
|
||||
BranchTool.RegisterRead(tool.ServerTool{
|
||||
Tool: ListBranchesTool,
|
||||
Handler: ListBranchesFn,
|
||||
})
|
||||
}
|
||||
|
||||
func CreateBranchFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func CreateBranchFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -101,8 +99,7 @@ func CreateBranchFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallTool
|
||||
return to.TextResult("Branch Created")
|
||||
}
|
||||
|
||||
func DeleteBranchFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func DeleteBranchFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -127,8 +124,7 @@ func DeleteBranchFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallTool
|
||||
return to.TextResult("Branch Deleted")
|
||||
}
|
||||
|
||||
func ListBranchesFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func ListBranchesFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
|
||||
+20
-23
@@ -11,8 +11,7 @@ import (
|
||||
"gitea.com/gitea/gitea-mcp/pkg/tool"
|
||||
|
||||
gitea_sdk "gitea.dev/sdk"
|
||||
"github.com/mark3labs/mcp-go/mcp"
|
||||
"github.com/mark3labs/mcp-go/server"
|
||||
"github.com/modelcontextprotocol/go-sdk/mcp"
|
||||
)
|
||||
|
||||
// CommitTool holds the commit-related tools (scope "commit").
|
||||
@@ -24,41 +23,40 @@ const (
|
||||
)
|
||||
|
||||
var (
|
||||
ListRepoCommitsTool = mcp.NewTool(
|
||||
ListRepoCommitsTool = tool.NewDefinition(
|
||||
ListRepoCommitsToolName,
|
||||
mcp.WithDescription("List commits in a repository, optionally starting from a specific branch or SHA and filtered to commits touching a given file path."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("List repository commits")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("sha", mcp.Description("starting SHA or branch")),
|
||||
mcp.WithString("path", mcp.Description("only commits touching this path")),
|
||||
mcp.WithNumber("page", mcp.Description(params.PageDesc), mcp.DefaultNumber(1), mcp.Min(1)),
|
||||
mcp.WithNumber("per_page", mcp.Description(params.PaginationDesc), mcp.DefaultNumber(30), mcp.Min(1)),
|
||||
"List commits in a repository, optionally starting from a specific branch or SHA and filtered to commits touching a given file path.",
|
||||
annotation.ReadOnly("List repository commits"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("sha", tool.Description("starting SHA or branch")),
|
||||
tool.String("path", tool.Description("only commits touching this path")),
|
||||
tool.Number("page", tool.Description(params.PageDesc), tool.Default(1), tool.Minimum(1)),
|
||||
tool.Number("per_page", tool.Description(params.PaginationDesc), tool.Default(30), tool.Minimum(1)),
|
||||
)
|
||||
|
||||
GetCommitTool = mcp.NewTool(
|
||||
GetCommitTool = tool.NewDefinition(
|
||||
GetCommitToolName,
|
||||
mcp.WithDescription("Get details for a single commit in a repository by its SHA."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("Get commit details")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("sha", mcp.Required()),
|
||||
"Get details for a single commit in a repository by its SHA.",
|
||||
annotation.ReadOnly("Get commit details"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("sha", tool.Required()),
|
||||
)
|
||||
)
|
||||
|
||||
func init() {
|
||||
CommitTool.RegisterRead(server.ServerTool{
|
||||
CommitTool.RegisterRead(tool.ServerTool{
|
||||
Tool: ListRepoCommitsTool,
|
||||
Handler: ListRepoCommitsFn,
|
||||
})
|
||||
CommitTool.RegisterRead(server.ServerTool{
|
||||
CommitTool.RegisterRead(tool.ServerTool{
|
||||
Tool: GetCommitTool,
|
||||
Handler: GetCommitFn,
|
||||
})
|
||||
}
|
||||
|
||||
func ListRepoCommitsFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func ListRepoCommitsFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -89,8 +87,7 @@ func ListRepoCommitsFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallT
|
||||
return to.TextResult(slimCommits(commits))
|
||||
}
|
||||
|
||||
func GetCommitFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func GetCommitFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
|
||||
+44
-49
@@ -15,8 +15,7 @@ import (
|
||||
"gitea.com/gitea/gitea-mcp/pkg/tool"
|
||||
|
||||
gitea_sdk "gitea.dev/sdk"
|
||||
"github.com/mark3labs/mcp-go/mcp"
|
||||
"github.com/mark3labs/mcp-go/server"
|
||||
"github.com/modelcontextprotocol/go-sdk/mcp"
|
||||
)
|
||||
|
||||
// FileTool holds the file-related tools (scope "file").
|
||||
@@ -30,68 +29,68 @@ const (
|
||||
)
|
||||
|
||||
var (
|
||||
GetFileContentTool = mcp.NewTool(
|
||||
GetFileContentTool = tool.NewDefinition(
|
||||
GetFileToolName,
|
||||
mcp.WithDescription("Get file content and metadata"),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("Get file content")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("ref", mcp.Required(), mcp.Description("branch, tag, or commit SHA")),
|
||||
mcp.WithString("path", mcp.Required()),
|
||||
mcp.WithBoolean("withLines", mcp.Description("return numbered lines")),
|
||||
"Get file content and metadata",
|
||||
annotation.ReadOnly("Get file content"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("ref", tool.Required(), tool.Description("branch, tag, or commit SHA")),
|
||||
tool.String("path", tool.Required()),
|
||||
tool.Boolean("withLines", tool.Description("return numbered lines")),
|
||||
)
|
||||
|
||||
GetDirContentTool = mcp.NewTool(
|
||||
GetDirContentTool = tool.NewDefinition(
|
||||
GetDirToolName,
|
||||
mcp.WithDescription("List the entries (files and subdirectories) in a repository directory at a given ref (branch, tag, or commit SHA)."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("Get directory contents")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("ref", mcp.Required(), mcp.Description("branch, tag, or commit SHA")),
|
||||
mcp.WithString("path", mcp.Required()),
|
||||
"List the entries (files and subdirectories) in a repository directory at a given ref (branch, tag, or commit SHA).",
|
||||
annotation.ReadOnly("Get directory contents"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("ref", tool.Required(), tool.Description("branch, tag, or commit SHA")),
|
||||
tool.String("path", tool.Required()),
|
||||
)
|
||||
|
||||
CreateOrUpdateFileTool = mcp.NewTool(
|
||||
CreateOrUpdateFileTool = tool.NewDefinition(
|
||||
CreateOrUpdateFileToolName,
|
||||
mcp.WithDescription("Create or update a file (provide sha to update an existing file)."),
|
||||
mcp.WithToolAnnotation(annotation.Write("Create or update a file")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("path", mcp.Required()),
|
||||
mcp.WithString("content", mcp.Required()),
|
||||
mcp.WithString("message", mcp.Required(), mcp.Description("commit message")),
|
||||
mcp.WithString("branch_name", mcp.Required()),
|
||||
mcp.WithString("sha", mcp.Description("existing file SHA (omit to create)")),
|
||||
mcp.WithString("new_branch_name", mcp.Description("new branch (create only)")),
|
||||
"Create or update a file (provide sha to update an existing file).",
|
||||
annotation.Write("Create or update a file"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("path", tool.Required()),
|
||||
tool.String("content", tool.Required()),
|
||||
tool.String("message", tool.Required(), tool.Description("commit message")),
|
||||
tool.String("branch_name", tool.Required()),
|
||||
tool.String("sha", tool.Description("existing file SHA (omit to create)")),
|
||||
tool.String("new_branch_name", tool.Description("new branch (create only)")),
|
||||
)
|
||||
|
||||
DeleteFileTool = mcp.NewTool(
|
||||
DeleteFileTool = tool.NewDefinition(
|
||||
DeleteFileToolName,
|
||||
mcp.WithDescription("Delete a file from a repository by committing the removal to a branch. Requires the file's current SHA and a commit message."),
|
||||
mcp.WithToolAnnotation(annotation.Destructive("Delete a file")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("path", mcp.Required()),
|
||||
mcp.WithString("message", mcp.Required(), mcp.Description("commit message")),
|
||||
mcp.WithString("branch_name", mcp.Required()),
|
||||
mcp.WithString("sha", mcp.Required()),
|
||||
"Delete a file from a repository by committing the removal to a branch. Requires the file's current SHA and a commit message.",
|
||||
annotation.Destructive("Delete a file"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("path", tool.Required()),
|
||||
tool.String("message", tool.Required(), tool.Description("commit message")),
|
||||
tool.String("branch_name", tool.Required()),
|
||||
tool.String("sha", tool.Required()),
|
||||
)
|
||||
)
|
||||
|
||||
func init() {
|
||||
FileTool.RegisterRead(server.ServerTool{
|
||||
FileTool.RegisterRead(tool.ServerTool{
|
||||
Tool: GetFileContentTool,
|
||||
Handler: GetFileContentFn,
|
||||
})
|
||||
FileTool.RegisterRead(server.ServerTool{
|
||||
FileTool.RegisterRead(tool.ServerTool{
|
||||
Tool: GetDirContentTool,
|
||||
Handler: GetDirContentFn,
|
||||
})
|
||||
FileTool.RegisterWrite(server.ServerTool{
|
||||
FileTool.RegisterWrite(tool.ServerTool{
|
||||
Tool: CreateOrUpdateFileTool,
|
||||
Handler: CreateOrUpdateFileFn,
|
||||
})
|
||||
FileTool.RegisterWrite(server.ServerTool{
|
||||
FileTool.RegisterWrite(tool.ServerTool{
|
||||
Tool: DeleteFileTool,
|
||||
Handler: DeleteFileFn,
|
||||
})
|
||||
@@ -102,8 +101,7 @@ type ContentLine struct {
|
||||
Content string `json:"content"`
|
||||
}
|
||||
|
||||
func GetFileContentFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func GetFileContentFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -165,8 +163,7 @@ func GetFileContentFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallTo
|
||||
return to.TextResult(slimContents(content))
|
||||
}
|
||||
|
||||
func GetDirContentFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func GetDirContentFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -191,8 +188,7 @@ func GetDirContentFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToo
|
||||
return to.TextResult(slimDirEntries(content))
|
||||
}
|
||||
|
||||
func CreateOrUpdateFileFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func CreateOrUpdateFileFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -250,8 +246,7 @@ func CreateOrUpdateFileFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.Ca
|
||||
return to.TextResult("Create file success")
|
||||
}
|
||||
|
||||
func DeleteFileFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func DeleteFileFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
|
||||
+48
-54
@@ -11,8 +11,7 @@ import (
|
||||
"gitea.com/gitea/gitea-mcp/pkg/tool"
|
||||
|
||||
gitea_sdk "gitea.dev/sdk"
|
||||
"github.com/mark3labs/mcp-go/mcp"
|
||||
"github.com/mark3labs/mcp-go/server"
|
||||
"github.com/modelcontextprotocol/go-sdk/mcp"
|
||||
)
|
||||
|
||||
// ReleaseTool holds the release-related tools (scope "release").
|
||||
@@ -27,84 +26,83 @@ const (
|
||||
)
|
||||
|
||||
var (
|
||||
CreateReleaseTool = mcp.NewTool(
|
||||
CreateReleaseTool = tool.NewDefinition(
|
||||
CreateReleaseToolName,
|
||||
mcp.WithDescription("Create a new release in a repository from a tag, optionally marking it as a draft or pre-release."),
|
||||
mcp.WithToolAnnotation(annotation.Write("Create a release")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("tag_name", mcp.Required()),
|
||||
mcp.WithString("target", mcp.Required(), mcp.Description("commitish")),
|
||||
mcp.WithString("title", mcp.Required()),
|
||||
mcp.WithBoolean("is_draft"),
|
||||
mcp.WithBoolean("is_pre_release"),
|
||||
mcp.WithString("body"),
|
||||
"Create a new release in a repository from a tag, optionally marking it as a draft or pre-release.",
|
||||
annotation.Write("Create a release"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("tag_name", tool.Required()),
|
||||
tool.String("target", tool.Required(), tool.Description("commitish")),
|
||||
tool.String("title", tool.Required()),
|
||||
tool.Boolean("is_draft"),
|
||||
tool.Boolean("is_pre_release"),
|
||||
tool.String("body"),
|
||||
)
|
||||
|
||||
DeleteReleaseTool = mcp.NewTool(
|
||||
DeleteReleaseTool = tool.NewDefinition(
|
||||
DeleteReleaseToolName,
|
||||
mcp.WithDescription("Delete a release from a repository by its numeric ID. This action is destructive and cannot be undone."),
|
||||
mcp.WithToolAnnotation(annotation.Destructive("Delete a release")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithNumber("id", mcp.Required()),
|
||||
"Delete a release from a repository by its numeric ID. This action is destructive and cannot be undone.",
|
||||
annotation.Destructive("Delete a release"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.Number("id", tool.Required()),
|
||||
)
|
||||
|
||||
GetReleaseTool = mcp.NewTool(
|
||||
GetReleaseTool = tool.NewDefinition(
|
||||
GetReleaseToolName,
|
||||
mcp.WithDescription("Get a release by ID"),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("Get release details")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithNumber("id", mcp.Required()),
|
||||
"Get a release by ID",
|
||||
annotation.ReadOnly("Get release details"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.Number("id", tool.Required()),
|
||||
)
|
||||
|
||||
GetLatestReleaseTool = mcp.NewTool(
|
||||
GetLatestReleaseTool = tool.NewDefinition(
|
||||
GetLatestReleaseToolName,
|
||||
mcp.WithDescription("Get the most recent published (non-draft) release in a repository."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("Get latest release")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
"Get the most recent published (non-draft) release in a repository.",
|
||||
annotation.ReadOnly("Get latest release"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
)
|
||||
|
||||
ListReleasesTool = mcp.NewTool(
|
||||
ListReleasesTool = tool.NewDefinition(
|
||||
ListReleasesToolName,
|
||||
mcp.WithDescription("List releases in a repository, optionally filtered to drafts or pre-releases."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("List releases")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithBoolean("is_draft"),
|
||||
mcp.WithBoolean("is_pre_release"),
|
||||
mcp.WithNumber("page", mcp.Description(params.PageDesc), mcp.DefaultNumber(1), mcp.Min(1)),
|
||||
mcp.WithNumber("per_page", mcp.Description(params.PaginationDesc), mcp.DefaultNumber(20), mcp.Min(1)),
|
||||
"List releases in a repository, optionally filtered to drafts or pre-releases.",
|
||||
annotation.ReadOnly("List releases"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.Boolean("is_draft"),
|
||||
tool.Boolean("is_pre_release"),
|
||||
tool.Number("page", tool.Description(params.PageDesc), tool.Default(1), tool.Minimum(1)),
|
||||
tool.Number("per_page", tool.Description(params.PaginationDesc), tool.Default(20), tool.Minimum(1)),
|
||||
)
|
||||
)
|
||||
|
||||
func init() {
|
||||
ReleaseTool.RegisterWrite(server.ServerTool{
|
||||
ReleaseTool.RegisterWrite(tool.ServerTool{
|
||||
Tool: CreateReleaseTool,
|
||||
Handler: CreateReleaseFn,
|
||||
})
|
||||
ReleaseTool.RegisterWrite(server.ServerTool{
|
||||
ReleaseTool.RegisterWrite(tool.ServerTool{
|
||||
Tool: DeleteReleaseTool,
|
||||
Handler: DeleteReleaseFn,
|
||||
})
|
||||
ReleaseTool.RegisterRead(server.ServerTool{
|
||||
ReleaseTool.RegisterRead(tool.ServerTool{
|
||||
Tool: GetReleaseTool,
|
||||
Handler: GetReleaseFn,
|
||||
})
|
||||
ReleaseTool.RegisterRead(server.ServerTool{
|
||||
ReleaseTool.RegisterRead(tool.ServerTool{
|
||||
Tool: GetLatestReleaseTool,
|
||||
Handler: GetLatestReleaseFn,
|
||||
})
|
||||
ReleaseTool.RegisterRead(server.ServerTool{
|
||||
ReleaseTool.RegisterRead(tool.ServerTool{
|
||||
Tool: ListReleasesTool,
|
||||
Handler: ListReleasesFn,
|
||||
})
|
||||
}
|
||||
|
||||
func CreateReleaseFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func CreateReleaseFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -148,8 +146,7 @@ func CreateReleaseFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToo
|
||||
return to.TextResult("Release Created")
|
||||
}
|
||||
|
||||
func DeleteReleaseFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func DeleteReleaseFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -175,8 +172,7 @@ func DeleteReleaseFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToo
|
||||
return to.TextResult("Release deleted successfully")
|
||||
}
|
||||
|
||||
func GetReleaseFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func GetReleaseFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -202,8 +198,7 @@ func GetReleaseFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolRe
|
||||
return to.TextResult(slimRelease(release))
|
||||
}
|
||||
|
||||
func GetLatestReleaseFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func GetLatestReleaseFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -225,8 +220,7 @@ func GetLatestReleaseFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.Call
|
||||
return to.TextResult(slimRelease(release))
|
||||
}
|
||||
|
||||
func ListReleasesFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func ListReleasesFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
|
||||
+46
-49
@@ -12,8 +12,7 @@ import (
|
||||
"gitea.com/gitea/gitea-mcp/pkg/tool"
|
||||
|
||||
gitea_sdk "gitea.dev/sdk"
|
||||
"github.com/mark3labs/mcp-go/mcp"
|
||||
"github.com/mark3labs/mcp-go/server"
|
||||
"github.com/modelcontextprotocol/go-sdk/mcp"
|
||||
)
|
||||
|
||||
var Tool = tool.New("repository")
|
||||
@@ -26,74 +25,73 @@ const (
|
||||
)
|
||||
|
||||
var (
|
||||
CreateRepoTool = mcp.NewTool(
|
||||
CreateRepoTool = tool.NewDefinition(
|
||||
CreateRepoToolName,
|
||||
mcp.WithDescription("Create a new Git repository, optionally under an organization (defaults to the authenticated user's account), with options for visibility, template, license, .gitignore, and initial README."),
|
||||
mcp.WithToolAnnotation(annotation.Write("Create a new repository")),
|
||||
mcp.WithString("name", mcp.Required()),
|
||||
mcp.WithString("description"),
|
||||
mcp.WithBoolean("private"),
|
||||
mcp.WithString("issue_labels"),
|
||||
mcp.WithBoolean("auto_init"),
|
||||
mcp.WithBoolean("template"),
|
||||
mcp.WithString("gitignores"),
|
||||
mcp.WithString("license"),
|
||||
mcp.WithString("readme"),
|
||||
mcp.WithString("default_branch"),
|
||||
mcp.WithString("trust_model", mcp.Enum("default", "collaborator", "committer", "collaboratorcommitter")),
|
||||
mcp.WithString("object_format_name", mcp.Enum("sha1", "sha256")),
|
||||
mcp.WithString("organization", mcp.Description("defaults to personal account")),
|
||||
"Create a new Git repository, optionally under an organization (defaults to the authenticated user's account), with options for visibility, template, license, .gitignore, and initial README.",
|
||||
annotation.Write("Create a new repository"),
|
||||
tool.String("name", tool.Required()),
|
||||
tool.String("description"),
|
||||
tool.Boolean("private"),
|
||||
tool.String("issue_labels"),
|
||||
tool.Boolean("auto_init"),
|
||||
tool.Boolean("template"),
|
||||
tool.String("gitignores"),
|
||||
tool.String("license"),
|
||||
tool.String("readme"),
|
||||
tool.String("default_branch"),
|
||||
tool.String("trust_model", tool.Enum("default", "collaborator", "committer", "collaboratorcommitter")),
|
||||
tool.String("object_format_name", tool.Enum("sha1", "sha256")),
|
||||
tool.String("organization", tool.Description("defaults to personal account")),
|
||||
)
|
||||
|
||||
ForkRepoTool = mcp.NewTool(
|
||||
ForkRepoTool = tool.NewDefinition(
|
||||
ForkRepoToolName,
|
||||
mcp.WithDescription("Fork an existing repository into the authenticated user's account or a target organization, optionally under a new name."),
|
||||
mcp.WithToolAnnotation(annotation.Write("Fork a repository")),
|
||||
mcp.WithString("user", mcp.Required(), mcp.Description("owner of source repo")),
|
||||
mcp.WithString("repo", mcp.Required()),
|
||||
mcp.WithString("organization", mcp.Description("target org")),
|
||||
mcp.WithString("name", mcp.Description("fork name")),
|
||||
"Fork an existing repository into the authenticated user's account or a target organization, optionally under a new name.",
|
||||
annotation.Write("Fork a repository"),
|
||||
tool.String("user", tool.Required(), tool.Description("owner of source repo")),
|
||||
tool.String("repo", tool.Required()),
|
||||
tool.String("organization", tool.Description("target org")),
|
||||
tool.String("name", tool.Description("fork name")),
|
||||
)
|
||||
|
||||
ListMyReposTool = mcp.NewTool(
|
||||
ListMyReposTool = tool.NewDefinition(
|
||||
ListMyReposToolName,
|
||||
mcp.WithDescription("List repositories owned by the authenticated user."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("List my repositories")),
|
||||
mcp.WithNumber("page", mcp.Description(params.PageDesc), mcp.DefaultNumber(1), mcp.Min(1)),
|
||||
mcp.WithNumber("per_page", mcp.Description(params.PaginationDesc), mcp.DefaultNumber(30), mcp.Min(1)),
|
||||
"List repositories owned by the authenticated user.",
|
||||
annotation.ReadOnly("List my repositories"),
|
||||
tool.Number("page", tool.Description(params.PageDesc), tool.Default(1), tool.Minimum(1)),
|
||||
tool.Number("per_page", tool.Description(params.PaginationDesc), tool.Default(30), tool.Minimum(1)),
|
||||
)
|
||||
|
||||
ListOrgReposTool = mcp.NewTool(
|
||||
ListOrgReposTool = tool.NewDefinition(
|
||||
ListOrgReposToolName,
|
||||
mcp.WithDescription("List repositories belonging to an organization."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("List organization repositories")),
|
||||
mcp.WithString("org", mcp.Required()),
|
||||
mcp.WithNumber("page", mcp.Description(params.PageDesc), mcp.DefaultNumber(1), mcp.Min(1)),
|
||||
mcp.WithNumber("per_page", mcp.Description(params.PaginationDesc), mcp.DefaultNumber(100), mcp.Min(1)),
|
||||
"List repositories belonging to an organization.",
|
||||
annotation.ReadOnly("List organization repositories"),
|
||||
tool.String("org", tool.Required()),
|
||||
tool.Number("page", tool.Description(params.PageDesc), tool.Default(1), tool.Minimum(1)),
|
||||
tool.Number("per_page", tool.Description(params.PaginationDesc), tool.Default(100), tool.Minimum(1)),
|
||||
)
|
||||
)
|
||||
|
||||
func init() {
|
||||
Tool.RegisterWrite(server.ServerTool{
|
||||
Tool.RegisterWrite(tool.ServerTool{
|
||||
Tool: CreateRepoTool,
|
||||
Handler: CreateRepoFn,
|
||||
})
|
||||
Tool.RegisterWrite(server.ServerTool{
|
||||
Tool.RegisterWrite(tool.ServerTool{
|
||||
Tool: ForkRepoTool,
|
||||
Handler: ForkRepoFn,
|
||||
})
|
||||
Tool.RegisterRead(server.ServerTool{
|
||||
Tool.RegisterRead(tool.ServerTool{
|
||||
Tool: ListMyReposTool,
|
||||
Handler: ListMyReposFn,
|
||||
})
|
||||
Tool.RegisterRead(server.ServerTool{
|
||||
Tool.RegisterRead(tool.ServerTool{
|
||||
Tool: ListOrgReposTool,
|
||||
Handler: ListOrgReposFn,
|
||||
})
|
||||
}
|
||||
|
||||
func CreateRepoFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func CreateRepoFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
name, err := params.GetString(args, "name")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -145,8 +143,7 @@ func CreateRepoFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolRe
|
||||
return to.TextResult(slim.Repo(repo))
|
||||
}
|
||||
|
||||
func ForkRepoFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func ForkRepoFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
user, err := params.GetString(args, "user")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -170,8 +167,8 @@ func ForkRepoFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResu
|
||||
return to.TextResult("Fork success")
|
||||
}
|
||||
|
||||
func ListMyReposFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
page, pageSize := params.GetPagination(req.GetArguments(), 30)
|
||||
func ListMyReposFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
page, pageSize := params.GetPagination(args, 30)
|
||||
opt := gitea_sdk.ListReposOptions{
|
||||
ListOptions: gitea_sdk.ListOptions{
|
||||
Page: page,
|
||||
@@ -190,12 +187,12 @@ func ListMyReposFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolR
|
||||
return to.TextResult(slim.Repos(repos))
|
||||
}
|
||||
|
||||
func ListOrgReposFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
org, err := params.GetString(req.GetArguments(), "org")
|
||||
func ListOrgReposFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
org, err := params.GetString(args, "org")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
}
|
||||
page, pageSize := params.GetPagination(req.GetArguments(), 100)
|
||||
page, pageSize := params.GetPagination(args, 100)
|
||||
opt := gitea_sdk.ListOrgReposOptions{
|
||||
ListOptions: gitea_sdk.ListOptions{
|
||||
Page: page,
|
||||
|
||||
+36
-41
@@ -11,8 +11,7 @@ import (
|
||||
"gitea.com/gitea/gitea-mcp/pkg/tool"
|
||||
|
||||
gitea_sdk "gitea.dev/sdk"
|
||||
"github.com/mark3labs/mcp-go/mcp"
|
||||
"github.com/mark3labs/mcp-go/server"
|
||||
"github.com/modelcontextprotocol/go-sdk/mcp"
|
||||
)
|
||||
|
||||
// TagTool holds the tag-related tools (scope "tag").
|
||||
@@ -26,67 +25,66 @@ const (
|
||||
)
|
||||
|
||||
var (
|
||||
CreateTagTool = mcp.NewTool(
|
||||
CreateTagTool = tool.NewDefinition(
|
||||
CreateTagToolName,
|
||||
mcp.WithDescription("Create a new Git tag in a repository at a target commit, branch, or existing tag, with an optional annotation message."),
|
||||
mcp.WithToolAnnotation(annotation.Write("Create a tag")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("tag_name", mcp.Required()),
|
||||
mcp.WithString("target", mcp.Description("commitish")),
|
||||
mcp.WithString("message", mcp.Description("tag message")),
|
||||
"Create a new Git tag in a repository at a target commit, branch, or existing tag, with an optional annotation message.",
|
||||
annotation.Write("Create a tag"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("tag_name", tool.Required()),
|
||||
tool.String("target", tool.Description("commitish")),
|
||||
tool.String("message", tool.Description("tag message")),
|
||||
)
|
||||
|
||||
DeleteTagTool = mcp.NewTool(
|
||||
DeleteTagTool = tool.NewDefinition(
|
||||
DeleteTagToolName,
|
||||
mcp.WithDescription("Permanently delete a tag from a repository. This action is destructive and cannot be undone."),
|
||||
mcp.WithToolAnnotation(annotation.Destructive("Delete a tag")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("tag_name", mcp.Required()),
|
||||
"Permanently delete a tag from a repository. This action is destructive and cannot be undone.",
|
||||
annotation.Destructive("Delete a tag"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("tag_name", tool.Required()),
|
||||
)
|
||||
|
||||
GetTagTool = mcp.NewTool(
|
||||
GetTagTool = tool.NewDefinition(
|
||||
GetTagToolName,
|
||||
mcp.WithDescription("Get details for a single tag in a repository by name."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("Get tag details")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("tag_name", mcp.Required()),
|
||||
"Get details for a single tag in a repository by name.",
|
||||
annotation.ReadOnly("Get tag details"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("tag_name", tool.Required()),
|
||||
)
|
||||
|
||||
ListTagsTool = mcp.NewTool(
|
||||
ListTagsTool = tool.NewDefinition(
|
||||
ListTagsToolName,
|
||||
mcp.WithDescription("List all tags in a repository, paginated."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("List tags")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithNumber("page", mcp.Description(params.PageDesc), mcp.DefaultNumber(1), mcp.Min(1)),
|
||||
mcp.WithNumber("per_page", mcp.Description(params.PaginationDesc), mcp.DefaultNumber(20), mcp.Min(1)),
|
||||
"List all tags in a repository, paginated.",
|
||||
annotation.ReadOnly("List tags"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.Number("page", tool.Description(params.PageDesc), tool.Default(1), tool.Minimum(1)),
|
||||
tool.Number("per_page", tool.Description(params.PaginationDesc), tool.Default(20), tool.Minimum(1)),
|
||||
)
|
||||
)
|
||||
|
||||
func init() {
|
||||
TagTool.RegisterWrite(server.ServerTool{
|
||||
TagTool.RegisterWrite(tool.ServerTool{
|
||||
Tool: CreateTagTool,
|
||||
Handler: CreateTagFn,
|
||||
})
|
||||
TagTool.RegisterWrite(server.ServerTool{
|
||||
TagTool.RegisterWrite(tool.ServerTool{
|
||||
Tool: DeleteTagTool,
|
||||
Handler: DeleteTagFn,
|
||||
})
|
||||
TagTool.RegisterRead(server.ServerTool{
|
||||
TagTool.RegisterRead(tool.ServerTool{
|
||||
Tool: GetTagTool,
|
||||
Handler: GetTagFn,
|
||||
})
|
||||
TagTool.RegisterRead(server.ServerTool{
|
||||
TagTool.RegisterRead(tool.ServerTool{
|
||||
Tool: ListTagsTool,
|
||||
Handler: ListTagsFn,
|
||||
})
|
||||
}
|
||||
|
||||
func CreateTagFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func CreateTagFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -118,8 +116,7 @@ func CreateTagFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolRes
|
||||
return to.TextResult("Tag Created")
|
||||
}
|
||||
|
||||
func DeleteTagFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func DeleteTagFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -145,8 +142,7 @@ func DeleteTagFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolRes
|
||||
return to.TextResult("Tag deleted")
|
||||
}
|
||||
|
||||
func GetTagFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func GetTagFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
@@ -172,8 +168,7 @@ func GetTagFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult
|
||||
return to.TextResult(slimTag(tag))
|
||||
}
|
||||
|
||||
func ListTagsFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func ListTagsFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
|
||||
+13
-14
@@ -8,37 +8,36 @@ import (
|
||||
"gitea.com/gitea/gitea-mcp/pkg/gitea"
|
||||
"gitea.com/gitea/gitea-mcp/pkg/params"
|
||||
"gitea.com/gitea/gitea-mcp/pkg/to"
|
||||
"gitea.com/gitea/gitea-mcp/pkg/tool"
|
||||
|
||||
gitea_sdk "gitea.dev/sdk"
|
||||
"github.com/mark3labs/mcp-go/mcp"
|
||||
"github.com/mark3labs/mcp-go/server"
|
||||
"github.com/modelcontextprotocol/go-sdk/mcp"
|
||||
)
|
||||
|
||||
const (
|
||||
GetRepoTreeToolName = "get_repository_tree"
|
||||
)
|
||||
|
||||
var GetRepoTreeTool = mcp.NewTool(
|
||||
var GetRepoTreeTool = tool.NewDefinition(
|
||||
GetRepoTreeToolName,
|
||||
mcp.WithDescription("Get the file tree of a repository at a given ref (SHA, branch, or tag), optionally recursively."),
|
||||
mcp.WithToolAnnotation(annotation.ReadOnly("Get repository file tree")),
|
||||
mcp.WithString("owner", mcp.Required(), mcp.Description(params.OwnerDesc)),
|
||||
mcp.WithString("repo", mcp.Required(), mcp.Description(params.RepoDesc)),
|
||||
mcp.WithString("tree_sha", mcp.Required(), mcp.Description("SHA, branch, or tag")),
|
||||
mcp.WithBoolean("recursive"),
|
||||
mcp.WithNumber("page", mcp.Description(params.PageDesc), mcp.DefaultNumber(1)),
|
||||
mcp.WithNumber("per_page", mcp.Description(params.PaginationDesc), mcp.DefaultNumber(30)),
|
||||
"Get the file tree of a repository at a given ref (SHA, branch, or tag), optionally recursively.",
|
||||
annotation.ReadOnly("Get repository file tree"),
|
||||
tool.String("owner", tool.Required(), tool.Description(params.OwnerDesc)),
|
||||
tool.String("repo", tool.Required(), tool.Description(params.RepoDesc)),
|
||||
tool.String("tree_sha", tool.Required(), tool.Description("SHA, branch, or tag")),
|
||||
tool.Boolean("recursive"),
|
||||
tool.Number("page", tool.Description(params.PageDesc), tool.Default(1)),
|
||||
tool.Number("per_page", tool.Description(params.PaginationDesc), tool.Default(30)),
|
||||
)
|
||||
|
||||
func init() {
|
||||
Tool.RegisterRead(server.ServerTool{
|
||||
Tool.RegisterRead(tool.ServerTool{
|
||||
Tool: GetRepoTreeTool,
|
||||
Handler: GetRepoTreeFn,
|
||||
})
|
||||
}
|
||||
|
||||
func GetRepoTreeFn(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
|
||||
args := req.GetArguments()
|
||||
func GetRepoTreeFn(ctx context.Context, args map[string]any) (*mcp.CallToolResult, error) {
|
||||
owner, err := params.GetString(args, "owner")
|
||||
if err != nil {
|
||||
return to.ErrorResult(err)
|
||||
|
||||
@@ -44,8 +44,10 @@ func TestSlimTreeNil(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestGetRepoTreeToolRequired(t *testing.T) {
|
||||
inputSchema := GetRepoTreeTool.InputSchema.(map[string]any)
|
||||
required, _ := inputSchema["required"].([]string)
|
||||
for _, field := range []string{"owner", "repo", "tree_sha"} {
|
||||
if !slices.Contains(GetRepoTreeTool.InputSchema.Required, field) {
|
||||
if !slices.Contains(required, field) {
|
||||
t.Errorf("expected %q to be required", field)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user