ha

package
v0.42.2 Latest Latest
Warning

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

Go to latest
Published: Apr 17, 2026 License: MIT Imports: 13 Imported by: 0

Documentation

Overview

Package ha registers writer/replica HA for a Base app.

Quasar consensus is leaderless — all nodes are equal validators. SQLite's single-writer constraint is satisfied by deterministic writer-pinning: the lowest-sorted alive NodeID holds the write lock. All others are replicas that 307 mutating requests to the writer.

app := base.New()
ha.Register(app)
app.Start()

Config lives under the BASE_* env namespace. See the base-ha README.

HA is a no-op unless BASE_LOCAL_TARGET or BASE_STATIC_WRITER is set.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Register

func Register(app core.App)

Register wires HA into the given app.

Behavior depends on env:

  • BASE_STATIC_WRITER=http://... → all writes forward to that URL.
  • BASE_LOCAL_TARGET=http://... + BASE_PEERS=a,b → Quasar heartbeat writer-pin; lowest-sorted alive NodeID is the writer.
  • Neither set → plugin is inactive (standalone Base).

The full go-ha CDC pipeline (change-set capture over NATS-compatible JetStream) is provisioned by the base-ha binary at the SQL driver level. This plugin handles the HTTP surface: write-forwarding middleware and the /_ha/heartbeat endpoint.

Types

type Heartbeat added in v0.40.5

type Heartbeat struct {
	NodeID string `json:"node_id"`
	Target string `json:"target"`
}

type QuasarConfig added in v0.40.5

type QuasarConfig struct {
	NodeID            string
	LocalTarget       string   // this node's reachable URL
	Peers             []string // peer base URLs
	HeartbeatInterval time.Duration
	LeaseTimeout      time.Duration
}

type QuasarWriter added in v0.40.5

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

QuasarWriter pins one node as the SQLite writer using Quasar-style deterministic ranking over a heartbeat-based alive set.

Quasar consensus is leaderless — all nodes are equal validators. But SQLite has a single-writer constraint, so we rank alive peers by NodeID and pin the lowest-sorted as the writer. All others are replicas that 307 mutating HTTP to the writer and apply change-sets via async replication.

Transport: HTTP /_ha/heartbeat by default. Compose with plugins/zap for sub-ms ZAP transport (the ZAP plugin provides mDNS discovery + binary messaging for the fast path).

O(peers) memory, O(1) per heartbeat.

func NewQuasarWriter added in v0.40.5

func NewQuasarWriter(cfg QuasarConfig) (*QuasarWriter, error)

func (*QuasarWriter) Close added in v0.40.5

func (w *QuasarWriter) Close()

func (*QuasarWriter) HandleHeartbeat added in v0.40.5

func (w *QuasarWriter) HandleHeartbeat(rw http.ResponseWriter, r *http.Request)

HandleHeartbeat is the HTTP handler for /_ha/heartbeat.

func (*QuasarWriter) Ingest added in v0.40.5

func (w *QuasarWriter) Ingest(h heartbeat)

Ingest processes an incoming heartbeat (from any transport — HTTP or ZAP). Exported so the ZAP plugin can feed heartbeats in from the binary path.

func (*QuasarWriter) IsWriter added in v0.40.5

func (w *QuasarWriter) IsWriter() bool

func (*QuasarWriter) Ready added in v0.40.5

func (w *QuasarWriter) Ready() <-chan struct{}

func (*QuasarWriter) RedirectTarget added in v0.40.5

func (w *QuasarWriter) RedirectTarget() string

func (*QuasarWriter) SelfHeartbeat added in v0.40.5

func (w *QuasarWriter) SelfHeartbeat() Heartbeat

SelfHeartbeat returns this node's identity for external transports.

type StaticWriter added in v0.40.5

type StaticWriter struct{ Target string }

StaticWriter always routes writes to a fixed URL.

func (*StaticWriter) IsWriter added in v0.40.5

func (s *StaticWriter) IsWriter() bool

func (*StaticWriter) RedirectTarget added in v0.40.5

func (s *StaticWriter) RedirectTarget() string

type WriterProvider added in v0.40.5

type WriterProvider interface {
	IsWriter() bool
	RedirectTarget() string
}

WriterProvider abstracts writer-pin strategies.

Jump to

Keyboard shortcuts

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