Dashboards: Preserve schema version in /api (#104213)
--------- Co-authored-by: Stephanie Hingtgen <stephanie.hingtgen@grafana.com>
This commit is contained in:
@@ -340,6 +340,14 @@ func TestIntegrationCreateK8s(t *testing.T) {
|
||||
testCreate(t, []string{featuremgmt.FlagKubernetesClientDashboardsFolders})
|
||||
}
|
||||
|
||||
func TestIntegrationPreserveSchemaVersion(t *testing.T) {
|
||||
if testing.Short() {
|
||||
t.Skip("skipping integration test")
|
||||
}
|
||||
|
||||
testPreserveSchemaVersion(t, []string{featuremgmt.FlagKubernetesClientDashboardsFolders})
|
||||
}
|
||||
|
||||
func testCreate(t *testing.T, featureToggles []string) {
|
||||
// Setup Grafana and its Database
|
||||
dir, path := testinfra.CreateGrafDir(t, testinfra.GrafanaOpts{
|
||||
@@ -499,3 +507,105 @@ func createFolder(t *testing.T, grafanaListedAddr string, title string) *dtos.Fo
|
||||
|
||||
return f
|
||||
}
|
||||
|
||||
func intPtr(n int) *int {
|
||||
return &n
|
||||
}
|
||||
|
||||
func testPreserveSchemaVersion(t *testing.T, featureToggles []string) {
|
||||
dir, path := testinfra.CreateGrafDir(t, testinfra.GrafanaOpts{
|
||||
DisableAnonymous: true,
|
||||
EnableFeatureToggles: featureToggles,
|
||||
})
|
||||
|
||||
grafanaListedAddr, env := testinfra.StartGrafanaEnv(t, dir, path)
|
||||
store, cfg := env.SQLStore, env.Cfg
|
||||
|
||||
createUser(t, store, cfg, user.CreateUserCommand{
|
||||
DefaultOrgRole: string(org.RoleAdmin),
|
||||
Password: "admin",
|
||||
Login: "admin",
|
||||
})
|
||||
|
||||
schemaVersions := []*int{intPtr(1), intPtr(36), intPtr(40), nil}
|
||||
for _, schemaVersion := range schemaVersions {
|
||||
var title string
|
||||
if schemaVersion == nil {
|
||||
title = "save dashboard with no schemaVersion"
|
||||
} else {
|
||||
title = fmt.Sprintf("save dashboard with schemaVersion %d", *schemaVersion)
|
||||
}
|
||||
|
||||
t.Run(title, func(t *testing.T) {
|
||||
// Create dashboard JSON with specified schema version
|
||||
var dashboardJSON string
|
||||
if schemaVersion != nil {
|
||||
dashboardJSON = fmt.Sprintf(`{"title":"Schema Version Test", "schemaVersion": %d}`, *schemaVersion)
|
||||
} else {
|
||||
dashboardJSON = `{"title":"Schema Version Test"}`
|
||||
}
|
||||
|
||||
dashboardData, err := simplejson.NewJson([]byte(dashboardJSON))
|
||||
require.NoError(t, err)
|
||||
|
||||
// Save the dashboard via API
|
||||
buf := &bytes.Buffer{}
|
||||
err = json.NewEncoder(buf).Encode(dashboards.SaveDashboardCommand{
|
||||
Dashboard: dashboardData,
|
||||
})
|
||||
require.NoError(t, err)
|
||||
|
||||
url := fmt.Sprintf("http://admin:admin@%s/api/dashboards/db", grafanaListedAddr)
|
||||
// nolint:gosec
|
||||
resp, err := http.Post(url, "application/json", buf)
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, http.StatusOK, resp.StatusCode)
|
||||
t.Cleanup(func() {
|
||||
err := resp.Body.Close()
|
||||
require.NoError(t, err)
|
||||
})
|
||||
|
||||
// Get dashboard UID from response
|
||||
b, err := io.ReadAll(resp.Body)
|
||||
require.NoError(t, err)
|
||||
var saveResp struct {
|
||||
UID string `json:"uid"`
|
||||
}
|
||||
err = json.Unmarshal(b, &saveResp)
|
||||
require.NoError(t, err)
|
||||
require.NotEmpty(t, saveResp.UID)
|
||||
|
||||
getDashURL := fmt.Sprintf("http://admin:admin@%s/api/dashboards/uid/%s", grafanaListedAddr, saveResp.UID)
|
||||
// nolint:gosec
|
||||
getResp, err := http.Get(getDashURL)
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, http.StatusOK, getResp.StatusCode)
|
||||
t.Cleanup(func() {
|
||||
err := getResp.Body.Close()
|
||||
require.NoError(t, err)
|
||||
})
|
||||
|
||||
// Parse response and check if schema version is preserved
|
||||
dashBody, err := io.ReadAll(getResp.Body)
|
||||
require.NoError(t, err)
|
||||
|
||||
var dashResp struct {
|
||||
Dashboard *simplejson.Json `json:"dashboard"`
|
||||
}
|
||||
err = json.Unmarshal(dashBody, &dashResp)
|
||||
require.NoError(t, err)
|
||||
|
||||
actualSchemaVersion := dashResp.Dashboard.Get("schemaVersion")
|
||||
if schemaVersion != nil {
|
||||
// Check if schemaVersion is preserved (not migrated to latest)
|
||||
actualVersion := actualSchemaVersion.MustInt()
|
||||
require.Equal(t, *schemaVersion, actualVersion,
|
||||
"Dashboard schemaVersion should not be automatically changed when saved through /api/dashboards/db")
|
||||
} else {
|
||||
actualVersion, err := actualSchemaVersion.Int()
|
||||
s, _ := dashResp.Dashboard.EncodePretty()
|
||||
require.Error(t, err, fmt.Sprintf("Dashboard schemaVersion should not be automatically populated when saved through /api/dashboards/db, was %d. %s", actualVersion, string(s)))
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user