progression

package
v0.4.0 Latest Latest
Warning

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

Go to latest
Published: May 30, 2026 License: MIT Imports: 2 Imported by: 0

Documentation

Overview

Package progression tracks an accumulating scalar (XP, points, score) against a tiered Curve and emits threshold-crossing events when the subject moves into a new tier.

Domain-agnostic; common applications:

  • Game character XP / level systems.
  • User reputation / karma tiers in apps.
  • Loyalty / fee tiers in commerce or finance.
  • Gamified onboarding (% complete → milestone band).

The package ships an in-memory Store; consumers needing durability supply a Postgres or Redis implementation of the same interface.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type Crossed

type Crossed struct {
	Subject  SubjectID
	From, To int
	NewTotal int64
	Reason   string
}

Crossed describes a tier crossing produced by Award. From < To always.

type Curve

type Curve interface {
	LevelFor(total int64) int
	NextThreshold(level int) int64
}

Curve maps a cumulative total to a tier (level / band / rank) and returns the threshold at which the next tier is reached. Implementations must be monotone — LevelFor must never decrease as total grows.

type InMemoryStore

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

InMemoryStore is a concurrent-safe Store backed by a map. For tests and ephemeral use only.

func NewInMemoryStore

func NewInMemoryStore() *InMemoryStore

func (*InMemoryStore) Add

func (s *InMemoryStore) Add(_ context.Context, subject SubjectID, amount int64) (int64, int64, error)

func (*InMemoryStore) Total

func (s *InMemoryStore) Total(_ context.Context, subject SubjectID) (int64, error)

type Linear

type Linear struct {
	Step int64
}

Linear curve: each tier requires `Step` more total than the previous. LevelFor(2*Step) == 2, NextThreshold(2) == 3*Step, etc.

func (Linear) LevelFor

func (l Linear) LevelFor(total int64) int

func (Linear) NextThreshold

func (l Linear) NextThreshold(level int) int64

type Steps

type Steps struct {
	Thresholds []int64
}

Steps curve: explicit cumulative thresholds. Index i represents the minimum cumulative total to be at level i. Element 0 is implicitly 0 (a fresh subject starts at level 0).

func (Steps) LevelFor

func (s Steps) LevelFor(total int64) int

func (Steps) NextThreshold

func (s Steps) NextThreshold(level int) int64

type Store

type Store interface {
	Total(ctx context.Context, subject SubjectID) (int64, error)
	// Add atomically adds amount and returns (before, after).
	Add(ctx context.Context, subject SubjectID, amount int64) (before, after int64, err error)
}

Store persists per-subject cumulative totals.

type SubjectID

type SubjectID string

SubjectID is whatever the consumer treats as the bearer of progress.

type Tracker

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

Tracker combines a Curve and a Store to award amounts and emit threshold-crossing events.

func NewTracker

func NewTracker(curve Curve, store Store) *Tracker

NewTracker constructs a Tracker.

func (*Tracker) Award

func (t *Tracker) Award(ctx context.Context, subject SubjectID, amount int64, reason string) (*Crossed, error)

Award adds amount to subject's total. If the tier increases, returns a Crossed describing the transition; otherwise the Crossed pointer is nil. Reason is opaque metadata the caller passes through to the event.

func (*Tracker) Level

func (t *Tracker) Level(ctx context.Context, subject SubjectID) (int, error)

Level returns the subject's current tier.

func (*Tracker) Total

func (t *Tracker) Total(ctx context.Context, subject SubjectID) (int64, error)

Total returns the subject's current cumulative total.

Jump to

Keyboard shortcuts

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