Documentation
¶
Overview ¶
Package http contains HTTP specific constructs that complement the code generated by Loom. The constructs include a composable HTTP client, default encodings, a mux and a websocket implementation that relies on the Gorilla websocket package.
Index ¶
- Constants
- Variables
- func AsHandlerFunc(handler http.Handler) http.HandlerFunc
- func CORSHandler(policy CORSPolicy, next http.HandlerFunc) http.HandlerFunc
- func DecodeFormValue(values url.Values, prefix string, target any) (bool, error)
- func DecodeFormValues(values url.Values, target any) error
- func DefaultProblemTitle(code string, status int) string
- func DefaultProblemTypeURI(code string) string
- func EffectiveClientAddress(r *http.Request) string
- func EncodeFormValue(values url.Values, prefix string, v any) (bool, error)
- func EncodeFormValues(v any) (url.Values, error)
- func EncodeSSEData(payload any) (string, error)
- func ErrDecodingError(svc, m string, err error) error
- func ErrEncodingError(svc, m string, err error) error
- func ErrInvalidResponse(svc, m string, code int, body string) error
- func ErrInvalidType(svc, m, expected string, actual any) error
- func ErrInvalidURL(svc, m, u string, err error) error
- func ErrRequestError(svc, m string, err error) error
- func ErrValidationError(svc, m string, err error) error
- func ErrorEncoder(encoder func(context.Context, http.ResponseWriter) Encoder, ...) func(context.Context, http.ResponseWriter, error) error
- func FormChildKey(prefix, name string) string
- func HandleCORSPreflight(w http.ResponseWriter, r *http.Request, policy CORSPolicy, ...)
- func MountHandler(mux Muxer, method, pattern string, handler http.Handler)
- func NewUnaryHandler[Payload, Result any](spec UnaryHandlerSpec[Payload, Result]) http.Handler
- func ProblemErrorFromBody(code string, status int, detail string, instance string, retryHint *string) *loom.ServiceError
- func ProblemInstanceID(instance string) string
- func ProblemInstanceURI(id string) string
- func ReadResponseBody(resp *http.Response) ([]byte, error)
- func ReadUnexpectedResponseBody(resp *http.Response) (string, error)
- func RequestMetadataMiddleware(policy RequestMetadataPolicy) func(http.Handler) http.Handler
- func ResolveProblemTypeAndTitle(code string, status int, explicitType, explicitTitle string) (string, string)
- func SafeDecodePayloadMessage(error) string
- func SetContentType(w http.ResponseWriter, ct string)
- func SetFormRequest(req *http.Request, body any) error
- func ValidateResponseContract(resp *http.Response, contract ResponseContractCase) error
- func ValidateSSEResponseContract(observation *SSEResponseContractObservation, contract ResponseContractCase) error
- func ValidateWebSocketResponseContract(observation *WebSocketResponseContractObservation, ...) error
- func WriteCORSActualHeaders(w http.ResponseWriter, r *http.Request, policy CORSPolicy) bool
- func WriteJSONSSEEvent(w io.Writer, msg SSEMessage, payload any) error
- func WriteSSEEvent(w io.Writer, msg SSEMessage) error
- type CORSOrigin
- type CORSPolicy
- type ClientError
- type ConnConfigureFunc
- type DebugDoer
- type Decoder
- type Dialer
- type Doer
- type Encoder
- type EncodingFunc
- type ErrorResponse
- type FileResponse
- type FormValuesMarshaler
- type FormValuesUnmarshaler
- type HandlerLifecycle
- func (l *HandlerLifecycle) Context() context.Context
- func (l *HandlerLifecycle) DecodeFailed(err error, encodeError func(context.Context, http.ResponseWriter, error) error, ...)
- func (l *HandlerLifecycle) End()
- func (l *HandlerLifecycle) HandlerFailed(err error, committed bool, ...)
- func (l *HandlerLifecycle) ResponseFailed(err error, handleFailure func(context.Context, http.ResponseWriter, error))
- func (l *HandlerLifecycle) ServeFile(r *http.Request, file *FileResponse, contentType string, ...)
- func (l *HandlerLifecycle) WriteRawBody(body io.ReadCloser, ...)
- func (l *HandlerLifecycle) Writer() http.ResponseWriter
- type MiddlewareMuxer
- type Mounter
- type MultipartFile
- type MultipartForm
- type MultipartPartContract
- type MultipartRequestContract
- type Muxer
- type ProblemResponse
- type RequestMetadata
- type RequestMetadataPolicy
- type ResolverMuxer
- type ResponseContractCase
- type ResponseContractCaseKind
- type ResponseContractTransport
- type RuntimeCORSPolicy
- type SSEControl
- type SSEEvent
- type SSEMessage
- type SSEResponseContract
- type SSEResponseContractObservation
- type SSEStreamReader
- type SSEStreamWriter
- func (s *SSEStreamWriter) Close() error
- func (s *SSEStreamWriter) Context() context.Context
- func (s *SSEStreamWriter) Open(ctx context.Context) error
- func (s *SSEStreamWriter) SendComment(ctx context.Context, text string) error
- func (s *SSEStreamWriter) Started() bool
- func (s *SSEStreamWriter) WriteEvent(ctx context.Context, write func(io.Writer) error) error
- type Server
- type Servers
- type Statuser
- type StreamWritePolicy
- type UnaryHandlerSpec
- type UnaryResult
- type Upgrader
- type WebSocketResponseContract
- type WebSocketResponseContractObservation
- type WebSocketStream
- func (s *WebSocketStream) Close() error
- func (s *WebSocketStream) Conn() *websocket.Conn
- func (s *WebSocketStream) ReadJSON(ctx context.Context, v any) error
- func (s *WebSocketStream) SetConn(conn *websocket.Conn)
- func (s *WebSocketStream) WriteClose(message string) error
- func (s *WebSocketStream) WriteJSON(ctx context.Context, v any) error
Constants ¶
const ( // AcceptTypeKey is the context key used to store the value of the HTTP // request Accept-Type header. The value may be used by encoders and // decoders to implement a content type negotiation algorithm. AcceptTypeKey contextKey = iota + 1 // ContentTypeKey is the context key used to store the value of the HTTP // response Content-Type header when explicitly set in the DSL. The value // may be used by encoders to set the header appropriately. ContentTypeKey // LastEventIDKey is the context key used to store the Last-Event-ID // request header for Server-Sent Events endpoints. LastEventIDKey // DefaultMaxRequestBodyBytes is the default maximum number of request-body // bytes decoded by Loom's built-in HTTP decoders. DefaultMaxRequestBodyBytes = 32 << 20 // DefaultMaxErrorBodyBytes is the default maximum number of unexpected // response-body bytes included in client-side response errors. DefaultMaxErrorBodyBytes = 64 << 10 )
const ( // ResponseContractSuccess identifies a successful response contract case. ResponseContractSuccess ResponseContractCaseKind = "success" // ResponseContractError identifies an error response contract case. ResponseContractError ResponseContractCaseKind = "error" // ResponseContractHTTP identifies an ordinary HTTP response contract. ResponseContractHTTP ResponseContractTransport = "http" // ResponseContractSSE identifies a Server-Sent Events response contract. ResponseContractSSE ResponseContractTransport = "sse" // ResponseContractWebSocket identifies a WebSocket response contract. ResponseContractWebSocket ResponseContractTransport = "websocket" )
const ( // ProblemJSONContentType is the default media type for Loom HTTP problem // responses. ProblemJSONContentType = "application/problem+json" )
Variables ¶
var ( // ErrSSEStreamClosed is returned when a control or event write is attempted // after the generated SSE stream has closed. ErrSSEStreamClosed = errors.New("loom http SSE stream closed") // ErrInvalidSSEComment is returned when comment text contains a line break // that could inject another SSE field or event. ErrInvalidSSEComment = errors.New("loom http SSE comment contains a line break") )
var ( // ErrInvalidStreamWriteTimeout is returned when a stream write timeout is negative. ErrInvalidStreamWriteTimeout = errors.New("loom http stream write timeout must not be negative") // ErrStreamWriteDeadlineUnsupported is returned when a streaming transport // cannot install the deadline required by a write policy or caller context. ErrStreamWriteDeadlineUnsupported = errors.New("loom http stream write deadline unsupported") )
var ( // ErrInvalidRequestMetadataHeader is returned when a retained header name is invalid. ErrInvalidRequestMetadataHeader = errors.New("loom http invalid request metadata header") )
var ( // ErrWebSocketStreamClosed is returned when generated code uses a stream // after its WebSocket connection has been closed. ErrWebSocketStreamClosed = errors.New("loom http websocket stream closed") )
Functions ¶
func AsHandlerFunc ¶ added in v1.8.0
func AsHandlerFunc(handler http.Handler) http.HandlerFunc
AsHandlerFunc adapts handler to the function type required by Muxer.
func CORSHandler ¶ added in v1.3.0
func CORSHandler(policy CORSPolicy, next http.HandlerFunc) http.HandlerFunc
CORSHandler wraps next and writes CORS response headers for matching actual browser requests. Non-CORS requests and disallowed origins pass through unchanged.
func DecodeFormValue ¶
DecodeFormValue decodes application/x-www-form-urlencoded values into target using prefix.
func DecodeFormValues ¶
DecodeFormValues decodes application/x-www-form-urlencoded values into target.
func DefaultProblemTitle ¶ added in v1.0.9
DefaultProblemTitle returns the deterministic default problem title for code and status when no explicit title override is provided.
func DefaultProblemTypeURI ¶ added in v1.0.9
DefaultProblemTypeURI returns the deterministic default problem type URI for code when no explicit override is provided.
func EffectiveClientAddress ¶ added in v1.7.0
EffectiveClientAddress returns the trusted effective client IP when request metadata middleware has installed a snapshot. Otherwise it returns the direct network peer and never trusts forwarding headers on its own.
func EncodeFormValue ¶
EncodeFormValue appends the application/x-www-form-urlencoded representation of v to values using prefix.
func EncodeFormValues ¶
EncodeFormValues encodes v as application/x-www-form-urlencoded values.
func EncodeSSEData ¶ added in v1.3.0
EncodeSSEData encodes a payload as an SSE data field.
func ErrDecodingError ¶
ErrDecodingError is the error returned when the decoder fails to decode the response body.
func ErrEncodingError ¶
ErrEncodingError is the error returned when the encoder fails to encode the request body.
func ErrInvalidResponse ¶
ErrInvalidResponse is the error returned when the service responded with an unexpected response status code.
func ErrInvalidType ¶
ErrInvalidType is the error returned when the wrong type is given to a method function.
func ErrInvalidURL ¶
ErrInvalidURL is the error returned when the URL computed for an method is invalid.
func ErrRequestError ¶
ErrRequestError is the error returned when the request fails to be sent.
func ErrValidationError ¶
ErrValidationError is the error returned when the response body is properly received and decoded but fails validation.
func ErrorEncoder ¶
func ErrorEncoder(encoder func(context.Context, http.ResponseWriter) Encoder, formatter func(ctx context.Context, err error) Statuser) func(context.Context, http.ResponseWriter, error) error
ErrorEncoder returns an encoder that encodes errors returned by service methods. The default encoder checks whether the error is a Loom ServiceError struct and if so uses the error temporary and timeout fields to infer a proper HTTP status code and marshals the error struct to the body using the provided encoder. If the error is not a Loom ServiceError struct then it is encoded as a permanent internal server error. This behavior as well as the shape of the response can be overridden by providing a non-nil formatter.
func FormChildKey ¶
FormChildKey returns the fully qualified form key for name under prefix.
func HandleCORSPreflight ¶ added in v1.3.0
func HandleCORSPreflight(w http.ResponseWriter, r *http.Request, policy CORSPolicy, allowedMethods []string)
HandleCORSPreflight writes a CORS preflight response for a matching origin. allowedMethods is the route-local method set generated for the matched path.
func MountHandler ¶ added in v1.8.0
MountHandler registers handler for method and pattern on mux. Generated servers use this function so handler adaptation remains runtime behavior.
func NewUnaryHandler ¶ added in v1.8.0
NewUnaryHandler creates an HTTP handler from typed endpoint adapters. It owns the request context, observation, and failure sequence.
func ProblemErrorFromBody ¶ added in v1.0.9
func ProblemErrorFromBody( code string, status int, detail string, instance string, retryHint *string, ) *loom.ServiceError
ProblemErrorFromBody rebuilds a Loom service error from a decoded problem document body.
func ProblemInstanceID ¶ added in v1.0.9
ProblemInstanceID extracts the Loom error instance ID from a problem instance URI when it uses the framework default URN form.
func ProblemInstanceURI ¶ added in v1.0.9
ProblemInstanceURI returns a stable URI reference for a specific problem occurrence.
func ReadResponseBody ¶ added in v1.2.1
ReadResponseBody reads the bounded response body used when generated clients restore the response body after decoding.
func ReadUnexpectedResponseBody ¶ added in v1.2.1
ReadUnexpectedResponseBody reads the bounded body text used in generated client-side invalid-response errors.
func RequestMetadataMiddleware ¶ added in v1.6.0
func RequestMetadataMiddleware(policy RequestMetadataPolicy) func(http.Handler) http.Handler
RequestMetadataMiddleware snapshots inbound request metadata before the next handler executes. Apply it with a generated server's Use method so endpoint decoders and security functions observe the same snapshot.
func ResolveProblemTypeAndTitle ¶ added in v1.0.9
func ResolveProblemTypeAndTitle(code string, status int, explicitType, explicitTitle string) (string, string)
ResolveProblemTypeAndTitle resolves the final RFC 9457 type/title pair for a problem code and HTTP status. Explicit overrides win over generated values.
func SafeDecodePayloadMessage ¶ added in v1.2.1
SafeDecodePayloadMessage returns a stable client-facing description for a request body decode failure without exposing Go decoder internals.
func SetContentType ¶
func SetContentType(w http.ResponseWriter, ct string)
SetContentType initializes the response Content-Type header given a MIME type. If the Content-Type header is already set and the MIME type is "application/json" or "application/xml" then SetContentType appends a suffix to the header ("+json" or "+xml" respectively).
func SetFormRequest ¶
SetFormRequest encodes body as application/x-www-form-urlencoded and stores it in req.
func ValidateResponseContract ¶ added in v1.8.0
func ValidateResponseContract(resp *http.Response, contract ResponseContractCase) error
ValidateResponseContract validates the transport-owned wire invariants in contract against resp. Applications remain responsible for arranging the service state and request that produce the response.
func ValidateSSEResponseContract ¶ added in v1.8.0
func ValidateSSEResponseContract(observation *SSEResponseContractObservation, contract ResponseContractCase) error
ValidateSSEResponseContract validates an SSE handshake, observed frames, and clean end-of-stream behavior against contract.
func ValidateWebSocketResponseContract ¶ added in v1.8.0
func ValidateWebSocketResponseContract(observation *WebSocketResponseContractObservation, contract ResponseContractCase) error
ValidateWebSocketResponseContract validates a WebSocket handshake, observed server messages, and declared terminal behavior against contract.
func WriteCORSActualHeaders ¶ added in v1.3.0
func WriteCORSActualHeaders(w http.ResponseWriter, r *http.Request, policy CORSPolicy) bool
WriteCORSActualHeaders writes CORS headers for a matching actual request.
func WriteJSONSSEEvent ¶
func WriteJSONSSEEvent(w io.Writer, msg SSEMessage, payload any) error
WriteJSONSSEEvent marshals payload as JSON and writes it as an SSE event.
func WriteSSEEvent ¶
func WriteSSEEvent(w io.Writer, msg SSEMessage) error
WriteSSEEvent writes a single SSE event frame.
Types ¶
type CORSOrigin ¶ added in v1.3.0
type CORSOrigin struct {
Pattern string
Regex bool
Methods []string
Headers []string
Expose []string
MaxAge int
Credentials bool
}
CORSOrigin defines one allowed origin and the response policy attached to it. Pattern is an exact origin, "*", or a regular expression when Regex is true.
type CORSPolicy ¶ added in v1.3.0
type CORSPolicy struct {
Origins []CORSOrigin
}
CORSPolicy defines the Cross-Origin Resource Sharing headers generated handlers may write for actual and preflight requests.
type ClientError ¶
type ClientError struct {
// Name is a name for this class of errors.
Name string
// Message contains the specific error details.
Message string
// Service is the name of the service.
Service string
// Method is the name of the service method.
Method string
// Is the error temporary?
Temporary bool
// Is the error a timeout?
Timeout bool
// Is the error a server-side fault?
Fault bool
// The original error if any
Err error
}
ClientError is an error returned by a HTTP service client.
func (ClientError) Unwrap ¶
func (c ClientError) Unwrap() error
type ConnConfigureFunc ¶
ConnConfigureFunc is used to configure a websocket connection with custom handlers. The cancel function cancels the request context when invoked in the configure function.
type DebugDoer ¶
type DebugDoer interface {
Doer
// Fprint prints the HTTP request and response details.
Fprint(io.Writer)
}
DebugDoer is a Doer that can print the low level HTTP details.
func NewDebugDoer ¶
NewDebugDoer wraps the given doer and captures the request and response so they can be printed.
type Decoder ¶
Decoder provides the actual decoding algorithm used to load HTTP request and response bodies.
func RequestDecoder ¶
RequestDecoder returns a HTTP request body decoder suitable for the given request. The decoder handles the following mime types:
- application/json using package encoding/json
- application/xml using package encoding/xml
- application/gob using package encoding/gob
- text/html and text/plain for strings
RequestDecoder defaults to the JSON decoder if the request "Content-Type" header does not match any of the supported mime type or is missing altogether.
func ResponseDecoder ¶
ResponseDecoder returns a HTTP response decoder. The decoder handles the following content types:
- application/json using package encoding/json (default)
- application/xml using package encoding/xml
- application/gob using package encoding/gob
- text/html and text/plain for strings
type Dialer ¶
type Dialer interface {
// DialContext creates a client connection to the websocket server.
DialContext(ctx context.Context, url string, h http.Header) (*websocket.Conn, *http.Response, error)
}
Dialer creates a websocket connection to a given URL.
type Encoder ¶
Encoder provides the actual encoding algorithm used to write HTTP request and response bodies.
func RequestEncoder ¶
RequestEncoder returns a HTTP request encoder. The encoder uses package encoding/json.
func ResponseEncoder ¶
func ResponseEncoder(ctx context.Context, w http.ResponseWriter) Encoder
ResponseEncoder returns a HTTP response encoder leveraging the mime type set in the context under the AcceptTypeKey or the ContentTypeKey if any. The encoder supports the following mime types:
- application/json using package encoding/json
- application/xml using package encoding/xml
- application/gob using package encoding/gob
- text/html and text/plain for strings
ResponseEncoder defaults to the JSON encoder if the context AcceptTypeKey or ContentTypeKey value does not match any of the supported mime types or is missing altogether.
type EncodingFunc ¶
EncodingFunc allows a function with appropriate signature to act as a Decoder/Encoder.
func (EncodingFunc) Decode ¶
func (f EncodingFunc) Decode(v any) error
Decode implements the Decoder interface. It simply calls f(v).
func (EncodingFunc) Encode ¶
func (f EncodingFunc) Encode(v any) error
Encode implements the Encoder interface. It simply calls f(v).
type ErrorResponse ¶
type ErrorResponse = ProblemResponse
ErrorResponse is kept as an alias for compatibility with older Loom code.
type FileResponse ¶ added in v1.8.0
type FileResponse struct {
// Name is the content name used to infer its media type.
Name string
// ModTime is the content modification time. A zero value omits Last-Modified.
ModTime time.Time
// Content is the seekable content served in the response.
Content io.ReadSeeker
}
FileResponse describes seekable file or media content returned by a service method. Name is used to infer Content-Type, and a non-zero ModTime enables Last-Modified and conditional request handling. Content must support seeking so the standard library can serve byte ranges.
func (*FileResponse) ServeHTTP ¶ added in v1.8.0
func (f *FileResponse) ServeHTTP(w http.ResponseWriter, r *http.Request)
ServeHTTP serves the file response using net/http ServeContent semantics. Callers must set application response headers before calling ServeHTTP.
type FormValuesMarshaler ¶
type FormValuesMarshaler interface {
// MarshalFormValues appends the encoded representation of the receiver to
// the given values using the given field prefix.
MarshalFormValues(values url.Values, prefix string) error
}
FormValuesMarshaler is implemented by generated types that need custom application/x-www-form-urlencoded encoding semantics.
type FormValuesUnmarshaler ¶
type FormValuesUnmarshaler interface {
// UnmarshalFormValues decodes the receiver from the given values using the
// given field prefix.
UnmarshalFormValues(values url.Values, prefix string) error
}
FormValuesUnmarshaler is implemented by generated types that need custom application/x-www-form-urlencoded decoding semantics.
type HandlerLifecycle ¶ added in v1.8.0
type HandlerLifecycle struct {
// contains filtered or unexported fields
}
HandlerLifecycle owns the shared context, observation, and failure routing for one generated HTTP handler invocation.
func NewHandlerLifecycle ¶ added in v1.8.0
func NewHandlerLifecycle( w http.ResponseWriter, r *http.Request, service string, method string, ) *HandlerLifecycle
NewHandlerLifecycle starts the shared runtime lifecycle for a generated HTTP handler invocation.
func (*HandlerLifecycle) Context ¶ added in v1.8.0
func (l *HandlerLifecycle) Context() context.Context
Context returns the request context enriched with Loom transport metadata.
func (*HandlerLifecycle) DecodeFailed ¶ added in v1.8.0
func (l *HandlerLifecycle) DecodeFailed( err error, encodeError func(context.Context, http.ResponseWriter, error) error, handleFailure func(context.Context, http.ResponseWriter, error), )
DecodeFailed records and writes a request decoding failure.
func (*HandlerLifecycle) End ¶ added in v1.8.0
func (l *HandlerLifecycle) End()
End completes request observation and preserves panic propagation.
func (*HandlerLifecycle) HandlerFailed ¶ added in v1.8.0
func (l *HandlerLifecycle) HandlerFailed( err error, committed bool, encodeError func(context.Context, http.ResponseWriter, error) error, handleFailure func(context.Context, http.ResponseWriter, error), )
HandlerFailed records an endpoint failure. When committed is true, the transport can no longer encode an HTTP error response and the failure is routed directly to handleFailure.
func (*HandlerLifecycle) ResponseFailed ¶ added in v1.8.0
func (l *HandlerLifecycle) ResponseFailed( err error, handleFailure func(context.Context, http.ResponseWriter, error), )
ResponseFailed records a response write or close failure and routes it to handleFailure.
func (*HandlerLifecycle) ServeFile ¶ added in v1.8.0
func (l *HandlerLifecycle) ServeFile( r *http.Request, file *FileResponse, contentType string, encodeResponse func(context.Context, http.ResponseWriter) error, encodeError func(context.Context, http.ResponseWriter, error) error, handleFailure func(context.Context, http.ResponseWriter, error), )
ServeFile encodes response metadata, applies the designed content type, serves file with standard HTTP semantics, and closes seekable content when it also implements io.Closer.
func (*HandlerLifecycle) WriteRawBody ¶ added in v1.8.0
func (l *HandlerLifecycle) WriteRawBody( body io.ReadCloser, encodeResponse func(context.Context, http.ResponseWriter) error, encodeError func(context.Context, http.ResponseWriter, error) error, handleFailure func(context.Context, http.ResponseWriter, error), )
WriteRawBody encodes response metadata, streams body, closes it, and applies the generated HTTP late-error policy.
func (*HandlerLifecycle) Writer ¶ added in v1.8.0
func (l *HandlerLifecycle) Writer() http.ResponseWriter
Writer returns the response writer wrapped for transport observation.
type MiddlewareMuxer ¶
type MiddlewareMuxer interface {
Muxer
// Use appends a middleware to the list of middlewares to be applied
// to the Muxer. Use must be called before Handle or before mounting a
// generated server.
Use(func(http.Handler) http.Handler)
}
MiddlewareMuxer makes it possible to mount middlewares downstream of the Muxer.
type Mounter ¶
type Mounter interface {
Mount(Muxer)
}
Mounter is the interface for servers that allow mounting their endpoints into a muxer.
type MultipartFile ¶
type MultipartFile struct {
// Filename is the uploaded filename from the part headers.
Filename string
// ContentType is the part content type.
ContentType string
// Data contains the full part payload.
Data []byte
}
MultipartFile holds one multipart file part.
type MultipartForm ¶
type MultipartForm struct {
// Values contains non-file part values keyed by form field name.
Values url.Values
// Files contains file parts keyed by form field name.
Files map[string][]MultipartFile
}
MultipartForm is the parsed in-memory representation of a multipart request body.
func ReadMultipartForm ¶
func ReadMultipartForm(mr *multipart.Reader) (*MultipartForm, error)
ReadMultipartForm reads all multipart parts from mr into an in-memory form representation suitable for generated request decoding.
type MultipartPartContract ¶ added in v1.8.0
type MultipartPartContract struct {
// Name is the multipart form field name.
Name string
// MediaType is the default media type for the part value.
MediaType string
// Required reports whether the request body requires the part.
Required bool
}
MultipartPartContract describes one designed multipart request field.
type MultipartRequestContract ¶ added in v1.8.0
type MultipartRequestContract struct {
// ContentType is the request media type.
ContentType string
// Parts lists the designed multipart fields in body order.
Parts []MultipartPartContract
}
MultipartRequestContract describes the stable request shape supplied to a consumer-owned multipart response scenario.
type Muxer ¶
type Muxer interface {
// Handle registers the handler function for the given method
// and pattern.
Handle(method, pattern string, handler http.HandlerFunc)
// ServeHTTP dispatches the request to the handler whose method
// matches the request method and whose pattern most closely
// matches the request URL.
ServeHTTP(http.ResponseWriter, *http.Request)
// Vars returns the path variables captured for the given
// request.
Vars(*http.Request) map[string]string
}
Muxer is the HTTP request multiplexer interface used by the generated code. ServeHTTP must match the HTTP method and URL of each incoming request against the list of registered patterns and call the handler for the corresponding method and the pattern that most closely matches the URL.
The patterns may include wildcards that identify URL segments that must be captured.
There are two forms of wildcards the implementation must support:
"{name}" wildcards capture a single path segment, for example the pattern "/images/{name}" captures "/images/favicon.ico" and adds the key "name" with the value "favicon.ico" to the map returned by Vars.
"{*name}" wildcards must appear at the end of the pattern and captures the entire path starting where the wildcard matches. For example the pattern "/images/{*filename}" captures "/images/public/thumbnail.jpg" and associates the key key "filename" with "public/thumbnail.jpg" in the map returned by Vars.
The names of wildcards must match the regular expression "[a-zA-Z0-9_]+".
type ProblemResponse ¶ added in v1.0.9
type ProblemResponse struct {
Type string `json:"type" xml:"type" form:"type"`
Title string `json:"title" xml:"title" form:"title"`
Status int `json:"status" xml:"status" form:"status"`
Detail string `json:"detail" xml:"detail" form:"detail"`
Instance string `json:"instance" xml:"instance" form:"instance"`
Code string `json:"code" xml:"code" form:"code"`
RetryHint *string `json:"retry_hint,omitempty" xml:"retry_hint,omitempty" form:"retry_hint,omitempty"`
}
ProblemResponse is the default RFC 9457 problem document encoded in HTTP responses for Loom service errors.
func NewProblemResponse ¶ added in v1.0.9
func NewProblemResponse(_ context.Context, err error, status int, problemType, problemTitle string) *ProblemResponse
NewProblemResponse creates a problem document from err using the supplied status and optional explicit type/title overrides.
func (*ProblemResponse) StatusCode ¶ added in v1.0.9
func (resp *ProblemResponse) StatusCode() int
StatusCode returns the HTTP status code carried by the problem document.
type RequestMetadata ¶ added in v1.6.0
type RequestMetadata struct {
// Method is the request method.
Method string
// Path is the decoded request URL path.
Path string
// Host is the effective host after trusted-proxy processing.
Host string
// Scheme is the effective http or https scheme after trusted-proxy processing.
Scheme string
// ClientAddr is the effective client IP after trusted-proxy processing.
ClientAddr string
// PeerAddr is the direct network peer IP and is never forwarded.
PeerAddr string
// RequestID is the X-Request-Id header value.
RequestID string
// UserAgent is the request User-Agent value.
UserAgent string
// Origin is the request Origin value.
Origin string
// SecFetchSite is the request Sec-Fetch-Site value.
SecFetchSite string
// contains filtered or unexported fields
}
RequestMetadata is an immutable snapshot of an inbound HTTP request.
func RequestMetadataFromContext ¶ added in v1.6.0
func RequestMetadataFromContext(ctx context.Context) (RequestMetadata, bool)
RequestMetadataFromContext returns the inbound request metadata snapshot.
func (RequestMetadata) HeaderValues ¶ added in v1.6.0
func (m RequestMetadata) HeaderValues(name string) []string
HeaderValues returns a copy of the retained values for name.
func (RequestMetadata) Headers ¶ added in v1.6.0
func (m RequestMetadata) Headers() http.Header
Headers returns a fresh clone of all explicitly retained headers.
type RequestMetadataPolicy ¶ added in v1.6.0
type RequestMetadataPolicy struct {
// contains filtered or unexported fields
}
RequestMetadataPolicy is an immutable trusted-proxy and retained-header policy.
func NewRequestMetadataPolicy ¶ added in v1.6.0
func NewRequestMetadataPolicy( retainedHeaders []string, trustedProxies []netip.Prefix, ) (RequestMetadataPolicy, error)
NewRequestMetadataPolicy validates and returns an immutable metadata policy. retainedHeaders is an explicit allowlist; Authorization and Cookie are not retained unless named. trustedProxies contains direct peer CIDR ranges that may supply X-Forwarded-For, X-Forwarded-Host, and X-Forwarded-Proto.
type ResolverMuxer ¶
type ResolverMuxer interface {
MiddlewareMuxer
ResolvePattern(*http.Request) string
}
ResolverMuxer is a MiddlewareMuxer that can resolve the route pattern used to register the handler for the given request.
func NewMuxer ¶
func NewMuxer() ResolverMuxer
NewMuxer returns a Muxer implementation based on a Chi router.
The returned muxer sets r.Pattern (Go 1.22+) on every matched request. When mux middleware is registered, r.Pattern is set before the middleware runs so observability middleware such as otelhttp can read the matched route for span attributes and metrics. To take advantage of this, register otelhttp as a mux middleware rather than wrapping the mux externally:
mux := loomhttp.NewMuxer()
mux.Use(otelhttp.NewMiddleware("service"))
type ResponseContractCase ¶ added in v1.8.0
type ResponseContractCase struct {
// ID is stable while the service response contract is unchanged.
ID string
// Kind identifies a successful result or service error response.
Kind ResponseContractCaseKind
// Transport identifies the response protocol.
Transport ResponseContractTransport
// StatusCode is the exact declared HTTP status code.
StatusCode int
// ErrorName is the expected Loom-Error header value for an error case.
ErrorName string
// ContentTypes lists the allowed response media types.
ContentTypes []string
// RequiredHeaders lists declared response headers that must be present.
RequiredHeaders []string
// RequiredCookies lists declared response cookies that must be present.
RequiredCookies []string
// Multipart describes the designed multipart request, if present.
Multipart *MultipartRequestContract
// SSE describes stream assertions for an SSE success case.
SSE *SSEResponseContract
// WebSocket describes stream assertions for a WebSocket success case.
WebSocket *WebSocketResponseContract
}
ResponseContractCase describes the HTTP wire invariants for one declared response branch. It does not describe how application code reaches that branch.
type ResponseContractCaseKind ¶ added in v1.8.0
type ResponseContractCaseKind string
ResponseContractCaseKind identifies whether a generated response contract case describes a successful result or a service error.
type ResponseContractTransport ¶ added in v1.8.0
type ResponseContractTransport string
ResponseContractTransport identifies the wire protocol validated by a generated response contract case.
type RuntimeCORSPolicy ¶ added in v1.5.0
type RuntimeCORSPolicy struct {
// contains filtered or unexported fields
}
RuntimeCORSPolicy is an immutable, validated startup snapshot of a CORS policy supplied by application configuration.
func NewRuntimeCORSPolicy ¶ added in v1.5.0
func NewRuntimeCORSPolicy(policy CORSPolicy) (RuntimeCORSPolicy, error)
NewRuntimeCORSPolicy validates policy and returns an immutable startup snapshot suitable for generated servers declared with RuntimeCORS.
func (RuntimeCORSPolicy) HandlePreflight ¶ added in v1.5.0
func (p RuntimeCORSPolicy) HandlePreflight(w http.ResponseWriter, r *http.Request, allowedMethods []string)
HandlePreflight writes a preflight response using the runtime CORS policy.
func (RuntimeCORSPolicy) Handler ¶ added in v1.5.0
func (p RuntimeCORSPolicy) Handler(next http.HandlerFunc) http.HandlerFunc
Handler wraps next and applies the runtime CORS policy to actual requests.
type SSEControl ¶ added in v1.6.0
type SSEControl interface {
Open(context.Context) error
SendComment(context.Context, string) error
}
SSEControl exposes transport lifecycle operations implemented by generated server SSE streams. Endpoint implementations may type assert their stream to this interface without depending on generated concrete types.
type SSEEvent ¶
SSEEvent represents a parsed server-sent event frame.
func ParseSSEEvent ¶
ParseSSEEvent parses a single SSE event frame.
type SSEMessage ¶
SSEMessage describes an SSE frame to write to an output stream.
type SSEResponseContract ¶ added in v1.8.0
type SSEResponseContract struct {
// Direction is the designed stream direction.
Direction string
// MessageType is the designed streaming result type name.
MessageType string
// DataField is the result field encoded into SSE data, if any.
DataField string
// DataEncoding identifies whether SSE data is JSON or plain text.
DataEncoding string
// IDField is the result field encoded into SSE id, if any.
IDField string
// EventField is the result field encoded into SSE event, if any.
EventField string
// RetryField is the result field encoded into SSE retry, if any.
RetryField string
// IDRequired reports whether every event must include an ID.
IDRequired bool
// EventTypeRequired reports whether every event must include a type.
EventTypeRequired bool
// EventTypes lists allowed projection discriminator values, if constrained.
EventTypes []string
// Terminal identifies the expected stream completion behavior.
Terminal string
}
SSEResponseContract describes the observable wire contract of an SSE stream.
type SSEResponseContractObservation ¶ added in v1.8.0
type SSEResponseContractObservation struct {
// Response is the HTTP handshake response.
Response *http.Response
// Events contains parsed SSE frames observed before completion.
Events []SSEEvent
// TerminalError is the final error returned by the stream reader.
TerminalError error
}
SSEResponseContractObservation contains the response and frames produced by one consumer-owned SSE scenario.
type SSEStreamReader ¶ added in v1.3.0
type SSEStreamReader struct {
// contains filtered or unexported fields
}
SSEStreamReader reads framed Server-Sent Events from a response body.
func NewSSEStreamReader ¶ added in v1.3.0
func NewSSEStreamReader(body io.ReadCloser) *SSEStreamReader
NewSSEStreamReader returns a reader for framed Server-Sent Events.
func (*SSEStreamReader) Close ¶ added in v1.3.0
func (r *SSEStreamReader) Close() error
Close closes the SSE stream body.
type SSEStreamWriter ¶ added in v1.6.0
type SSEStreamWriter struct {
// contains filtered or unexported fields
}
SSEStreamWriter owns serialized writes for a generated server SSE stream.
func NewSSEStreamWriter ¶ added in v1.6.0
func NewSSEStreamWriter( w http.ResponseWriter, requestCtx context.Context, transport loomtransport.TransportKind, policy StreamWritePolicy, ) *SSEStreamWriter
NewSSEStreamWriter returns a shared writer for a generated server SSE stream.
func (*SSEStreamWriter) Close ¶ added in v1.6.0
func (s *SSEStreamWriter) Close() error
Close prevents later control and event writes.
func (*SSEStreamWriter) Context ¶ added in v1.6.0
func (s *SSEStreamWriter) Context() context.Context
Context returns the inbound request context associated with the stream.
func (*SSEStreamWriter) Open ¶ added in v1.6.0
func (s *SSEStreamWriter) Open(ctx context.Context) error
Open commits and flushes the successful SSE response once.
func (*SSEStreamWriter) SendComment ¶ added in v1.6.0
func (s *SSEStreamWriter) SendComment(ctx context.Context, text string) error
SendComment writes and flushes one SSE comment frame.
func (*SSEStreamWriter) Started ¶ added in v1.6.0
func (s *SSEStreamWriter) Started() bool
Started reports whether the successful SSE response has been committed.
func (*SSEStreamWriter) WriteEvent ¶ added in v1.6.0
WriteEvent serializes and flushes one generated SSE event.
type Server ¶
Server is the HTTP server interface used to wrap the server handlers with the given middleware.
type Servers ¶
type Servers []Server
Servers is a list of servers.
type Statuser ¶
type Statuser interface {
// StatusCode return the HTTP status code used to encode the response
// when not defined in the design.
StatusCode() int
}
Statuser is implemented by error response object to provide the response HTTP status code.
type StreamWritePolicy ¶ added in v1.6.0
type StreamWritePolicy struct {
// contains filtered or unexported fields
}
StreamWritePolicy configures the maximum duration of each server-stream network write or flush. The zero value preserves unbounded writes.
func NewStreamWritePolicy ¶ added in v1.6.0
func NewStreamWritePolicy(timeout time.Duration) (StreamWritePolicy, error)
NewStreamWritePolicy returns an immutable server-stream write policy.
func (StreamWritePolicy) Timeout ¶ added in v1.6.0
func (p StreamWritePolicy) Timeout() time.Duration
Timeout returns the maximum duration allowed for each write or flush.
type UnaryHandlerSpec ¶ added in v1.8.0
type UnaryHandlerSpec[Payload, Result any] struct { // Service is the designed service name. Service string // Method is the designed service method name. Method string // Decode converts an HTTP request into the service payload. A nil // function supplies the zero value of Payload. Decode func(*http.Request) (Payload, error) // Invoke calls the typed service endpoint. Invoke func(context.Context, Payload) (Result, error) // EncodeResponse writes a successful typed result. EncodeResponse func(context.Context, http.ResponseWriter, Result) error // EncodeError writes a request or endpoint error. EncodeError func(context.Context, http.ResponseWriter, error) error // HandleFailure receives errors that cannot be written as responses. HandleFailure func(context.Context, http.ResponseWriter, error) }
UnaryHandlerSpec defines the typed adapters and runtime policy for one ordinary unary HTTP endpoint.
type UnaryResult ¶ added in v1.8.0
type UnaryResult[Result any] struct { // Value is the raw value returned by the service endpoint. Value any }
UnaryResult carries an endpoint result to its typed response adapter. Result identifies the designed result type, and Value retains the raw endpoint value for generated validation.
type Upgrader ¶
type Upgrader interface {
// Upgrade upgrades the HTTP connection to the websocket protocol.
Upgrade(w http.ResponseWriter, r *http.Request, responseHeader http.Header) (*websocket.Conn, error)
}
Upgrader is an HTTP connection that is able to upgrade to websocket.
type WebSocketResponseContract ¶ added in v1.8.0
type WebSocketResponseContract struct {
// Direction is the designed stream direction.
Direction string
// InboundMessageType is the designed client-to-server message type name.
InboundMessageType string
// OutboundMessageType is the designed server-to-client message type name.
OutboundMessageType string
// HandshakeHeaders lists required WebSocket upgrade response headers.
HandshakeHeaders []string
// Terminal identifies the expected stream completion behavior.
Terminal string
}
WebSocketResponseContract describes the observable wire contract of a WebSocket stream.
type WebSocketResponseContractObservation ¶ added in v1.8.0
type WebSocketResponseContractObservation struct {
// Response is the HTTP upgrade response.
Response *http.Response
// Messages contains server-to-client JSON messages in wire order.
Messages []json.RawMessage
// TerminalError is the final error returned by the WebSocket reader. It is
// nil when the contract terminates with one final response message.
TerminalError error
}
WebSocketResponseContractObservation contains the handshake, JSON messages, and terminal read result produced by one consumer-owned WebSocket scenario.
type WebSocketStream ¶ added in v1.3.0
type WebSocketStream struct {
// contains filtered or unexported fields
}
WebSocketStream owns the lifecycle for a WebSocket connection used by generated HTTP streaming clients and servers.
func NewWebSocketStream ¶ added in v1.3.0
func NewWebSocketStream(conn *websocket.Conn, policies ...StreamWritePolicy) *WebSocketStream
NewWebSocketStream wraps conn with shared generated-stream lifecycle behavior. A nil conn is allowed so generated server streams can be allocated before the WebSocket upgrade happens.
func (*WebSocketStream) Close ¶ added in v1.3.0
func (s *WebSocketStream) Close() error
Close closes the WebSocket connection at most once.
func (*WebSocketStream) Conn ¶ added in v1.3.0
func (s *WebSocketStream) Conn() *websocket.Conn
Conn returns the wrapped Gorilla WebSocket connection.
func (*WebSocketStream) ReadJSON ¶ added in v1.3.0
func (s *WebSocketStream) ReadJSON(ctx context.Context, v any) error
ReadJSON reads one JSON WebSocket frame while honoring ctx cancellation.
func (*WebSocketStream) SetConn ¶ added in v1.3.0
func (s *WebSocketStream) SetConn(conn *websocket.Conn)
SetConn replaces the wrapped Gorilla WebSocket connection.
func (*WebSocketStream) WriteClose ¶ added in v1.3.0
func (s *WebSocketStream) WriteClose(message string) error
WriteClose writes a close control frame. It does not close the underlying connection; call Close after WriteClose to release the socket.
Source Files
¶
Directories
¶
| Path | Synopsis |
|---|---|
|
Package cli contains runtime helpers for generated HTTP command-line clients.
|
Package cli contains runtime helpers for generated HTTP command-line clients. |
|
Package codegen generates HTTP servers, clients, and OpenAPI specifications from an evaluated Loom design.
|
Package codegen generates HTTP servers, clients, and OpenAPI specifications from an evaluated Loom design. |
|
openapi
Package openapi provides common algorithms and data structures used to generate OpenAPI 3.1 and 3.2 specifications from Loom designs.
|
Package openapi provides common algorithms and data structures used to generate OpenAPI 3.1 and 3.2 specifications from Loom designs. |
|
openapi/v3
Package openapiv3 contains the algorithms and data structures used to generate OpenAPI 3.1 and 3.2 specifications from Loom designs.
|
Package openapiv3 contains the algorithms and data structures used to generate OpenAPI 3.1 and 3.2 specifications from Loom designs. |
|
Package middleware contains HTTP middlewares that wrap a HTTP handler to provide ancillary functionality such as capturing HTTP details into the request context or printing debug information on incoming requests.
|
Package middleware contains HTTP middlewares that wrap a HTTP handler to provide ancillary functionality such as capturing HTTP details into the request context or printing debug information on incoming requests. |
|
otel
Package otel provides thin OpenTelemetry middleware helpers for Loom HTTP servers and clients.
|
Package otel provides thin OpenTelemetry middleware helpers for Loom HTTP servers and clients. |