package version import ( "sort" ) // Migration maps provide a simple way to store and run versioned 'patch' functions. type Migration map[string]Patch // Down reverts all patches in reverse version order. func (m Migration) Down(after func(*Version)) error { versions, err := m.Versions() if err != nil { return err } for i := len(versions); i > 0; i-- { v := versions[i-1] patch := m[v.Text] if err := patch.Down(); err != nil { return err } if after != nil { after(v) } } return nil } // Match tests versions against a constraint and returns a new migration map of matching versions only. func (m Migration) Match(constraints ...*Constraint) (Migration, error) { l, err := m.Versions() if err != nil { return nil, err } l = l.Match(constraints...) m2 := Migration{} for _, v := range l { m2[v.Text] = m[v.Text] } return m2, nil } // Up executes all patches in version order. func (m Migration) Up(after func(*Version)) error { versions, err := m.Versions() if err != nil { return err } for _, v := range versions { patch := m[v.Text] if err := patch.Up(); err != nil { return err } if after != nil { after(v) } } return nil } // Versions returns a List of all versions in the migration map. func (m Migration) Versions() (List, error) { l := List{} for str := range m { v, err := Parse(str) if err != nil { return nil, err } l = append(l, v) } sort.Stable(l) return l, nil } type Patch struct { Down func() error Up func() error }