Files
sherlock/cmd/gitea-mcp/tools.go
T
amacocian f5109abfad
CI / build (push) Successful in 19s
Gitea mcp pre-release
2026-05-25 15:22:30 +02:00

79 lines
1.8 KiB
Go

package main
import (
"net/url"
"github.com/modelcontextprotocol/go-sdk/mcp"
)
// registerTools wires every tool onto server. Each `tools_*.go` file
// owns one domain (issues, pulls, actions, …); this file just calls
// into them and provides cross-domain helpers.
func registerTools(server *mcp.Server, api *giteaAPI) {
registerUserTools(server, api)
registerRepoTools(server, api)
registerContentTools(server, api)
registerCommitTools(server, api)
registerIssueTools(server, api)
registerPullTools(server, api)
registerReleaseTools(server, api)
registerRefTools(server, api)
registerWikiTools(server, api)
registerActionsTools(server, api)
registerPackageTools(server, api)
registerOrgTools(server, api)
}
// clampInt returns dflt when v <= 0, else v clipped to [min, max].
func clampInt(v, min, max, dflt int) int {
if v <= 0 {
return dflt
}
if v < min {
return min
}
if v > max {
return max
}
return v
}
func firstLine(s string) string {
for i := 0; i < len(s); i++ {
if s[i] == '\n' {
return s[:i]
}
}
return s
}
// escapePathSegments escapes each segment of a file path individually
// so that slashes survive but per-segment specials (#, ?, etc.) get
// percent-encoded. url.PathEscape on the whole path would escape the
// slashes too and break Gitea's path-based routing.
func escapePathSegments(p string) string {
var b []byte
first := true
from := 0
for i := 0; i <= len(p); i++ {
if i == len(p) || p[i] == '/' {
seg := p[from:i]
if !first {
b = append(b, '/')
}
b = append(b, url.PathEscape(seg)...)
first = false
from = i + 1
}
}
return string(b)
}
// setIf sets q[k]=v when v is non-empty. Saves a lot of three-line
// if-non-empty blocks in the tool handlers.
func setIf(q url.Values, k, v string) {
if v != "" {
q.Set(k, v)
}
}