Help us shape the future of Go! Take the 2026 Go Developer Survey

schema

package
v0.32.0 Latest Latest
Warning

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

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

Documentation

Overview

Package schema compares complete schemas and evaluates migration rules. Connectors own inspection, locking, DDL, and verification.

Index

Constants

This section is empty.

Variables

View Source
var ErrBlocked = errors.New("schema_blocked")

ErrBlocked identifies drift requiring intervention before another attempt.

Functions

func CheckMessageChange

func CheckMessageChange(resource string, before, after MessageLayout, policy Policy) error

CheckMessageChange permits only changes authorized by policy, preserving the meaning of all previously decoded fields and the raw/object representation.

func CheckMessageLayouts

func CheckMessageLayouts(before, after map[string]MessageLayout) error

CheckMessageLayouts rejects lost resources or incompatible decoder changes between committed epochs. Execution also applies the configured policy.

func CloneMessageLayouts

func CloneMessageLayouts(layouts map[string]MessageLayout) map[string]MessageLayout

CloneMessageLayouts owns both the resource map and its field slices.

func Observe

func Observe(ctx context.Context, side, resource string, policy Policy, diff Diff)

Observe reports only nonempty diffs. The projection cannot mutate the plan.

func Reconcile

func Reconcile(ctx context.Context, target Target, desired rowmodel.Schema, policy Policy) error

Reconcile validates the entire diff before invoking DDL, then verifies it. Additions are passed together so connectors can use one ALTER statement. It never creates, truncates or commits. On error, committed DDL may remain on nontransactional destinations. A retry always inspects the actual table.

func Validate

func Validate(s rowmodel.Schema) error

Validate checks structural identity, not engine-specific type validity or reserved-field permission. Empty/unknown logical types remain representable.

func WithObserver

func WithObserver(ctx context.Context, observer func(string, Detection)) context.Context

WithObserver installs a synchronous diagnostic callback. Observers must be safe for concurrent resource writers. They cannot authorize schema changes.

Types

type BlockError

type BlockError struct {
	Resource string
	Reasons  []string
}

BlockError is actionable drift information, without row values. A block never authorizes acknowledgement, progress advancement, or destructive DDL.

func (*BlockError) Error

func (e *BlockError) Error() string

func (*BlockError) Unwrap

func (e *BlockError) Unwrap() error

type Change

type Change struct {
	Kind          ChangeKind
	Field         string
	Before, After *rowmodel.Field
}

Change owns its before/after values independently of the compared schemas. Renames are deliberately represented as drop/add until stable identities or an explicit mapping provide evidence of a rename.

type ChangeKind

type ChangeKind string

ChangeKind classifies one structural difference.

const (
	AddField          ChangeKind = "add_field"
	DropField         ChangeKind = "drop_field"
	ChangeType        ChangeKind = "type"
	ChangeNullability ChangeKind = "nullability"
	ChangeKey         ChangeKind = "key"
	ChangeOrder       ChangeKind = "order"
	ChangeEngine      ChangeKind = "engine"
	ChangeDestination ChangeKind = "destination"
	ChangeSemantics   ChangeKind = "semantics"
)

Structural change categories. A rename is a drop and an addition.

type Detection

type Detection struct {
	Side    string        `json:"side"`
	Policy  Policy        `json:"policy"`
	Changes []FieldChange `json:"changes"`
}

Detection describes observed drift, not a successful migration. It contains field names and change categories, never source values or native DDL.

type Diff

type Diff struct {
	Changes        []Change
	OldKey, NewKey []string
}

Diff contains all differences and the compared primary keys.

func Compare

func Compare(before, after rowmodel.Schema) (Diff, error)

Compare compares complete models of the same resource. Both inputs must be complete; absence in a sample is not evidence that a field was dropped. Changes are ordered by old fields, then additions by new fields, followed by resource-level changes.

func CompareNamed

func CompareNamed(actual, desired rowmodel.Schema) (Diff, error)

CompareNamed compares tables addressed by column name, ignoring physical order. Both models must already use the connector's canonical physical types.

type FieldChange

type FieldChange struct {
	Kind  ChangeKind `json:"kind"`
	Field string     `json:"field,omitempty"`
}

FieldChange is the diagnostic projection of a structural difference.

type MessageLayout

type MessageLayout struct {
	Raw    bool
	Fields []rowmodel.Field
}

MessageLayout is the accepted payload decoder layout. Transport metadata is source-owned and reconstructed separately. Epoch certificates persist it with progress so missing fields on replay cannot redefine a resource's schema.

func (MessageLayout) Clone

func (m MessageLayout) Clone() MessageLayout

Clone returns an independent decoder layout.

func (MessageLayout) Validate

func (m MessageLayout) Validate() error

Validate accepts the scalar/JSON inference contract used by message sources. Null-only values use JSON, never an assumed string or non-nullable type.

type Policy

type Policy string

Policy selects the set of automatically permitted changes.

const (
	Strict      Policy = "strict"
	NullableAdd Policy = "nullable_add"
)

Supported migration policies.

func (Policy) Check

func (p Policy) Check(resource string, d Diff) error

Check rejects the entire diff if any change is disallowed. A connector must additionally verify that it can safely implement every permitted change. Column order is meaningful here. Name-based sinks may normalize it first.

func (Policy) Validate

func (p Policy) Validate() error

Validate rejects unknown policies, including an unset policy.

type Target

type Target interface {
	Inspect(context.Context) (rowmodel.Schema, error)
	AddNullable(context.Context, []rowmodel.Field) error
}

Target is an existing, protected destination table. The connector owns table creation, type normalization, locks and transaction lifetime. AddNullable must restore protection before returning if DDL releases the destination's locks.

Jump to

Keyboard shortcuts

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