feat(mcp): cap inbound request body at 1 MiB
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -8,7 +8,10 @@ import (
|
|||||||
"gitea.d-ma.be/mathias/gitea-mcp/internal/registry"
|
"gitea.d-ma.be/mathias/gitea-mcp/internal/registry"
|
||||||
)
|
)
|
||||||
|
|
||||||
const ProtocolVersion = "2025-06-18"
|
const (
|
||||||
|
ProtocolVersion = "2025-06-18"
|
||||||
|
maxRequestBodyBytes = 1 << 20 // 1 MiB
|
||||||
|
)
|
||||||
|
|
||||||
type ServerOptions struct {
|
type ServerOptions struct {
|
||||||
Registry *registry.Registry
|
Registry *registry.Registry
|
||||||
@@ -38,6 +41,7 @@ func (s *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (s *Server) handlePOST(w http.ResponseWriter, r *http.Request) {
|
func (s *Server) handlePOST(w http.ResponseWriter, r *http.Request) {
|
||||||
|
r.Body = http.MaxBytesReader(w, r.Body, maxRequestBodyBytes) // 1 MiB cap
|
||||||
var req Request
|
var req Request
|
||||||
if err := json.NewDecoder(r.Body).Decode(&req); err != nil {
|
if err := json.NewDecoder(r.Body).Decode(&req); err != nil {
|
||||||
writeJSON(w, http.StatusBadRequest, NewErrorResponse(nil, -32700, "parse error", nil))
|
writeJSON(w, http.StatusBadRequest, NewErrorResponse(nil, -32700, "parse error", nil))
|
||||||
|
|||||||
@@ -105,3 +105,15 @@ func TestToolsListAfterInitialize(t *testing.T) {
|
|||||||
result := resp["result"].(map[string]any)
|
result := resp["result"].(map[string]any)
|
||||||
assert.Contains(t, result, "tools")
|
assert.Contains(t, result, "tools")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestPostBodyTooLarge(t *testing.T) {
|
||||||
|
srv := newServer(t)
|
||||||
|
// 2 MiB of 'a' characters — exceeds the 1 MiB cap.
|
||||||
|
payload := bytes.Repeat([]byte("a"), 2<<20)
|
||||||
|
req := httptest.NewRequest(http.MethodPost, "/", bytes.NewBuffer(payload))
|
||||||
|
req.Header.Set("Content-Type", "application/json")
|
||||||
|
rr := httptest.NewRecorder()
|
||||||
|
srv.ServeHTTP(rr, req)
|
||||||
|
assert.NotEqual(t, http.StatusOK, rr.Code, "oversized body must not return 200")
|
||||||
|
assert.Equal(t, http.StatusBadRequest, rr.Code)
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user