cost

package
v0.4.12 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Oct 20, 2026 License: Apache-2.0 Imports: 14 Imported by: 0

Documentation

Index

Constants

View Source
const (
	DefaultTopSessions = 10
	MaxTopSessions     = 500
)

Limits for the session list of a cost breakdown.

View Source
const (
	AlertTypeIdleSession    = "idle_session"
	AlertTypeBudgetWarning  = "budget_warning"
	AlertTypeBudgetExceeded = "budget_exceeded"
	AlertTypeOptimization   = "optimization"
	AlertTypeStorageGrowth  = "storage_growth"
)

Alert types

View Source
const (
	SeverityInfo     = "info"
	SeverityWarning  = "warning"
	SeverityCritical = "critical"
)

Severity levels

View Source
const MaxMonthlyLimit = 99_999_999.99

MaxMonthlyLimit is the largest budget the schema can store: monthly_limit is DECIMAL(10,2), so a larger value would fail the insert with a numeric overflow rather than a useful validation error.

View Source
const MinAccrualSpan = 5 * time.Minute

MinAccrualSpan is how much running time must have built up before a still running session is billed. Cost metrics are immutable rows, so billing every sweep would write one row per session per minute and cost values would round to zero at the column's four decimals. A session that has stopped is always billed for its remainder, whatever its length.

Variables

View Source
var ErrAlertNotFound = errors.New("cost alert not found")

ErrAlertNotFound is returned when an alert does not exist, or exists but is not visible to the caller. The two cases are deliberately indistinguishable.

View Source
var ErrInvalidBudget = errors.New("invalid budget")

ErrInvalidBudget is returned when budget input fails validation.

Functions

This section is empty.

Types

type BudgetOpts added in v0.3.2

type BudgetOpts struct {
	MonthlyLimit   float64
	AlertThreshold float64
	Month          string // YYYY-MM
}

BudgetOpts describes a monthly spending limit for an org.

type CostAlert

type CostAlert struct {
	ID               uuid.UUID  `db:"id" json:"id"`
	AlertType        string     `db:"alert_type" json:"alert_type"`
	Severity         string     `db:"severity" json:"severity"`
	SessionID        *uuid.UUID `db:"session_id" json:"session_id,omitempty"`
	OrgID            *uuid.UUID `db:"org_id" json:"org_id,omitempty"`
	Title            string     `db:"title" json:"title"`
	Description      string     `db:"description" json:"description"`
	PotentialSavings *float64   `db:"potential_savings" json:"potential_savings,omitempty"`
	Resolved         bool       `db:"resolved" json:"resolved"`
	ResolvedAt       *time.Time `db:"resolved_at" json:"resolved_at,omitempty"`
	ResolvedBy       *string    `db:"resolved_by" json:"resolved_by,omitempty"`
	CreatedAt        time.Time  `db:"created_at" json:"created_at"`
	UpdatedAt        time.Time  `db:"updated_at" json:"updated_at"`
}

CostAlert notifies about cost issues (idle sessions, budget warnings, etc.)

type CostBreakdown

type CostBreakdown struct {
	Period      string               `db:"-" json:"period"` // YYYY-MM or YYYY-MM-DD
	ComputeCost float64              `db:"compute_cost" json:"compute_cost"`
	StorageCost float64              `db:"storage_cost" json:"storage_cost"`
	NetworkCost float64              `db:"network_cost" json:"network_cost"`
	TotalCost   float64              `db:"total_cost"   json:"total_cost"`
	TopSessions []SessionCostSummary `db:"-" json:"top_sessions"`
	// TotalSessions counts every session with a cost in the period, also those
	// beyond the limit applied to TopSessions.
	TotalSessions int `db:"-" json:"total_sessions"`
	AlertCount    int `db:"-" json:"alert_count"`
}

CostBreakdown provides detailed cost analysis.

The cost fields carry db tags because the totals are scanned straight into this struct; without them sqlx maps `compute_cost` to no field and the whole query fails with "missing destination name". Period, TopSessions and AlertCount are filled in separately and are explicitly ignored by the mapper.

type CostBudget

type CostBudget struct {
	ID             uuid.UUID  `db:"id" json:"id"`
	OrgID          uuid.UUID  `db:"org_id" json:"org_id"`
	MonthlyLimit   float64    `db:"monthly_limit" json:"monthly_limit"`
	AlertThreshold float64    `db:"alert_threshold" json:"alert_threshold"`
	CurrentMonth   string     `db:"current_month" json:"current_month"`
	CurrentSpend   float64    `db:"current_spend" json:"current_spend"`
	AlertSent      bool       `db:"alert_sent" json:"alert_sent"`
	ExceededAt     *time.Time `db:"exceeded_at" json:"exceeded_at,omitempty"`
	CreatedAt      time.Time  `db:"created_at" json:"created_at"`
	UpdatedAt      time.Time  `db:"updated_at" json:"updated_at"`
}

