Skip to main content

Overview

The contenttype middleware validates and enforces Content-Type headers on requests. It ensures requests have the expected content type and can set default content types for responses. Use it when you need:
  • JSON-only API endpoints
  • Form submission validation
  • Content-Type enforcement
  • Default response types

Installation

import "github.com/go-mizu/mizu/middlewares/contenttype"

Quick Start

app := mizu.New()

// Require JSON for all POST/PUT/PATCH requests
app.Use(contenttype.RequireJSON())

Functions

Request Validation

FunctionDescription
Require(types...)Require specific content types
RequireJSON()Require application/json
RequireForm()Require form content types
Default(type)Set default if missing

Response Headers

FunctionDescription
SetResponse(type)Set response Content-Type

Examples

Require JSON

// Only accept JSON requests
app.Use(contenttype.RequireJSON())

app.Post("/api/users", func(c *mizu.Ctx) error {
    // Guaranteed to receive JSON
    var user User
    if err := c.BindJSON(&user); err != nil {
        return err
    }
    return c.JSON(201, user)
})

Require Form Data

// Only accept form submissions
app.Post("/contact", contactHandler, contenttype.RequireForm())

Multiple Content Types

// Accept either JSON or XML
app.Use(contenttype.Require("application/json", "application/xml"))

Set Default Content-Type

// Set default for requests without Content-Type
app.Use(contenttype.Default("application/json"))

Set Response Content-Type

// All responses are JSON
app.Use(contenttype.SetResponse("application/json; charset=utf-8"))

Per-Route Configuration

// API routes: JSON only
api := app.Group("/api")
api.Use(contenttype.RequireJSON())

// Form routes: Form data only
forms := app.Group("/forms")
forms.Use(contenttype.RequireForm())

Combined Request/Response

// Require JSON input, set JSON output
app.Use(contenttype.RequireJSON())
app.Use(contenttype.SetResponse("application/json; charset=utf-8"))

API Reference

Functions

// Require specific content types
func Require(types ...string) mizu.Middleware

// RequireJSON requires application/json
func RequireJSON() mizu.Middleware

// RequireForm requires form content types
func RequireForm() mizu.Middleware

// Default sets default Content-Type if not present
func Default(contentType string) mizu.Middleware

// SetResponse sets response Content-Type
func SetResponse(contentType string) mizu.Middleware

Behavior

  • Only validates POST, PUT, PATCH requests (methods with bodies)
  • Compares media type only, ignores parameters (charset, boundary)
  • Returns 415 Unsupported Media Type on validation failure

Common Content Types

TypeDescription
application/jsonJSON data
application/xmlXML data
application/x-www-form-urlencodedURL-encoded form
multipart/form-dataFile uploads
text/plainPlain text

Technical Details

Implementation Overview

The contenttype middleware provides Content-Type validation and enforcement through a set of middleware functions that operate on request and response headers.

Request Validation (Require, RequireJSON, RequireForm)

The validation middleware follows these steps:
  1. Method Filtering: Only validates requests with body content (POST, PUT, PATCH). GET, DELETE, and other methods bypass validation.
  2. Header Extraction: Retrieves the Content-Type header from the incoming request.
  3. Media Type Parsing: Extracts the base media type by:
    • Finding the semicolon separator (if present)
    • Stripping parameters (charset, boundary, etc.)
    • Trimming whitespace from the result
  4. Case-Insensitive Matching: Compares the extracted media type against allowed types using case-insensitive comparison.
  5. Error Response: Returns HTTP 415 (Unsupported Media Type) if:
    • Content-Type header is missing (for methods that require it)
    • The media type doesn’t match any allowed types

Default Content-Type (Default)

Sets a default Content-Type header on the request if none is present. This middleware:
  • Checks if the Content-Type header exists
  • Sets the header to the specified default value if missing
  • Preserves existing headers without modification

Response Content-Type (SetResponse)

Sets the Content-Type header on the response. This middleware:
  • Unconditionally sets the response Content-Type header
  • Executes before the handler processes the request
  • Can be combined with request validation middleware

Key Design Decisions

  • Parameter Stripping: Media type parameters are ignored during validation, allowing application/json; charset=utf-8 to match application/json
  • Method-Specific: Only methods with request bodies are validated
  • Fail-Fast: Validation happens before the handler executes
  • Composable: Multiple middleware can be chained for complex scenarios

Best Practices

  • Use RequireJSON() for REST APIs
  • Use RequireForm() for traditional forms
  • Set response Content-Type for consistency
  • Combine Default() with Require() to provide fallback behavior
  • Apply validation at the router group level for route-specific rules

Testing

The contenttype middleware includes comprehensive test coverage for all functions and edge cases.

Test Cases

Test CaseDescriptionExpected Behavior
Require Middleware
Allows matching content typePOST request with application/json headerRequest proceeds (200 OK)
Allows with charsetPOST request with application/json; charset=utf-8Request proceeds (200 OK), parameters ignored
Rejects wrong content typePOST request with application/xml header (not in allowed list)Returns 415 Unsupported Media Type
Rejects missing content typePOST request without Content-Type headerReturns 415 Unsupported Media Type
Skips GET requestsGET request without Content-Type headerRequest proceeds (200 OK), validation skipped
RequireJSON Middleware
Allows JSONPOST request with application/json headerRequest proceeds (200 OK)
Rejects formPOST request with application/x-www-form-urlencoded headerReturns 415 Unsupported Media Type
RequireForm Middleware
Allows form-urlencodedPOST request with application/x-www-form-urlencoded headerRequest proceeds (200 OK)
Allows multipartPOST request with multipart/form-data; boundary=---- headerRequest proceeds (200 OK)
Default Middleware
Sets default when missingPOST request without Content-Type headerRequest header set to application/json
Preserves existingPOST request with text/plain headerExisting header preserved as text/plain
SetResponse Middleware
Sets response Content-TypeGET request to endpoint with SetResponse middlewareResponse includes Content-Type: application/json; charset=utf-8 header