store/json: move commits backwards compatibility

By the same logic as the previous patch.

This exposed an apparent bug, where we are sorting by the version field
of the blueprint in the change objects, but these were never
(un)marshalled, so would always be set to zero in the past.

Remove the no-op sorting for now, as it never had an effect, and
put a note whether we should instantiate the blueprint in the change
object somehow.

Signed-off-by: Tom Gundersen <teg@jklm.no>
This commit is contained in:
Tom Gundersen 2020-05-12 18:38:19 +02:00
parent 15a0e78c15
commit f8db2e28e1

View file

@ -5,7 +5,6 @@ import (
"sort" "sort"
"time" "time"
"github.com/coreos/go-semver/semver"
"github.com/google/uuid" "github.com/google/uuid"
"github.com/osbuild/osbuild-composer/internal/blueprint" "github.com/osbuild/osbuild-composer/internal/blueprint"
"github.com/osbuild/osbuild-composer/internal/common" "github.com/osbuild/osbuild-composer/internal/common"
@ -70,6 +69,7 @@ type changeV0 struct {
Message string `json:"message"` Message string `json:"message"`
Revision *int `json:"revision"` Revision *int `json:"revision"`
Timestamp string `json:"timestamp"` Timestamp string `json:"timestamp"`
// BUG: We are currently not (un)marshalling the Blueprint field.
} }
type changesV0 map[string]map[string]changeV0 type changesV0 map[string]map[string]changeV0
@ -181,22 +181,12 @@ func newChangesFromV0(changesStruct changesV0) map[string]map[string]blueprint.C
return changes return changes
} }
func newCommitsFromV0(commitsStruct commitsV0) map[string][]string { func newCommitsFromV0(commitsMapStruct commitsV0, changesMapStruct changesV0) map[string][]string {
commits := make(map[string][]string) commitsMap := make(map[string][]string)
for name, changes := range commitsStruct { for name, commitsStruct := range commitsMapStruct {
commits[name] = changes // TODO: deep copy commits := make([]string, 0, len(commitsStruct))
} copy(commits, commitsStruct)
return commits commitsMap[name] = commits
}
func newStoreFromV0(storeStruct storeV0, arch distro.Arch) *Store {
store := Store{
blueprints: newBlueprintsFromV0(storeStruct.Blueprints),
workspace: newWorkspaceFromV0(storeStruct.Workspace),
composes: newComposesFromV0(storeStruct.Composes, arch),
sources: newSourceConfigsFromV0(storeStruct.Sources),
blueprintsChanges: newChangesFromV0(storeStruct.Changes),
blueprintsCommits: newCommitsFromV0(storeStruct.Commits),
} }
// Populate BlueprintsCommits for existing blueprints without commit history // Populate BlueprintsCommits for existing blueprints without commit history
@ -205,41 +195,43 @@ func newStoreFromV0(storeStruct storeV0, arch distro.Arch) *Store {
// This will sort the existing commits by timestamp and version to update // This will sort the existing commits by timestamp and version to update
// the store. BUT since the timestamp resolution is only 1s it is possible // the store. BUT since the timestamp resolution is only 1s it is possible
// that the order may be slightly wrong. // that the order may be slightly wrong.
for name := range store.blueprintsChanges { for name, changes := range changesMapStruct {
if len(store.blueprintsChanges[name]) != len(store.blueprintsCommits[name]) { if _, exists := commitsMap[name]; !exists {
changes := make([]blueprint.Change, 0, len(store.blueprintsChanges[name])) changesSlice := make([]changeV0, 0, len(changes))
for commit := range store.blueprintsChanges[name] { // Copy the change objects from a map to a sortable slice
changes = append(changes, store.blueprintsChanges[name][commit]) for _, change := range changes {
changesSlice = append(changesSlice, change)
} }
// Sort the changes by Timestamp then version, ascending // Sort the changes by Timestamp ascending
sort.Slice(changes, func(i, j int) bool { sort.Slice(changesSlice, func(i, j int) bool {
if changes[i].Timestamp == changes[j].Timestamp { return changesSlice[i].Timestamp <= changesSlice[j].Timestamp
vI, err := semver.NewVersion(changes[i].Blueprint.Version)
if err != nil {
vI = semver.New("0.0.0")
}
vJ, err := semver.NewVersion(changes[j].Blueprint.Version)
if err != nil {
vJ = semver.New("0.0.0")
}
return vI.LessThan(*vJ)
}
return changes[i].Timestamp < changes[j].Timestamp
}) })
// Create a sorted list of commits based on the sorted list of change objects
commits := make([]string, 0, len(changes)) commits := make([]string, 0, len(changes))
for _, c := range changes { for _, c := range changesSlice {
commits = append(commits, c.Commit) commits = append(commits, c.Commit)
} }
store.blueprintsCommits[name] = commits // Assign the commits to the commit map, as an approximation of what we want
commitsMap[name] = commits
} }
} }
return &store return commitsMap
}
func newStoreFromV0(storeStruct storeV0, arch distro.Arch) *Store {
return &Store{
blueprints: newBlueprintsFromV0(storeStruct.Blueprints),
workspace: newWorkspaceFromV0(storeStruct.Workspace),
composes: newComposesFromV0(storeStruct.Composes, arch),
sources: newSourceConfigsFromV0(storeStruct.Sources),
blueprintsChanges: newChangesFromV0(storeStruct.Changes),
blueprintsCommits: newCommitsFromV0(storeStruct.Commits, storeStruct.Changes),
}
} }
func newBlueprintsV0(blueprints map[string]blueprint.Blueprint) blueprintsV0 { func newBlueprintsV0(blueprints map[string]blueprint.Blueprint) blueprintsV0 {