Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

name: request-envelope
description: Request shapes, envelope contract, slot keys, smart defaults, streamability and time zones. Use when authoring or adapting any Pulse Request.
type: guide
kind: design
applies_to: process, compose, sample, facet, inspect, predict, manifest
covers: [Request, ComposedRequest, ChainRequest, FacetRequest, SampleRequest, Envelope]

Request envelope

Envelope (response side)

Every --json output and facade response uses descriptor.Envelope:

{"format_version": "1.1", "data": {...}, "request": {...}, "errors": [], "warnings": []}
  • format_version — "1.1"; additive data fields never bump it.
  • data — the operation’s payload.
  • request — opt-in echo of the normalized request (--echo-request); streaming skips it.
  • errors / warnings — always arrays of {code, message, details}; resolve via pulse_errors_lookup.

Request shapes (per command)

Operation (CLI)Wire typeTop-level keys
process, predict (pulse api process)Requestcohort, time_zone, filterers, features, attributes, groups, aggregations, windows, sort, tests, post_tests, joins, crosstab, overlays, outputs, return, multiplicity, vectors, matrices
compose (pulse api compose)ComposedRequestrequests[] (each = Request), return (overlays only)
process chain (pulse api process-chain)ChainRequestcohort, stages[], overlays (each stage: {request: Request})
facet (pulse api facet)FacetRequestcohort, time_zone, fields[], top_k, percentiles, histogram, additive, overlays
sample (pulse api sample)SampleRequestcohort, count, offset

Each operation’s MCP tool is listed in manifest mcp_tools.

Row weight: Request.weight {field, kind}; per-slot weight — a field, {field, kind} or null (null opts out, absent inherits); pulse.Options.DefaultWeight. See weighting.

Request slot order is pipeline order: features → filterers → attributes → groups → aggregations → windows → sort; sort shares the window comparator (nulls last both ways). A derived name (feature output, attribute / aggregation / window label) exists only DOWNSTREAM of its producer. Runtime and predict refuse (SERVICE_VALIDATION) a name nothing produces, a label shadowing a column, and an aggregation label equal to a group field or another aggregation label.

Canonical process Request

{
  "cohort": {"filename": "sales.pulse"},
  "filterers":    [{"type": "FILTER_INCLUDE", "field": "status", "values": ["active"]}],
  "groups":       [{"type": "GROUP_CATEGORY", "field": "region"}],
  "aggregations": [
    {"type": "AGG_COUNT", "field": "id",      "label": "n"},
    {"type": "AGG_SUM",   "field": "revenue", "label": "revenue"}
  ]
}

Every type is an operator constant from pulse_manifest components.<category>; runnable requests: pulse_examples_search.

Slot-key gotchas

Unknown keys drop silently on decode.

WrongRight
groupersgroups
aggregatorsaggregations
filtersfilterers
tests_postpost_tests
outputoutputs
request (Compose top-level)requests

Per-operator slot: type, field, label, optional params (keys per operator: its atomic skill).

Smart defaults

When a slot names field but omits type, the engine infers from schema type. Predict reports filled slots under data.defaults_applied.

Field typeDefault aggDefault grouper
numeric (u4, u8..u64, f32/f64, decimal128)AGG_SUMGROUP_RANGE (interval 10)
categorical_*, packed_boolAGG_MODE_COUNTGROUP_CATEGORY
date, datetime (truncated)(explicit only)GROUP_DATE ("day")

Never override explicit type or cross categories; tests / filterers / attrs / features / windows never defaulted. Disable via pulse.Options{DisableDefaults: true} / --no-defaults.

Streamability

pulse_predict returns data.streamable: bool + data.streamable_reasons: []string.

  • Streams: online aggregators (manifest streamable: true), ungrouped or under a streamable grouper; row-local attributes; whole-cohort-statistic attributes (z-scores and the like) in two passes.
  • Buffers: order-statistic aggregators (median, percentile); percentile-rank attributes; groupers with streamable: false; windows; decimal aggregations; two-pass attributes combined with features or groups; tier-2 post tests.

streamable_reasons is authoritative.

Time zones

time_zone sits on Request and FacetRequest (Compose / Chain: per inner Request; SampleRequest: none). Slot tz sits on groups, filterers, attributes, features and crosstab.rows/columns entries — a slot key, never inside params. Names are UTC or IANA (Europe/Berlin); EST, Local, +05:00 → PULSE_TIMEZONE_UNKNOWN.

Precedence per slot: tz → time_zone → pulse.Options.DefaultTimeZone → UTC. Only manifest zone: "capable" operators take tz; a zone: "following" operator (the year-over-year overlay) inherits its host grouper’s zone; extension operators are never capable.

On a datetime field instants read on their local day (DST-correct). Refused with PROCESSING_CONFIG: tz on a non-capable operator; explicit tz on a date field (even "UTC"); a non-UTC zone on a derived field. An inherited zone on a date field is not applied. UTC (and aliases like Etc/UTC) is byte-identical to no zone.

Predict-specific data fields

streamable, streamable_reasons, defaults_applied, weights / suggested_weight (weighting), resolved_vectors, time_zones (per zone-capable slot: {slot, operator, field_type, tz, source}, source ∈ slot|request|options|default), suggestions (on_invalid="suggest"), per-slot buffered_components (non-mergeable).

response-components (the Response.Components block) · response-shaping (return: trim the response, wire precision) · session-bootstrap (MCP session order) · aggregation-design / grouper-design / attribute-composition (slot shapes) · compose-requests · facet-design · streaming-and-watching (stream chunks, request hashing) · multiplicity-correction.