CostBudget defines spending limits for an organization

type CostMetric

type CostMetric struct {
	ID              uuid.UUID  `db:"id" json:"id"`
	SessionID       uuid.UUID  `db:"session_id" json:"session_id"`
	PeriodStart     time.Time  `db:"period_start" json:"period_start"`
	PeriodEnd       time.Time  `db:"period_end" json:"period_end"`
	CPUCoreHours    float64    `db:"cpu_core_hours" json:"cpu_core_hours"`
	MemoryGBHours   float64    `db:"memory_gb_hours" json:"memory_gb_hours"`
	GPUHours        float64    `db:"gpu_hours" json:"gpu_hours"`
	WorkspaceGBDays float64    `db:"workspace_gb_days" json:"workspace_gb_days"`
	SnapshotGBDays  float64    `db:"snapshot_gb_days" json:"snapshot_gb_days"`
	ArtifactGBDays  float64    `db:"artifact_gb_days" json:"artifact_gb_days"`
	EgressGB        float64    `db:"egress_gb" json:"egress_gb"`
	IngressGB       float64    `db:"ingress_gb" json:"ingress_gb"`
	ComputeCost     float64    `db:"compute_cost" json:"compute_cost"`
	StorageCost     float64    `db:"storage_cost" json:"storage_cost"`
	NetworkCost     float64    `db:"network_cost" json:"network_cost"`
	TotalCost       float64    `db:"total_cost" json:"total_cost"`
	RateID          *uuid.UUID `db:"rate_id" json:"rate_id,omitempty"`
	Checksum        string     `db:"checksum" json:"checksum"`
	Signature       string     `db:"signature" json:"signature"`
	CreatedAt       time.Time  `db:"created_at" json:"created_at"`
}

CostMetric records resource usage and costs for a session over a time period

type CostRate

type CostRate struct {
	ID                  uuid.UUID `db:"id" json:"id"`
	Name                string    `db:"name" json:"name"`
	CPUCoreHourRate     float64   `db:"cpu_core_hour_rate" json:"cpu_core_hour_rate"`
	MemoryGBHourRate    float64   `db:"memory_gb_hour_rate" json:"memory_gb_hour_rate"`
	GPUHourRate         float64   `db:"gpu_hour_rate" json:"gpu_hour_rate"`
	StorageGBMonthRate  float64   `db:"storage_gb_month_rate" json:"storage_gb_month_rate"`
	SnapshotGBMonthRate float64   `db:"snapshot_gb_month_rate" json:"snapshot_gb_month_rate"`
	ArtifactGBMonthRate float64   `db:"artifact_gb_month_rate" json:"artifact_gb_month_rate"`
	EgressGBRate        float64   `db:"egress_gb_rate" json:"egress_gb_rate"`
	Active              bool      `db:"active" json:"active"`
	CreatedAt           time.Time `db:"created_at" json:"created_at"`
	UpdatedAt           time.Time `db:"updated_at" json:"updated_at"`
}

CostRate defines pricing for compute, storage, and network resources

type OrgCostSummary

type OrgCostSummary struct {
	OrgID        uuid.UUID `db:"org_id"        json:"org_id"`
	OrgName      string    `db:"org_name"      json:"org_name"`
	ComputeCost  float64   `db:"compute_cost"  json:"compute_cost"`
	StorageCost  float64   `db:"storage_cost"  json:"storage_cost"`
	NetworkCost  float64   `db:"network_cost"  json:"network_cost"`
	TotalCost    float64   `db:"total_cost"    json:"total_cost"`
	SessionCount int       `db:"session_count" json:"session_count"`
}

OrgCostSummary aggregates all costs for an organization

type Scope added in v0.3.2

type Scope struct {
	// Master grants the deployment-wide view.
	Master bool
	// Actor is the API key principal whose sessions and orgs are visible.
	Actor string
}

Scope restricts a cost query to the data one caller is allowed to see.

Spend figures are business-sensitive: a deployment-wide total, and the names of the ten sessions that spent the most, tell any tenant how busy every other tenant is. Every aggregate query therefore takes a Scope, and only the master key gets the unrestricted view.

func ActorScope added in v0.3.2

func ActorScope(actor string) Scope

ActorScope returns the scope visible to one API key principal.

func DeploymentScope added in v0.3.2

func DeploymentScope() Scope

DeploymentScope returns the unrestricted scope used by the master key and by internal callers such as the cost sweeper.

type SessionCostSummary

