Skip to content

Request body not set in DELETE handlers via huma OpenAPI UI #887

@DoGab

Description

@DoGab

First of all thank you a lot for this awesome framework! Love it! ❤️

I guess i found a little issue in the OpenAPI documentation UI.

Problem

When issuing a request to a delete handler, that takes a request body, via Huma OpenAPI UI, the request fails with the following error. The curl statement shows that the request will not include the request body.

{
  "$schema": "http://localhost:8888/schemas/ErrorModel.json",
  "title": "Bad Request",
  "status": 400,
  "detail": "request body is required"
}
Image

When defining a handler with http.MethodDelete i want to be able to pass a request body to the handler via OpenAPI UI.

Expected Behavior

Whenever a request body passes the validation i want the handler to be able to read the request body and process it. Whenever the validation of the request body fails i want to receive a 422.

Reproduce

This minimal example demonstrates the how to reproduce the error. It was tested with versions v2.26.0, v2.28.0, v2.30.0, v2.32.0, v2.33.0, v2.34.1.

package main

import (
	"context"
	"log/slog"
	"net/http"

	"github.com/danielgtaylor/huma/v2"
	"github.com/danielgtaylor/huma/v2/adapters/humachi"
	"github.com/go-chi/chi/v5"
)

type UserDeleteInput struct {
	Body UserDeleteInputBody `body:""`
}

type UserDeleteInputBody struct {
	UserIDs []string `json:"user_ids" doc:"The IDs of the users to delete" minItems:"1"`
}

type DeleteResponse struct {
	Success bool `json:"success"`
}

func main() {
	router := gin.Default()
	api := humagin.New(router, huma.DefaultConfig("My API", "1.0.0"))

	huma.Register(api, huma.Operation{
		Method: http.MethodDelete,
		Path:   "/api/companies/users",
		OperationID: "delete-users-v1",
		Summary:     "Deletes a list of users (v1)",
		Description: "This endpoint deletes a list of users. It is authenticated and requires a valid access token.",
		Tags:        []string{"users"},
	}, UserDeleteHandler)

	http.ListenAndServe(":8888", router)
}

func UserDeleteHandler(ctx context.Context, input *UserDeleteInput) (*DeleteResponse, error) {
	users := input.Body.UserIDs
	slog.Info("Users received for deletion", "users", users)

	out := &DeleteResponse{
		Success: true,
	}
	slog.Info("success")
	return out, nil
}

Run the server.

go run main.go

Open a browser and head to http://localhost:8888/docs#/operations/delete-users-v1. Send a request via the OpenAPI UI. The request will fail with the error:

{
  "$schema": "http://localhost:8888/schemas/ErrorModel.json",
  "title": "Bad Request",
  "status": 400,
  "detail": "request body is required"
}

Send requests to the server via curl. The request succeeds.

curl -X DELETE http://localhost:8888/api/companies/users -H "Content-Type: application/json" -d '{"user_ids": ["123-456"]}' -v
* Host localhost:8888 was resolved.
* IPv6: ::1
* IPv4: 127.0.0.1
*   Trying [::1]:8888...
* Connected to localhost (::1) port 8888
> DELETE /api/companies/users HTTP/1.1
> Host: localhost:8888
> User-Agent: curl/8.7.1
> Accept: */*
> Content-Type: application/json
> Content-Length: 25
> 
* upload completely sent off: 25 bytes
< HTTP/1.1 204 No Content
< Success: true
< Date: Wed, 27 Aug 2025 09:35:26 GMT
< 
* Connection #0 to host localhost left intact

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions