Documentation
¶
Index ¶
- Constants
- func AckLink(page *models.Page) string
- func AcknowledgePage(tx *sql.Tx, pageId int, userId *int, via string, now time.Time) (bool, error)
- func AutoResolveByDedupKey(ruleId int, dedupToken string) error
- func AutoResolveByDedupKeyTx(tx *sql.Tx, ruleId int, dedupToken string, now time.Time) (bool, error)
- func CurrentAndNext(def *models.OncallScheduleDefinition, tz *time.Location, ...) (current *Shift, next *Shift)
- func CurrentOnCallForSchedule(tx *sql.Tx, scheduleId int, at time.Time) ([]int, error)
- func EmailDeliveryFor(accountEmail string, override string) (json.RawMessage, string)
- func EscalationChannelPolicyId(configJSON json.RawMessage) int
- func LoadTimezone(name string) (*time.Location, error)
- func MarshalDefinition(def *models.OncallScheduleDefinition) ([]byte, error)
- func MarshalPolicyDefinition(def *PolicyDefinition) ([]byte, error)
- func NewLayerId() string
- func OpenPageFromDispatch(configJSON json.RawMessage, rule *models.NotificationRuleWithChannel, ...) (bool, error)
- func OpenTestPage(policyId int, projectId uuid.UUID, channelId int, channelName string) (bool, error)
- func ParseDefinition(raw []byte) (*models.OncallScheduleDefinition, error)
- func ParseEmailOverride(config []byte) string
- func PoliciesReferencing(tx *sql.Tx, organizationId int, targetType string, targetIds ...int) ([]string, error)
- func RemoveUserFromOrgSchedules(tx *sql.Tx, organizationId int, userId int) error
- func ResolveAt(def *models.OncallScheduleDefinition, tz *time.Location, ...) []int
- func ResolvePage(tx *sql.Tx, pageId int, userId int, now time.Time) (bool, error)
- func ResolveUrgency(policyUrgency string, severity string) string
- func SMSPhoneNumber(config []byte) string
- func StartEscalator(ctx context.Context)
- func Wake()
- type OncallUser
- type PolicyDefinition
- type PolicyStep
- type ProjectOnCall
- type ScheduleRef
- type Shift
- type StepTarget
Constants ¶
const ( AckViaDashboard = "dashboard" AckViaLink = "link" )
const ( MaxPolicySteps = 10 MaxTargetsPerStep = 10 MinStepDelayMinutes = 1 MaxStepDelayMinutes = 1440 MaxPolicyRepeatCount = 5 )
const ( TargetSchedule = "schedule" TargetUser = "user" TargetTeam = "team" TargetChannel = "channel" )
const ( RestrictionDaily = "daily" RestrictionWeekly = "weekly" )
const ( RotationDaily = "daily" RotationWeekly = "weekly" RotationCustom = "custom" )
const ( MaxLayersPerSchedule = 20 MaxUsersPerLayer = 50 MaxRestrictionsPerLayer = 10 MaxCustomIntervalDays = 365 MaxTimelineRangeDays = 62 MaxOverrideDurationDays = 30 )
const SchemaVersion = 1
const UrgencyAuto = "auto"
Variables ¶
This section is empty.
Functions ¶
func AckLink ¶
AckLink builds the absolute dashboard link that acknowledges a page. The project id is included so the dashboard can switch to the page's project — pages are resolved against the viewer's selected project.
func AcknowledgePage ¶
AcknowledgePage transitions open -> acknowledged and cancels every queued or retrying delivery under the page's cancel key (mirroring their delivery log rows). Returns false when the page was not open. The single home for ack-side cancellation: used by the dashboard controller and the tokenized ack endpoint alike. userId is nil for anonymous link-acks.
func AutoResolveByDedupKey ¶ added in v1.9.13
AutoResolveByDedupKey is the transaction-owning variant, registered as the notifications page resolver in cmd/run.go (that caller holds no transaction; nesting one would deadlock the single-connection SQLite main DB).
func AutoResolveByDedupKeyTx ¶ added in v1.9.13
func AutoResolveByDedupKeyTx(tx *sql.Tx, ruleId int, dedupToken string, now time.Time) (bool, error)
AutoResolveByDedupKeyTx resolves the unresolved page holding the rule-scoped dedup key with no resolving user (a system resolve, e.g. a synthetic check recovering), cancelling its queued deliveries. Runs in the caller's transaction. Returns whether a page was resolved.
func CurrentAndNext ¶
func CurrentAndNext(def *models.OncallScheduleDefinition, tz *time.Location, overrides []*models.OncallOverride, now time.Time) (current *Shift, next *Shift)
CurrentAndNext gives the UI "on call until X, next up Y". The lookahead is bounded so sparse schedules terminate.
func CurrentOnCallForSchedule ¶
CurrentOnCallForSchedule resolves who is on call for a schedule at the given instant, filtered to current members of the schedule's organization. A missing schedule resolves to nobody rather than an error, so dangling references never abort a caller.
func EmailDeliveryFor ¶
func EmailDeliveryFor(accountEmail string, override string) (json.RawMessage, string)
EmailDeliveryFor builds the email adapter config (and display description) for a recipient, applying the override when present. Overrides are masked in the delivery log; the account email is not.
func EscalationChannelPolicyId ¶
func EscalationChannelPolicyId(configJSON json.RawMessage) int
EscalationChannelPolicyId extracts the policyId from an escalation channel's config; 0 means the config is missing or malformed.
func LoadTimezone ¶
LoadTimezone validates an IANA timezone name, returning a user-facing error.
func MarshalDefinition ¶
func MarshalDefinition(def *models.OncallScheduleDefinition) ([]byte, error)
func MarshalPolicyDefinition ¶
func MarshalPolicyDefinition(def *PolicyDefinition) ([]byte, error)
func NewLayerId ¶
func NewLayerId() string
func OpenPageFromDispatch ¶
func OpenPageFromDispatch(configJSON json.RawMessage, rule *models.NotificationRuleWithChannel, msg notifications.Message) (bool, error)
OpenPageFromDispatch is registered as the notifications package's page opener (see notifications.RegisterPageOpener). It runs inside dispatch for rules targeting an escalation channel: instead of sending anything, it opens (or dedups into) a page; the escalator worker does all notifying.
func OpenTestPage ¶
func OpenTestPage(policyId int, projectId uuid.UUID, channelId int, channelName string) (bool, error)
OpenTestPage opens a real page for the channel test endpoint, exercising the full escalation loop. Reports false when the fire deduped into a previous test page that is still unresolved.
func ParseDefinition ¶
func ParseDefinition(raw []byte) (*models.OncallScheduleDefinition, error)
ParseDefinition parses and validates a schedule definition, assigning ids to layers that lack one. Validation errors are user-facing (422) messages.
func ParseEmailOverride ¶
ParseEmailOverride extracts the optional email override from an email contact-method config; "" means the account email is used.
func PoliciesReferencing ¶
func PoliciesReferencing(tx *sql.Tx, organizationId int, targetType string, targetIds ...int) ([]string, error)
PoliciesReferencing returns the names of the organization's escalation policies that target any of the given ids of a type; it backs the delete guards on schedules and teams.
func RemoveUserFromOrgSchedules ¶
RemoveUserFromOrgSchedules scrubs a removed member from the organization's on-call data: their overrides are deleted and they are dropped from every schedule layer (a layer left with no members is dropped with them, keeping stored definitions valid). Resolution already filters to current org members; this keeps schedules and timelines from showing phantom coverage.
func ResolveAt ¶
func ResolveAt(def *models.OncallScheduleDefinition, tz *time.Location, overrides []*models.OncallOverride, at time.Time) []int
ResolveAt answers "who is on call at t" with the same stacking ResolveRange renders: a later layer replaces the layers under it and an override replaces everything, so at most one person is on call. Returning every covering user instead would page the person an override was meant to relieve, and page one person per layer on a stacked schedule. Empty means nobody is on call.
func ResolvePage ¶
ResolvePage transitions open/acknowledged -> resolved and cancels queued deliveries. Returns false when the page was already resolved.
func ResolveUrgency ¶
ResolveUrgency maps a policy's urgency setting and a message severity to the page urgency. Auto: critical pages are high urgency, everything else low. An empty severity counts as critical, mirroring buildPageMessage.
func SMSPhoneNumber ¶
SMSPhoneNumber extracts the phoneNumber from an sms contact-method config, or "" when missing or malformed.
func StartEscalator ¶
StartEscalator runs the ack-based escalation loop. Each tick is purely transactional: due pages advance a level and their deliveries are enqueued into the notification outbox, which owns sending, retries, and crash recovery. Ack/resolve cancels queued deliveries via outbox.CancelByKey.
Types ¶
type OncallUser ¶
type PolicyDefinition ¶
type PolicyDefinition struct {
SchemaVersion int `json:"schemaVersion"`
Steps []PolicyStep `json:"steps"`
RepeatCount int `json:"repeatCount"`
// Urgency picks which of each responder's notification-rule chains runs:
// ""|"auto" derives from severity, "high"/"low" force it. Optional so
// stored snapshots and old policies keep parsing (schemaVersion stays 1).
Urgency string `json:"urgency,omitempty"`
}
func ParsePolicyDefinition ¶
func ParsePolicyDefinition(raw []byte) (*PolicyDefinition, error)
ParsePolicyDefinition parses without target-existence checks; used for stored snapshots where dangling targets are tolerated at run time.
func ValidatePolicyDefinition ¶
func ValidatePolicyDefinition(tx *sql.Tx, organizationId int, raw []byte) (*PolicyDefinition, error)
ValidatePolicyDefinition parses and fully validates a policy definition for the organization, including target existence. Errors are user-facing 422 messages.
type PolicyStep ¶
type PolicyStep struct {
Targets []StepTarget `json:"targets"`
DelayMinutes int `json:"delayMinutes"`
}
type ProjectOnCall ¶
type ProjectOnCall struct {
Team *models.Team `json:"team"`
Schedules []ScheduleRef `json:"schedules"`
Oncall []OncallUser `json:"oncall"`
}
ProjectOnCall is the ownership seam: the team owning a project and who is on call for it right now.
func CurrentOnCallForProject ¶
CurrentOnCallForProject resolves the owning team's current on-call across all of its schedules (schedule creation order), filtered to current org members. Returns nil when the project has no owning team.
type ScheduleRef ¶
type Shift ¶
type Shift struct {
UserId int `json:"userId"`
LayerId string `json:"layerId"`
Start time.Time `json:"start"`
End time.Time `json:"end"`
IsOverride bool `json:"isOverride"`
}
Shift is one contiguous stretch of a single person being on call. Times are UTC.
func ResolveLayerRange ¶
ResolveLayerRange renders one layer's coverage for [from, to) without stacking or overrides: rotation periods intersected with the layer's restriction windows.
func ResolveRange ¶
func ResolveRange(def *models.OncallScheduleDefinition, tz *time.Location, overrides []*models.OncallOverride, from, to time.Time) []Shift
ResolveRange renders the final schedule for [from, to): per-layer coverage, stacked so that a later layer's coverage replaces earlier layers where they overlap (PagerDuty "higher layer number takes precedence"), with overrides on top of everything.