type SessionCostSummary struct {
	SessionID   uuid.UUID `db:"session_id"   json:"session_id"`
	SessionName string    `db:"session_name" json:"session_name"`
	ComputeCost float64   `db:"compute_cost" json:"compute_cost"`
	StorageCost float64   `db:"storage_cost" json:"storage_cost"`
	NetworkCost float64   `db:"network_cost" json:"network_cost"`
	TotalCost   float64   `db:"total_cost"   json:"total_cost"`
	// StoppedAt is set when the session has ended (deleted, or stopped when idle).
	StoppedAt   *time.Time `db:"stopped_at"   json:"stopped_at,omitempty"`
	FirstMetric *time.Time `db:"first_metric" json:"first_metric,omitempty"`
	LastMetric  *time.Time `db:"last_metric"  json:"last_metric,omitempty"`
}

SessionCostSummary aggregates all costs for a session FirstMetric and LastMetric are pointers because the query left-joins cost_metrics: a session that has not been billed yet has no metrics, and MIN/MAX over zero rows returns NULL.

type Tracker

type Tracker struct {
	// contains filtered or unexported fields
}

Tracker collects and calculates cost metrics for sessions

func New

func New(db *sqlx.DB, signingKey []byte) *Tracker

New creates a new cost Tracker

func (*Tracker) AccrueUsage added in v0.4.4

func (t *Tracker) AccrueUsage(ctx context.Context, now time.Time) (int, error)

AccrueUsage bills every session for the time that has passed since it was last billed, and returns how many metrics were recorded. It is safe to call repeatedly and from several API instances: a period that was already billed is skipped.

func (*Tracker) CreateAlert

func (t *Tracker) CreateAlert(ctx context.Context, alert *CostAlert) error

CreateAlert creates a cost alert

func (*Tracker) GetAlerts

func (t *Tracker) GetAlerts(ctx context.Context, resolved bool, scope Scope) ([]CostAlert, error)

GetAlerts returns active cost alerts the scope may see.

func (*Tracker) GetBudget added in v0.3.2

func (t *Tracker) GetBudget(ctx context.Context, orgID uuid.UUID, month string) (*CostBudget, error)

GetBudget returns the budget for an org and month, or nil when none is set.

func (*Tracker) GetCostBreakdown

func (t *Tracker) GetCostBreakdown(ctx context.Context, period string, scope Scope, topSessions int) (*CostBreakdown, error)

GetCostBreakdown returns cost breakdown for a period, restricted to the sessions and alerts the scope may see. topSessions caps the session list (DefaultTopSessions when zero or negative, MaxTopSessions at most); TotalSessions tells how many sessions there are beyond the cap.

func (*Tracker) GetOrgSummary

func (t *Tracker) GetOrgSummary(ctx context.Context, orgID uuid.UUID, month string) (*OrgCostSummary, error)

GetOrgSummary returns aggregated cost summary for an organization

func (*Tracker) GetSessionCosts

func (t *Tracker) GetSessionCosts(ctx context.Context, sessionID uuid.UUID) ([]CostMetric, error)

GetSessionCosts returns all cost metrics for a session

func (*Tracker) GetSessionSummary

func (t *Tracker) GetSessionSummary(ctx context.Context, sessionID uuid.UUID) (*SessionCostSummary, error)

GetSessionSummary returns aggregated cost summary for a session

func (*Tracker) RecordMetric

func (t *Tracker) RecordMetric(ctx context.Context, metric *CostMetric) error

RecordMetric records a cost metric for a session

func (*Tracker) ResolveAlert

func (t *Tracker) ResolveAlert(ctx context.Context, alertID uuid.UUID, resolvedBy string, scope Scope) error

ResolveAlert marks an alert as resolved.

The scope is part of the WHERE clause rather than a separate lookup: a caller must not be able to resolve — and so hide — an alert raised against another tenant's session. Returns ErrAlertNotFound when no visible alert matches, which also covers a wholly unknown ID.

func (*Tracker) SetBudget added in v0.3.2

func (t *Tracker) SetBudget(ctx context.Context, orgID uuid.UUID, opts BudgetOpts) error

SetBudget creates or replaces the budget for an org and month.

func (*Tracker) StartAccrual added in v0.4.4

func (t *Tracker) StartAccrual(ctx context.Context, interval time.Duration)

StartAccrual bills sessions every interval until ctx is cancelled.

func (*Tracker) VerifyMetric added in v0.3.1

func (t *Tracker) VerifyMetric(m *CostMetric) bool

VerifyMetric reports whether a metric's stored checksum and signature match its contents. Returns false when signing is not configured so that an unkeyed deployment cannot treat every metric as authentic.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL