Skip to content

Commit

Permalink
add attributes to available versions
Browse files Browse the repository at this point in the history
  • Loading branch information
ecordell committed Jan 18, 2023
1 parent 97ef526 commit d57763f
Show file tree
Hide file tree
Showing 9 changed files with 167 additions and 68 deletions.
23 changes: 23 additions & 0 deletions config/crds/authzed.com_spicedbclusters.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -73,11 +73,23 @@ spec:
channel.
items:
properties:
attributes:
description: Attributes is an optional set of descriptors for
the update, which carry additional information like whether
there will be a migration if this version is selected.
items:
type: string
type: array
channel:
description: Channel is the name of the channel this version
is in
type: string
description:
description: Description a human-readable description of the
update.
type: string
name:
description: Name is the identifier for this version
type: string
required:
- channel
Expand Down Expand Up @@ -185,11 +197,22 @@ spec:
description: CurrentVersion is a description of the currently selected
version from the channel, if an update channel is being used.
properties:
attributes:
description: Attributes is an optional set of descriptors for
the update, which carry additional information like whether
there will be a migration if this version is selected.
items:
type: string
type: array
channel:
description: Channel is the name of the channel this version is
in
type: string
description:
description: Description a human-readable description of the update.
type: string
name:
description: Name is the identifier for this version
type: string
required:
- channel
Expand Down
31 changes: 27 additions & 4 deletions pkg/apis/authzed/v1alpha1/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -131,25 +131,48 @@ func (s ClusterStatus) Equals(other ClusterStatus) bool {
s.Migration == other.Migration &&
s.Phase == other.Phase &&
s.CurrentVersion.Equals(other.CurrentVersion) &&
slices.Equal(s.AvailableVersions, other.AvailableVersions) &&
slices.EqualFunc(s.AvailableVersions, other.AvailableVersions, func(a, b SpiceDBVersion) bool {
return a.Equals(&b)
}) &&
slices.Equal(s.Conditions, other.Conditions):
return true
default:
return false
}
}

type SpiceDBVersionAttributes string

var (
SpiceDBVersionAttributesNext SpiceDBVersionAttributes = "next"
SpiceDBVersionAttributesMigration SpiceDBVersionAttributes = "migration"
SpiceDBVersionAttributesIncompatibleDispatch SpiceDBVersionAttributes = "incompatibleDispatch"
SpiceDBVersionAttributesLatest SpiceDBVersionAttributes = "latest"
)

type SpiceDBVersion struct {
Name string `json:"name"`
Channel string `json:"channel"`
// Name is the identifier for this version
Name string `json:"name"`

// Channel is the name of the channel this version is in
Channel string `json:"channel"`

// Attributes is an optional set of descriptors for the update, which
// carry additional information like whether there will be a migration
// if this version is selected.
// +optional
Attributes []SpiceDBVersionAttributes `json:"attributes,omitempty"`

// Description a human-readable description of the update.
// +optional
Description string `json:"description,omitempty"`
}

func (v *SpiceDBVersion) Equals(other *SpiceDBVersion) bool {
if v == other {
return true
}
if v != nil && other != nil && v.Name == other.Name && v.Channel == other.Channel {
if v != nil && other != nil && v.Name == other.Name && v.Channel == other.Channel && slices.Equal(v.Attributes, other.Attributes) {
return true
}
return false
Expand Down
11 changes: 9 additions & 2 deletions pkg/apis/authzed/v1alpha1/zz_generated.deepcopy.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions pkg/controller/validate_config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,8 @@ func TestValidateConfigHandler(t *testing.T) {
currentStatus: &v1alpha1.SpiceDBCluster{Status: v1alpha1.ClusterStatus{
Image: "image:v1",
Migration: "head",
TargetMigrationHash: "ndchdch68dh69h566h56fhb9h5dq",
CurrentMigrationHash: "ndchdch68dh69h566h56fhb9h5dq",
TargetMigrationHash: "n549hbh555h557h65ch64chc8h6dq",
CurrentMigrationHash: "n549hbh555h557h65ch64chc8h6dq",
CurrentVersion: &v1alpha1.SpiceDBVersion{
Name: "v1",
Channel: "cockroachdb",
Expand Down
23 changes: 23 additions & 0 deletions pkg/crds/authzed.com_spicedbclusters.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -73,11 +73,23 @@ spec:
channel.
items:
properties:
attributes:
description: Attributes is an optional set of descriptors for
the update, which carry additional information like whether
there will be a migration if this version is selected.
items:
type: string
type: array
channel:
description: Channel is the name of the channel this version
is in
type: string
description:
description: Description a human-readable description of the
update.
type: string
name:
description: Name is the identifier for this version
type: string
required:
- channel
Expand Down Expand Up @@ -185,11 +197,22 @@ spec:
description: CurrentVersion is a description of the currently selected
version from the channel, if an update channel is being used.
properties:
attributes:
description: Attributes is an optional set of descriptors for
the update, which carry additional information like whether
there will be a migration if this version is selected.
items:
type: string
type: array
channel:
description: Channel is the name of the channel this version is
in
type: string
description:
description: Description a human-readable description of the update.
type: string
name:
description: Name is the identifier for this version
type: string
required:
- channel
Expand Down
24 changes: 16 additions & 8 deletions pkg/updates/file.go
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ func (g *UpdateGraph) Copy() UpdateGraph {
}

// AvailableVersions traverses an UpdateGraph and collects a list of the
// safe versions for updating from the provided version.
// safe versions for updating from the provided currentVersion.
func (g *UpdateGraph) AvailableVersions(engine string, v v1alpha1.SpiceDBVersion) ([]v1alpha1.SpiceDBVersion, error) {
source, err := g.SourceForChannel(v.Channel)
if err != nil {
Expand All @@ -82,13 +82,16 @@ func (g *UpdateGraph) AvailableVersions(engine string, v v1alpha1.SpiceDBVersion
nextWithoutMigrations := source.NextVersionWithoutMigrations(v.Name)
latest := source.LatestVersion(v.Name)
if len(nextWithoutMigrations) > 0 {
// TODO: should also account for downtime, i.e. dispatch api changes
nextDirectVersion := v1alpha1.SpiceDBVersion{
Name: nextWithoutMigrations,
Channel: v.Channel,
Attributes: []v1alpha1.SpiceDBVersionAttributes{v1alpha1.SpiceDBVersionAttributesNext},
Description: "direct update with no migrations",
}
if nextWithoutMigrations == latest {
nextDirectVersion.Description += ", head of channel"
nextDirectVersion.Attributes = append(nextDirectVersion.Attributes, v1alpha1.SpiceDBVersionAttributesLatest)
}
availableVersions = append(availableVersions, nextDirectVersion)
}
Expand All @@ -98,17 +101,20 @@ func (g *UpdateGraph) AvailableVersions(engine string, v v1alpha1.SpiceDBVersion
nextVersion := v1alpha1.SpiceDBVersion{
Name: next,
Channel: v.Channel,
Attributes: []v1alpha1.SpiceDBVersionAttributes{v1alpha1.SpiceDBVersionAttributesNext, v1alpha1.SpiceDBVersionAttributesMigration},
Description: "update will run a migration",
}
if next == latest {
nextVersion.Description += ", head of channel"
nextVersion.Attributes = append(nextVersion.Attributes, v1alpha1.SpiceDBVersionAttributesLatest)
}
availableVersions = append(availableVersions, nextVersion)
}
if len(latest) > 0 && next != latest && nextWithoutMigrations != latest {
availableVersions = append(availableVersions, v1alpha1.SpiceDBVersion{
Name: latest,
Channel: v.Channel,
Attributes: []v1alpha1.SpiceDBVersionAttributes{v1alpha1.SpiceDBVersionAttributesLatest, v1alpha1.SpiceDBVersionAttributesMigration},
Description: "head of the channel, multiple updates will run in sequence",
})
}
Expand All @@ -130,6 +136,7 @@ func (g *UpdateGraph) AvailableVersions(engine string, v v1alpha1.SpiceDBVersion
availableVersions = append(availableVersions, v1alpha1.SpiceDBVersion{
Name: next,
Channel: c.Name,
Attributes: []v1alpha1.SpiceDBVersionAttributes{v1alpha1.SpiceDBVersionAttributesNext},
Description: "direct update with no migrations, different channel",
})
continue
Expand All @@ -138,6 +145,7 @@ func (g *UpdateGraph) AvailableVersions(engine string, v v1alpha1.SpiceDBVersion
availableVersions = append(availableVersions, v1alpha1.SpiceDBVersion{
Name: next,
Channel: c.Name,
Attributes: []v1alpha1.SpiceDBVersionAttributes{v1alpha1.SpiceDBVersionAttributesNext, v1alpha1.SpiceDBVersionAttributesMigration},
Description: "update will run a migration, different channel",
})
}
Expand All @@ -158,7 +166,7 @@ func explodeImage(image string) (baseImage, tag, digest string) {
return
}

// ComputeTarget determines the target update version and state given an update
// ComputeTarget determines the target update currentVersion and state given an update
// graph and the proper context.
func (g *UpdateGraph) ComputeTarget(defaultBaseImage, image, version, channel, engine string, currentVersion *v1alpha1.SpiceDBVersion, rolling bool) (baseImage string, target *v1alpha1.SpiceDBVersion, state State, err error) {
baseImage, tag, digest := explodeImage(image)
Expand All @@ -176,7 +184,7 @@ func (g *UpdateGraph) ComputeTarget(defaultBaseImage, image, version, channel, e
return
}

// Fallback to the channel from the current version.
// Fallback to the channel from the current currentVersion.
if channel == "" && currentVersion != nil {
channel = currentVersion.Channel
}
Expand All @@ -199,7 +207,7 @@ func (g *UpdateGraph) ComputeTarget(defaultBaseImage, image, version, channel, e
}
}

// Default to the version we're working toward.
// Default to the currentVersion we're working toward.
target = currentVersion

var currentState State
Expand All @@ -221,8 +229,8 @@ func (g *UpdateGraph) ComputeTarget(defaultBaseImage, image, version, channel, e
return
}

// If version is set, we only use the subset of the update graph that leads
// to that version.
// If currentVersion is set, we only use the subset of the update graph that leads
// to that currentVersion.
if len(version) > 0 {
updateSource, err = updateSource.Subgraph(version)
if err != nil {
Expand All @@ -235,13 +243,13 @@ func (g *UpdateGraph) ComputeTarget(defaultBaseImage, image, version, channel, e
if currentVersion != nil && len(currentVersion.Name) > 0 {
targetVersion = updateSource.NextVersion(currentVersion.Name)
if len(targetVersion) == 0 {
// There's no next version, so use the current state.
// There's no next currentVersion, so use the current state.
state = currentState
target = currentVersion
return
}
} else {
// There's no current version, so install head.
// There's no current currentVersion, so install head.
// TODO(jzelinskie): find a way to make this less "magical"
targetVersion = updateSource.LatestVersion("")
}
Expand Down
Loading

0 comments on commit d57763f

Please sign in to comment.