oapi-codegen icon indicating copy to clipboard operation
oapi-codegen copied to clipboard

Strict Server mode does not respect optional requestBody

Open ryan-bever opened this issue 2 months ago • 0 comments

Strict Server mode does not respect optional requestBody

Description

When using strict-server generation mode, the generated code does not properly handle optional request bodies (required: false). The generated strict handler always attempts to decode the JSON body, causing requests without a body to fail with an EOF error, even though the OpenAPI specification explicitly marks the request body as optional.

Environment

  • oapi-codegen version: v2.5.0
  • Go version: 1.24.5

Minimal Reproduction

A complete minimal reproduction is available at: https://github.com/ryan-bever/optional-request-body

OpenAPI Specification

The spec defines an optional request body:

paths:
  /things:
    post:
      summary: Create Thing
      operationId: createThing
      requestBody:
        required: false  # <-- Request body is optional
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/ThingRequest"
      responses:
        "201":
          description: Thing created

Generation Config

package: main
output: server.gen.go
generate:
  std-http-server: true
  strict-server: true
  embedded-spec: true
  models: true

Generated Code Issue

The generated strict handler always attempts to decode the body:

func (sh *strictHandler) CreateThing(w http.ResponseWriter, r *http.Request) {
	var request CreateThingRequestObject

	var body CreateThingJSONRequestBody
	if err := json.NewDecoder(r.Body).Decode(&body); err != nil {
		// This error handler is invoked even for empty bodies
		sh.options.RequestErrorHandlerFunc(w, r, fmt.Errorf("can't decode JSON body: %w", err))
		return
	}
	request.Body = &body
	// ... rest of handler
}

Steps to Reproduce

  1. Generate code with strict-server enabled for a spec with required: false on requestBody
  2. Start the server
  3. Make a POST request without a body:
    curl -X POST http://localhost:8080/things
    

Expected Behavior

The request should succeed. The handler should receive request.Body = nil when no body is provided, allowing the implementation to handle the optional body appropriately.

Actual Behavior

The request fails with:

can't decode JSON body: EOF

Workaround

Sending an empty JSON object works:

curl -X POST http://localhost:8080/things -d "{}"

However, this defeats the purpose of having an optional request body and forces clients to always send at least an empty object.

Additional Context

The CreateThingRequestObject already correctly defines Body as a pointer (*CreateThingJSONRequestBody), which is appropriate for optional fields. The issue is solely in the decoding logic of the generated strict handler.

ryan-bever avatar Oct 30 '25 20:10 ryan-bever