Skip to content

Navigation Menu

Sign in
Sign up

Configuration

wiki edited this page Sep 4, 2026 · 1 revision

Configuration

app := rex.New(validation.WithValidation(validation.NewConfig(
	validation.WithCodec(XMLCodec{}),
	validation.WithStrictResponses(true),
)))

validation.WithValidation(nil) takes the defaults.

⚠ A non-nil config is used verbatim

There is no field-by-field merge. A partial struct literal leaves everything else at its zero value:

// Wrong: Codecs nil (no codecs at all), ValidateResponses false.
validation.WithValidation(&validation.Config{StrictResponses: true})
// Right.
validation.WithValidation(validation.NewConfig(validation.WithStrictResponses(true)))

The merge used to exist and behaved as a trap: fields it forgot were silently ignored, fields it copied unconditionally were zeroed by a partial literal, and a deliberate zero could not be expressed at all.

Note how the negative phrasing of AllowUnknownFields interacts with this: the zero value has to be the safe one, or a partial literal would quietly opt out of rejection.

Fields

type Config struct {
	Codecs []Codec // default [JSONCodec{}]; first is the Accept default
	StrictResponses bool // default false
	ValidateResponses bool // default true
	AllowUnknownFields bool // default false — rejection is on
}

Options

WithCodec(c) append a codec
WithValidateResponses(bool) check response bodies against declared schemas
WithStrictResponses(bool) undocumented status → 500
WithAllowUnknownFields() ⚠ permit undeclared request members

A production shape

validation.NewConfig(
	// Responses are checked, and every status must be documented.
	validation.WithValidateResponses(true),
	validation.WithStrictResponses(true),
	// Unknown fields rejected — the default, stated for the reader.
)

For a service with an established client you cannot change:

validation.NewConfig(
	validation.WithAllowUnknownFields(), // deliberate, and worth a comment
	validation.WithValidateResponses(true),
)

Middleware configuration

type MiddlewareConfig struct {
	Registry *codecRegistry
	Validator routeValidator
	Strict bool
	ValidateResp bool
	RejectUnknown bool
	Logger rx.Logger
}

Set the logger. A strict-mode rejection describes the server's own internals, so the client gets a generic 500 — without somewhere to write the specifics the information is simply lost. The extension configures it from r.Logger().

ValidationFactory(cfg) builds the per-route middleware from it if you are composing a chain yourself. ValidationMiddleware(cfg) is the deprecated plain-http form — it has to find the route's schemas at request time, where the factory reads them once at freeze.

Interaction with OpenAPI

Both extensions read the same route interface. Register both and one declaration produces validation and documentation together:

app := rex.New(
	validation.WithValidation(nil),
	openapi.WithOpenAPI(nil),
)

There is nothing to keep in sync, which is the point of the contract living in rextension rather than in either extension.

Clone this wiki locally

AltStyle によって変換されたページ (->オリジナル) /