Documentation
¶
Overview ¶
Package http2 decodes HTTP/2 frames per RFC 9113.
Wrap-vs-native judgement
Native. RFC 9113 is fully public; HTTP/2 wire format is a tight 9-byte frame header (Length 24-bit + Type 8-bit + Flags 8-bit + Reserved 1-bit + Stream ID 31-bit) plus per-type body layouts that are themselves fixed-field. Operators paste TCP-stream bytes from a Wireshark Follow HTTP/2 view, a curl --http2 -v trace, or a Go pprof trace and inspect every documented frame field. Pure offline parser, no encryption at this layer (TLS termi- nation is upstream).
What this package covers
**Connection preface** — the literal 24-byte preface "PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n" sent by the client immediately after the upgrade. Auto-detected and surfaced as a synthetic "preface" frame at the start of the stream.
**Frame header** (9 bytes fixed): Length (24-bit BE payload-length-in-bytes) + Type (1 byte) + Flags (1 byte) + R+Stream Identifier (32-bit; high bit reserved, 31-bit stream ID). Stream ID 0 is the connection-level stream (used for SETTINGS / PING / GOAWAY).
**10 frame types** (RFC 9113 §6) with per-type bodies:
**0x0 DATA** — optional pad-length (1 byte if PADDED flag set) + data + padding. END_STREAM flag marks the last frame in a request/response body.
**0x1 HEADERS** — optional pad-length + optional priority block (5 bytes: exclusive+stream-dep+weight, PRIORITY flag) + HPACK header block + padding. END_HEADERS flag marks the last header frame in a CONTINUATION chain; END_STREAM marks no request body.
**0x2 PRIORITY** (deprecated in RFC 9113 but still valid) — exclusive bit + stream dependency (31-bit)
weight (1 byte).
**0x3 RST_STREAM** — error code (uint32 BE). 14-entry name table (NO_ERROR / PROTOCOL_ERROR / INTERNAL_ERROR / FLOW_CONTROL_ERROR / SETTINGS_TIMEOUT / STREAM_CLOSED / FRAME_SIZE_ERROR / REFUSED_STREAM / CANCEL / COMPRESSION_ERROR / CONNECT_ERROR / ENHANCE_YOUR_CALM / INADEQUATE_SECURITY / HTTP_1_1_REQUIRED).
**0x4 SETTINGS** — list of (Identifier uint16 BE + Value uint32 BE) pairs. 7-entry parameter table (HEADER_TABLE_SIZE / ENABLE_PUSH / MAX_CONCURRENT_ STREAMS / INITIAL_WINDOW_SIZE / MAX_FRAME_SIZE / MAX_HEADER_LIST_SIZE / ENABLE_CONNECT_PROTOCOL). ACK flag = empty body acknowledgement.
**0x5 PUSH_PROMISE** (deprecated in RFC 9113) — optional pad-length + R+promised-stream-ID (31-bit)
HPACK header block + padding.
**0x6 PING** — 8 bytes opaque payload. ACK flag = reply to a peer's PING. Used as keep-alive + RTT probe.
**0x7 GOAWAY** — R+last-stream-ID (31-bit) + error code (uint32) + opaque debug data.
**0x8 WINDOW_UPDATE** — R+window-size-increment (31-bit, must be > 0).
**0x9 CONTINUATION** — HPACK header block fragment (continuation of HEADERS or PUSH_PROMISE).
**Multi-frame walker** — one buffer may carry multiple concatenated frames; iterator walks frame-by-frame until the buffer is consumed.
**Flags decoding per frame type** — END_STREAM / END_HEADERS / PADDED / PRIORITY / ACK flags surfaced with their type-specific names.
What this package does NOT cover (deliberately out of scope)
HPACK header decompression (RFC 7541) — the static- table indexing + Huffman coding requires session state (the dynamic table evolves across frames). Compressed header bytes are surfaced as hex; a sibling Spec would handle decoding.
TLS layer — operators feed cleartext HTTP/2 frame bytes after TLS decryption (handled by Wireshark's SSL/TLS dissector with the appropriate key file).
HTTP/2 connection state machine — frames are decoded individually; tracking which stream is in which state belongs in a session-tracker.
HTTP/3 (RFC 9114) — wholly different wire format (QPACK + QUIC); a separate Spec.
WebSocket-over-HTTP/2 (RFC 8441 :protocol pseudo- header) — surfaced via the HPACK bytes when present.
Index ¶
Constants ¶
const ConnectionPreface = "PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n"
ConnectionPreface is the 24-byte literal sent by the client at the start of every HTTP/2 connection (RFC 9113 §3.4).
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type ContinuationFrame ¶
type ContinuationFrame struct {
HPACKBlockHex string `json:"hpack_header_block_hex,omitempty"`
HPACKBlockLen int `json:"hpack_header_block_length"`
}
ContinuationFrame is type 0x9.
type DataFrame ¶
type DataFrame struct {
PaddingLen int `json:"padding_length,omitempty"`
DataLen int `json:"data_length"`
DataHex string `json:"data_hex,omitempty"`
}
DataFrame is type 0x0.
type Frame ¶
type Frame struct {
Length int `json:"length"`
Type int `json:"type"`
TypeName string `json:"type_name"`
Flags int `json:"flags"`
FlagsDecoded string `json:"flags_decoded,omitempty"`
StreamID uint32 `json:"stream_id"`
IsPreface bool `json:"is_preface,omitempty"`
BodyHex string `json:"body_hex,omitempty"`
Data *DataFrame `json:"data,omitempty"`
Headers *HeadersFrame `json:"headers,omitempty"`
Priority *PriorityFrame `json:"priority,omitempty"`
RstStream *RstStreamFrame `json:"rst_stream,omitempty"`
Settings *SettingsFrame `json:"settings,omitempty"`
PushPromise *PushPromiseFrame `json:"push_promise,omitempty"`
Ping *PingFrame `json:"ping,omitempty"`
GoAway *GoAwayFrame `json:"goaway,omitempty"`
WindowUpdate *WindowUpdateFrame `json:"window_update,omitempty"`
Continuation *ContinuationFrame `json:"continuation,omitempty"`
}
Frame is one decoded HTTP/2 frame.
type GoAwayFrame ¶
type GoAwayFrame struct {
LastStreamID uint32 `json:"last_stream_id"`
ErrorCode uint32 `json:"error_code"`
ErrorCodeName string `json:"error_code_name"`
DebugHex string `json:"debug_data_hex,omitempty"`
}
GoAwayFrame is type 0x7.
type HeadersFrame ¶
type HeadersFrame struct {
PaddingLen int `json:"padding_length,omitempty"`
Exclusive bool `json:"priority_exclusive,omitempty"`
StreamDependency uint32 `json:"priority_stream_dependency,omitempty"`
Weight int `json:"priority_weight,omitempty"`
HasPriority bool `json:"has_priority,omitempty"`
HPACKBlockHex string `json:"hpack_header_block_hex,omitempty"`
HPACKBlockLen int `json:"hpack_header_block_length"`
}
HeadersFrame is type 0x1.
type PriorityFrame ¶
type PriorityFrame struct {
Exclusive bool `json:"exclusive"`
StreamDependency uint32 `json:"stream_dependency"`
Weight int `json:"weight"`
}
PriorityFrame is type 0x2.
type PushPromiseFrame ¶
type PushPromiseFrame struct {
PaddingLen int `json:"padding_length,omitempty"`
PromisedStreamID uint32 `json:"promised_stream_id"`
HPACKBlockHex string `json:"hpack_header_block_hex,omitempty"`
HPACKBlockLen int `json:"hpack_header_block_length"`
}
PushPromiseFrame is type 0x5.
type Result ¶
type Result struct {
Frames []Frame `json:"frames"`
FrameCount int `json:"frame_count"`
TotalBytes int `json:"total_bytes"`
HasPreface bool `json:"has_preface"`
Summary string `json:"summary"`
}
Result is the top-level decoded view.
type RstStreamFrame ¶
type RstStreamFrame struct {
ErrorCode uint32 `json:"error_code"`
ErrorCodeName string `json:"error_code_name"`
}
RstStreamFrame is type 0x3.
type SettingsFrame ¶
type SettingsFrame struct {
IsAck bool `json:"is_ack"`
Parameters []SettingsParam `json:"parameters,omitempty"`
}
SettingsFrame is type 0x4.
type SettingsParam ¶
type SettingsParam struct {
Identifier uint16 `json:"identifier"`
IdentifierName string `json:"identifier_name"`
Value uint32 `json:"value"`
}
SettingsParam is one identifier/value pair in a SETTINGS frame.
type WindowUpdateFrame ¶
type WindowUpdateFrame struct {
WindowSizeIncrement uint32 `json:"window_size_increment"`
}
WindowUpdateFrame is type 0x8.