fix(http): convert dashboard errors
parent
f32b6f2fea
commit
6ca7c68e2e
|
|
@ -3,7 +3,6 @@ package bolt
|
|||
import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
|
|
@ -51,26 +50,37 @@ func (c *Client) FindDashboardByID(ctx context.Context, id platform.ID) (*platfo
|
|||
})
|
||||
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Op: getOp(platform.OpFindDashboardByID),
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
|
||||
return d, nil
|
||||
}
|
||||
|
||||
func (c *Client) findDashboardByID(ctx context.Context, tx *bolt.Tx, id platform.ID) (*platform.Dashboard, error) {
|
||||
func (c *Client) findDashboardByID(ctx context.Context, tx *bolt.Tx, id platform.ID) (*platform.Dashboard, *platform.Error) {
|
||||
encodedID, err := id.Encode()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
|
||||
v := tx.Bucket(dashboardBucket).Get(encodedID)
|
||||
if len(v) == 0 {
|
||||
return nil, platform.ErrDashboardNotFound
|
||||
return nil, &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
var d platform.Dashboard
|
||||
if err := json.Unmarshal(v, &d); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
|
||||
return &d, nil
|
||||
|
|
@ -99,7 +109,10 @@ func (c *Client) FindDashboard(ctx context.Context, filter platform.DashboardFil
|
|||
}
|
||||
|
||||
if d == nil {
|
||||
return nil, platform.ErrDashboardNotFound
|
||||
return nil, &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
}
|
||||
}
|
||||
|
||||
return d, nil
|
||||
|
|
@ -122,19 +135,23 @@ func filterDashboardsFn(filter platform.DashboardFilter) func(d *platform.Dashbo
|
|||
|
||||
// FindDashboards retrives all dashboards that match an arbitrary dashboard filter.
|
||||
func (c *Client) FindDashboards(ctx context.Context, filter platform.DashboardFilter, opts platform.FindOptions) ([]*platform.Dashboard, int, error) {
|
||||
ds := []*platform.Dashboard{}
|
||||
if len(filter.IDs) == 1 {
|
||||
d, err := c.FindDashboardByID(ctx, *filter.IDs[0])
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
if err != nil && platform.ErrorCode(err) != platform.ENotFound {
|
||||
return ds, 0, &platform.Error{
|
||||
Err: err,
|
||||
Op: getOp(platform.OpFindDashboardByID),
|
||||
}
|
||||
}
|
||||
if d == nil {
|
||||
return ds, 0, nil
|
||||
}
|
||||
|
||||
return []*platform.Dashboard{d}, 1, nil
|
||||
}
|
||||
|
||||
ds := []*platform.Dashboard{}
|
||||
err := c.db.View(func(tx *bolt.Tx) error {
|
||||
dashs, err := c.findDashboards(ctx, tx, filter)
|
||||
if err != nil {
|
||||
if err != nil && platform.ErrorCode(err) != platform.ENotFound {
|
||||
return err
|
||||
}
|
||||
ds = dashs
|
||||
|
|
@ -142,7 +159,10 @@ func (c *Client) FindDashboards(ctx context.Context, filter platform.DashboardFi
|
|||
})
|
||||
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
return nil, 0, &platform.Error{
|
||||
Err: err,
|
||||
Op: getOp(platform.OpFindDashboards),
|
||||
}
|
||||
}
|
||||
|
||||
platform.SortDashboards(opts.SortBy, ds)
|
||||
|
|
@ -170,7 +190,7 @@ func (c *Client) findDashboards(ctx context.Context, tx *bolt.Tx, filter platfor
|
|||
|
||||
// CreateDashboard creates a platform dashboard and sets d.ID.
|
||||
func (c *Client) CreateDashboard(ctx context.Context, d *platform.Dashboard) error {
|
||||
return c.db.Update(func(tx *bolt.Tx) error {
|
||||
err := c.db.Update(func(tx *bolt.Tx) error {
|
||||
d.ID = c.IDGenerator.ID()
|
||||
|
||||
for _, cell := range d.Cells {
|
||||
|
|
@ -190,6 +210,13 @@ func (c *Client) CreateDashboard(ctx context.Context, d *platform.Dashboard) err
|
|||
|
||||
return c.putDashboardWithMeta(ctx, tx, d)
|
||||
})
|
||||
if err != nil {
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: getOp(platform.OpCreateDashboard),
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (c *Client) createViewIfNotExists(ctx context.Context, tx *bolt.Tx, cell *platform.Cell, opts platform.AddDashboardCellOptions) error {
|
||||
|
|
@ -226,7 +253,7 @@ func (c *Client) createViewIfNotExists(ctx context.Context, tx *bolt.Tx, cell *p
|
|||
|
||||
// ReplaceDashboardCells updates the positions of each cell in a dashboard concurrently.
|
||||
func (c *Client) ReplaceDashboardCells(ctx context.Context, id platform.ID, cs []*platform.Cell) error {
|
||||
return c.db.Update(func(tx *bolt.Tx) error {
|
||||
err := c.db.Update(func(tx *bolt.Tx) error {
|
||||
d, err := c.findDashboardByID(ctx, tx, id)
|
||||
if err != nil {
|
||||
return err
|
||||
|
|
@ -239,16 +266,25 @@ func (c *Client) ReplaceDashboardCells(ctx context.Context, id platform.ID, cs [
|
|||
|
||||
for _, cell := range cs {
|
||||
if !cell.ID.Valid() {
|
||||
return fmt.Errorf("cannot provide empty cell id")
|
||||
return &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Msg: "cannot provide empty cell id",
|
||||
}
|
||||
}
|
||||
|
||||
cl, ok := ids[cell.ID.String()]
|
||||
if !ok {
|
||||
return fmt.Errorf("cannot replace cells that were not already present")
|
||||
return &platform.Error{
|
||||
Code: platform.EConflict,
|
||||
Msg: "cannot replace cells that were not already present",
|
||||
}
|
||||
}
|
||||
|
||||
if cl.ViewID != cell.ViewID {
|
||||
return fmt.Errorf("cannot update view id in replace")
|
||||
return &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Msg: "cannot update view id in replace",
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -259,11 +295,18 @@ func (c *Client) ReplaceDashboardCells(ctx context.Context, id platform.ID, cs [
|
|||
|
||||
return c.putDashboardWithMeta(ctx, tx, d)
|
||||
})
|
||||
if err != nil {
|
||||
return &platform.Error{
|
||||
Op: getOp(platform.OpReplaceDashboardCells),
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// AddDashboardCell adds a cell to a dashboard and sets the cells ID.
|
||||
func (c *Client) AddDashboardCell(ctx context.Context, id platform.ID, cell *platform.Cell, opts platform.AddDashboardCellOptions) error {
|
||||
return c.db.Update(func(tx *bolt.Tx) error {
|
||||
err := c.db.Update(func(tx *bolt.Tx) error {
|
||||
d, err := c.findDashboardByID(ctx, tx, id)
|
||||
if err != nil {
|
||||
return err
|
||||
|
|
@ -281,14 +324,25 @@ func (c *Client) AddDashboardCell(ctx context.Context, id platform.ID, cell *pla
|
|||
|
||||
return c.putDashboardWithMeta(ctx, tx, d)
|
||||
})
|
||||
if err != nil {
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: getOp(platform.OpAddDashboardCell),
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// RemoveDashboardCell removes a cell from a dashboard.
|
||||
func (c *Client) RemoveDashboardCell(ctx context.Context, dashboardID, cellID platform.ID) error {
|
||||
op := getOp(platform.OpRemoveDashboardCell)
|
||||
return c.db.Update(func(tx *bolt.Tx) error {
|
||||
d, err := c.findDashboardByID(ctx, tx, dashboardID)
|
||||
if err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
idx := -1
|
||||
|
|
@ -299,27 +353,47 @@ func (c *Client) RemoveDashboardCell(ctx context.Context, dashboardID, cellID pl
|
|||
}
|
||||
}
|
||||
if idx == -1 {
|
||||
return platform.ErrCellNotFound
|
||||
return &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Op: op,
|
||||
Msg: platform.ErrCellNotFound,
|
||||
}
|
||||
}
|
||||
|
||||
if err := c.deleteView(ctx, tx, d.Cells[idx].ViewID); err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
d.Cells = append(d.Cells[:idx], d.Cells[idx+1:]...)
|
||||
|
||||
if err := c.appendDashboardEventToLog(ctx, tx, d.ID, dashboardCellRemovedEvent); err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
return c.putDashboardWithMeta(ctx, tx, d)
|
||||
if err := c.putDashboardWithMeta(ctx, tx, d); err != nil {
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
return nil
|
||||
})
|
||||
}
|
||||
|
||||
// UpdateDashboardCell udpates a cell on a dashboard.
|
||||
func (c *Client) UpdateDashboardCell(ctx context.Context, dashboardID, cellID platform.ID, upd platform.CellUpdate) (*platform.Cell, error) {
|
||||
op := getOp(platform.OpUpdateDashboardCell)
|
||||
if err := upd.Valid(); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
var cell *platform.Cell
|
||||
|
|
@ -337,7 +411,11 @@ func (c *Client) UpdateDashboardCell(ctx context.Context, dashboardID, cellID pl
|
|||
}
|
||||
}
|
||||
if idx == -1 {
|
||||
return platform.ErrCellNotFound
|
||||
return &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Op: op,
|
||||
Msg: platform.ErrCellNotFound,
|
||||
}
|
||||
}
|
||||
|
||||
if err := upd.Apply(d.Cells[idx]); err != nil {
|
||||
|
|
@ -354,7 +432,10 @@ func (c *Client) UpdateDashboardCell(ctx context.Context, dashboardID, cellID pl
|
|||
})
|
||||
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
return cell, nil
|
||||
|
|
@ -420,6 +501,12 @@ func (c *Client) UpdateDashboard(ctx context.Context, id platform.ID, upd platfo
|
|||
|
||||
return nil
|
||||
})
|
||||
if err != nil {
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: getOp(platform.OpUpdateDashboard),
|
||||
}
|
||||
}
|
||||
|
||||
return d, err
|
||||
}
|
||||
|
|
@ -448,38 +535,58 @@ func (c *Client) updateDashboard(ctx context.Context, tx *bolt.Tx, id platform.I
|
|||
// DeleteDashboard deletes a dashboard and prunes it from the index.
|
||||
func (c *Client) DeleteDashboard(ctx context.Context, id platform.ID) error {
|
||||
return c.db.Update(func(tx *bolt.Tx) error {
|
||||
return c.deleteDashboard(ctx, tx, id)
|
||||
if pe := c.deleteDashboard(ctx, tx, id); pe != nil {
|
||||
return &platform.Error{
|
||||
Err: pe,
|
||||
Op: getOp(platform.OpDeleteDashboard),
|
||||
}
|
||||
}
|
||||
return nil
|
||||
})
|
||||
}
|
||||
|
||||
func (c *Client) deleteDashboard(ctx context.Context, tx *bolt.Tx, id platform.ID) error {
|
||||
d, err := c.findDashboardByID(ctx, tx, id)
|
||||
if err != nil {
|
||||
return err
|
||||
func (c *Client) deleteDashboard(ctx context.Context, tx *bolt.Tx, id platform.ID) *platform.Error {
|
||||
d, pe := c.findDashboardByID(ctx, tx, id)
|
||||
if pe != nil {
|
||||
return pe
|
||||
}
|
||||
for _, cell := range d.Cells {
|
||||
if err := c.deleteView(ctx, tx, cell.ViewID); err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
}
|
||||
encodedID, err := id.Encode()
|
||||
if err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
if err := tx.Bucket(dashboardBucket).Delete(encodedID); err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
|
||||
err = c.deleteLabels(ctx, tx, platform.LabelFilter{ResourceID: id})
|
||||
if err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
|
||||
// TODO(desa): add DeleteKeyValueLog method and use it here.
|
||||
return c.deleteUserResourceMappings(ctx, tx, platform.UserResourceMappingFilter{
|
||||
err = c.deleteUserResourceMappings(ctx, tx, platform.UserResourceMappingFilter{
|
||||
ResourceID: id,
|
||||
ResourceType: platform.DashboardResourceType,
|
||||
})
|
||||
if err != nil {
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
const dashboardOperationLogKeyPrefix = "dashboard"
|
||||
|
|
|
|||
|
|
@ -5,10 +5,11 @@ import (
|
|||
"testing"
|
||||
|
||||
"github.com/influxdata/platform"
|
||||
"github.com/influxdata/platform/bolt"
|
||||
platformtesting "github.com/influxdata/platform/testing"
|
||||
)
|
||||
|
||||
func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (platform.DashboardService, func()) {
|
||||
func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (platform.DashboardService, string, func()) {
|
||||
c, closeFn, err := NewTestClient()
|
||||
if err != nil {
|
||||
t.Fatalf("failed to create new bolt client: %v", err)
|
||||
|
|
@ -26,7 +27,7 @@ func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (plat
|
|||
t.Fatalf("failed to populate views")
|
||||
}
|
||||
}
|
||||
return c, func() {
|
||||
return c, bolt.OpPrefix, func() {
|
||||
defer closeFn()
|
||||
for _, b := range f.Dashboards {
|
||||
if err := c.DeleteDashboard(ctx, b.ID); err != nil {
|
||||
|
|
@ -41,38 +42,6 @@ func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (plat
|
|||
}
|
||||
}
|
||||
|
||||
func TestDashboardService_CreateDashboard(t *testing.T) {
|
||||
platformtesting.CreateDashboard(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_FindDashboardByID(t *testing.T) {
|
||||
platformtesting.FindDashboardByID(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_FindDashboards(t *testing.T) {
|
||||
platformtesting.FindDashboards(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_DeleteDashboard(t *testing.T) {
|
||||
platformtesting.DeleteDashboard(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_UpdateDashboard(t *testing.T) {
|
||||
platformtesting.UpdateDashboard(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_AddDashboardCell(t *testing.T) {
|
||||
platformtesting.AddDashboardCell(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_RemoveDashboardCell(t *testing.T) {
|
||||
platformtesting.RemoveDashboardCell(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_UpdateDashboardCell(t *testing.T) {
|
||||
platformtesting.UpdateDashboardCell(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_ReplaceDashboardCells(t *testing.T) {
|
||||
platformtesting.ReplaceDashboardCells(initDashboardService, t)
|
||||
func TestDashboardService(t *testing.T) {
|
||||
platformtesting.DashboardService(initDashboardService, t)
|
||||
}
|
||||
|
|
|
|||
38
dashboard.go
38
dashboard.go
|
|
@ -2,16 +2,28 @@ package platform
|
|||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"sort"
|
||||
"time"
|
||||
)
|
||||
|
||||
// ErrDashboardNotFound is the error for a missing dashboard.
|
||||
const ErrDashboardNotFound = ChronografError("dashboard not found")
|
||||
// ErrDashboardNotFound is the error msg for a missing dashboard.
|
||||
const ErrDashboardNotFound = "dashboard not found"
|
||||
|
||||
// ErrCellNotFound is the error for a missing cell.
|
||||
const ErrCellNotFound = ChronografError("cell not found")
|
||||
// ErrCellNotFound is the error msg for a missing cell.
|
||||
const ErrCellNotFound = "cell not found"
|
||||
|
||||
// ops for dashboard service.
|
||||
const (
|
||||
OpFindDashboardByID = "FindDashboardByID"
|
||||
OpFindDashboards = "FindDashboards"
|
||||
OpCreateDashboard = "CreateDashboard"
|
||||
OpUpdateDashboard = "UpdateDashboard"
|
||||
OpAddDashboardCell = "AddDashboardCell"
|
||||
OpRemoveDashboardCell = "RemoveDashboardCell"
|
||||
OpUpdateDashboardCell = "UpdateDashboardCell"
|
||||
OpDeleteDashboard = "DeleteDashboard"
|
||||
OpReplaceDashboardCells = "ReplaceDashboardCells"
|
||||
)
|
||||
|
||||
// DashboardService represents a service for managing dashboard data.
|
||||
type DashboardService interface {
|
||||
|
|
@ -54,7 +66,7 @@ type Dashboard struct {
|
|||
Meta DashboardMeta `json:"meta"`
|
||||
}
|
||||
|
||||
// Dashboard meta contains meta information about dashboards
|
||||
// DashboardMeta contains meta information about dashboards
|
||||
type DashboardMeta struct {
|
||||
CreatedAt time.Time `json:"createdAt"`
|
||||
UpdatedAt time.Time `json:"updatedAt"`
|
||||
|
|
@ -125,9 +137,12 @@ func (u DashboardUpdate) Apply(d *Dashboard) error {
|
|||
}
|
||||
|
||||
// Valid returns an error if the dashboard update is invalid.
|
||||
func (u DashboardUpdate) Valid() error {
|
||||
func (u DashboardUpdate) Valid() *Error {
|
||||
if u.Name == nil && u.Description == nil {
|
||||
return fmt.Errorf("must update at least one attribute")
|
||||
return &Error{
|
||||
Code: EInvalid,
|
||||
Msg: "must update at least one attribute",
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
|
|
@ -175,9 +190,12 @@ func (u CellUpdate) Apply(c *Cell) error {
|
|||
}
|
||||
|
||||
// Valid returns an error if the cell update is invalid.
|
||||
func (u CellUpdate) Valid() error {
|
||||
func (u CellUpdate) Valid() *Error {
|
||||
if u.H == nil && u.W == nil && u.Y == nil && u.X == nil && !u.ViewID.Valid() {
|
||||
return fmt.Errorf("must update at least one attribute")
|
||||
return &Error{
|
||||
Code: EInvalid,
|
||||
Msg: "must update at least one attribute",
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
|
|
|
|||
|
|
@ -88,9 +88,12 @@ type dashboardResponse struct {
|
|||
}
|
||||
|
||||
func (d dashboardResponse) toPlatform() *platform.Dashboard {
|
||||
cells := make([]*platform.Cell, 0, len(d.Cells))
|
||||
var cells []*platform.Cell
|
||||
if len(d.Cells) > 0 {
|
||||
cells = make([]*platform.Cell, len(d.Cells))
|
||||
}
|
||||
for i := range d.Cells {
|
||||
cells = append(cells, d.Cells[i].toPlatform())
|
||||
cells[i] = d.Cells[i].toPlatform()
|
||||
}
|
||||
return &platform.Dashboard{
|
||||
ID: d.ID,
|
||||
|
|
@ -221,7 +224,7 @@ func (h *DashboardHandler) handleGetDashboards(w http.ResponseWriter, r *http.Re
|
|||
|
||||
dashboards, _, err := h.DashboardService.FindDashboards(ctx, req.filter, req.opts)
|
||||
if err != nil {
|
||||
EncodeError(ctx, errors.InternalErrorf("Error loading dashboards: %v", err), w)
|
||||
EncodeError(ctx, err, w)
|
||||
return
|
||||
}
|
||||
|
||||
|
|
@ -292,7 +295,9 @@ func newGetDashboardsResponse(dashboards []*platform.Dashboard) getDashboardsRes
|
|||
}
|
||||
|
||||
for _, dashboard := range dashboards {
|
||||
res.Dashboards = append(res.Dashboards, newDashboardResponse(dashboard))
|
||||
if dashboard != nil {
|
||||
res.Dashboards = append(res.Dashboards, newDashboardResponse(dashboard))
|
||||
}
|
||||
}
|
||||
|
||||
return res
|
||||
|
|
@ -344,9 +349,6 @@ func (h *DashboardHandler) handleGetDashboard(w http.ResponseWriter, r *http.Req
|
|||
|
||||
dashboard, err := h.DashboardService.FindDashboardByID(ctx, req.DashboardID)
|
||||
if err != nil {
|
||||
if err == platform.ErrDashboardNotFound {
|
||||
err = errors.New(err.Error(), errors.NotFound)
|
||||
}
|
||||
EncodeError(ctx, err, w)
|
||||
return
|
||||
}
|
||||
|
|
@ -454,9 +456,6 @@ func (h *DashboardHandler) handleDeleteDashboard(w http.ResponseWriter, r *http.
|
|||
}
|
||||
|
||||
if err := h.DashboardService.DeleteDashboard(ctx, req.DashboardID); err != nil {
|
||||
if err == platform.ErrDashboardNotFound {
|
||||
err = errors.New(err.Error(), errors.NotFound)
|
||||
}
|
||||
EncodeError(ctx, err, w)
|
||||
return
|
||||
}
|
||||
|
|
@ -496,9 +495,6 @@ func (h *DashboardHandler) handlePatchDashboard(w http.ResponseWriter, r *http.R
|
|||
}
|
||||
dashboard, err := h.DashboardService.UpdateDashboard(ctx, req.DashboardID, req.Upd)
|
||||
if err != nil {
|
||||
if err == platform.ErrDashboardNotFound {
|
||||
err = errors.New(err.Error(), errors.NotFound)
|
||||
}
|
||||
EncodeError(ctx, err, w)
|
||||
return
|
||||
}
|
||||
|
|
@ -520,7 +516,6 @@ func decodePatchDashboardRequest(ctx context.Context, r *http.Request) (*patchDa
|
|||
if err := json.NewDecoder(r.Body).Decode(&upd); err != nil {
|
||||
return nil, errors.MalformedDataf(err.Error())
|
||||
}
|
||||
|
||||
req.Upd = upd
|
||||
|
||||
params := httprouter.ParamsFromContext(ctx)
|
||||
|
|
@ -548,7 +543,10 @@ func (r *patchDashboardRequest) Valid() error {
|
|||
return fmt.Errorf("missing dashboard ID")
|
||||
}
|
||||
|
||||
return r.Upd.Valid()
|
||||
if pe := r.Upd.Valid(); pe != nil {
|
||||
return pe
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
type postDashboardCellRequest struct {
|
||||
|
|
@ -595,9 +593,6 @@ func (h *DashboardHandler) handlePostDashboardCell(w http.ResponseWriter, r *htt
|
|||
return
|
||||
}
|
||||
if err := h.DashboardService.AddDashboardCell(ctx, req.dashboardID, req.cell, req.opts); err != nil {
|
||||
if err == platform.ErrDashboardNotFound {
|
||||
err = errors.New(err.Error(), errors.NotFound)
|
||||
}
|
||||
EncodeError(ctx, err, w)
|
||||
return
|
||||
}
|
||||
|
|
@ -692,9 +687,6 @@ func (h *DashboardHandler) handleDeleteDashboardCell(w http.ResponseWriter, r *h
|
|||
return
|
||||
}
|
||||
if err := h.DashboardService.RemoveDashboardCell(ctx, req.dashboardID, req.cellID); err != nil {
|
||||
if err == platform.ErrDashboardNotFound || err == platform.ErrCellNotFound {
|
||||
err = errors.New(err.Error(), errors.NotFound)
|
||||
}
|
||||
EncodeError(ctx, err, w)
|
||||
return
|
||||
}
|
||||
|
|
@ -714,7 +706,10 @@ func decodePatchDashboardCellRequest(ctx context.Context, r *http.Request) (*pat
|
|||
params := httprouter.ParamsFromContext(ctx)
|
||||
id := params.ByName("id")
|
||||
if id == "" {
|
||||
return nil, errors.InvalidDataf("url missing id")
|
||||
return nil, &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Msg: "url missing id",
|
||||
}
|
||||
}
|
||||
if err := req.dashboardID.DecodeFromString(id); err != nil {
|
||||
return nil, err
|
||||
|
|
@ -722,18 +717,24 @@ func decodePatchDashboardCellRequest(ctx context.Context, r *http.Request) (*pat
|
|||
|
||||
cellID := params.ByName("cellID")
|
||||
if cellID == "" {
|
||||
return nil, errors.InvalidDataf("url missing cellID")
|
||||
return nil, &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Msg: "cannot provide empty cell id",
|
||||
}
|
||||
}
|
||||
if err := req.cellID.DecodeFromString(cellID); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if err := json.NewDecoder(r.Body).Decode(&req.upd); err != nil {
|
||||
return nil, errors.MalformedDataf(err.Error())
|
||||
return nil, &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
|
||||
if err := req.upd.Valid(); err != nil {
|
||||
return nil, errors.InvalidDataf(err.Error())
|
||||
if pe := req.upd.Valid(); pe != nil {
|
||||
return nil, pe
|
||||
}
|
||||
|
||||
return req, nil
|
||||
|
|
@ -750,9 +751,6 @@ func (h *DashboardHandler) handlePatchDashboardCell(w http.ResponseWriter, r *ht
|
|||
}
|
||||
cell, err := h.DashboardService.UpdateDashboardCell(ctx, req.dashboardID, req.cellID, req.upd)
|
||||
if err != nil {
|
||||
if err == platform.ErrDashboardNotFound || err == platform.ErrCellNotFound {
|
||||
err = errors.New(err.Error(), errors.NotFound)
|
||||
}
|
||||
EncodeError(ctx, err, w)
|
||||
return
|
||||
}
|
||||
|
|
@ -768,6 +766,8 @@ type DashboardService struct {
|
|||
Addr string
|
||||
Token string
|
||||
InsecureSkipVerify bool
|
||||
// OpPrefix is the op prefix for certain errors op.
|
||||
OpPrefix string
|
||||
}
|
||||
|
||||
// FindDashboardByID returns a single dashboard by ID.
|
||||
|
|
@ -791,7 +791,7 @@ func (s *DashboardService) FindDashboardByID(ctx context.Context, id platform.ID
|
|||
return nil, err
|
||||
}
|
||||
|
||||
if err := CheckError(resp); err != nil {
|
||||
if err := CheckError(resp, true); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
|
|
@ -807,9 +807,11 @@ func (s *DashboardService) FindDashboardByID(ctx context.Context, id platform.ID
|
|||
// FindDashboards returns a list of dashboards that match filter and the total count of matching dashboards.
|
||||
// Additional options provide pagination & sorting.
|
||||
func (s *DashboardService) FindDashboards(ctx context.Context, filter platform.DashboardFilter, opts platform.FindOptions) ([]*platform.Dashboard, int, error) {
|
||||
dashboards := []*platform.Dashboard{}
|
||||
url, err := newURL(s.Addr, dashboardsPath)
|
||||
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
return dashboards, 0, err
|
||||
}
|
||||
|
||||
qp := url.Query()
|
||||
|
|
@ -821,7 +823,7 @@ func (s *DashboardService) FindDashboards(ctx context.Context, filter platform.D
|
|||
|
||||
req, err := http.NewRequest("GET", url.String(), nil)
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
return dashboards, 0, err
|
||||
}
|
||||
|
||||
SetToken(s.Token, req)
|
||||
|
|
@ -829,19 +831,19 @@ func (s *DashboardService) FindDashboards(ctx context.Context, filter platform.D
|
|||
|
||||
resp, err := hc.Do(req)
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
return dashboards, 0, err
|
||||
}
|
||||
|
||||
if err := CheckError(resp); err != nil {
|
||||
return nil, 0, err
|
||||
if err := CheckError(resp, true); err != nil {
|
||||
return dashboards, 0, err
|
||||
}
|
||||
|
||||
var dr getDashboardsResponse
|
||||
if err := json.NewDecoder(resp.Body).Decode(&dr); err != nil {
|
||||
return nil, 0, err
|
||||
return dashboards, 0, err
|
||||
}
|
||||
|
||||
dashboards := dr.toPlatform()
|
||||
dashboards = dr.toPlatform()
|
||||
return dashboards, len(dashboards), nil
|
||||
}
|
||||
|
||||
|
|
@ -872,7 +874,7 @@ func (s *DashboardService) CreateDashboard(ctx context.Context, d *platform.Dash
|
|||
return err
|
||||
}
|
||||
|
||||
if err := CheckError(resp); err != nil {
|
||||
if err := CheckError(resp, true); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
|
|
@ -886,6 +888,7 @@ func (s *DashboardService) CreateDashboard(ctx context.Context, d *platform.Dash
|
|||
// UpdateDashboard updates a single dashboard with changeset.
|
||||
// Returns the new dashboard state after update.
|
||||
func (s *DashboardService) UpdateDashboard(ctx context.Context, id platform.ID, upd platform.DashboardUpdate) (*platform.Dashboard, error) {
|
||||
//op := s.OpPrefix + platform.OpUpdateDashboard
|
||||
u, err := newURL(s.Addr, dashboardIDPath(id))
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
|
@ -911,7 +914,7 @@ func (s *DashboardService) UpdateDashboard(ctx context.Context, id platform.ID,
|
|||
return nil, err
|
||||
}
|
||||
|
||||
if err := CheckError(resp); err != nil {
|
||||
if err := CheckError(resp, true); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
|
|
@ -945,7 +948,7 @@ func (s *DashboardService) DeleteDashboard(ctx context.Context, id platform.ID)
|
|||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return CheckError(resp)
|
||||
return CheckError(resp, true)
|
||||
}
|
||||
|
||||
// AddDashboardCell adds a cell to a dashboard.
|
||||
|
|
@ -975,7 +978,7 @@ func (s *DashboardService) AddDashboardCell(ctx context.Context, id platform.ID,
|
|||
return err
|
||||
}
|
||||
|
||||
if err := CheckError(resp); err != nil {
|
||||
if err := CheckError(resp, true); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
|
|
@ -1001,13 +1004,17 @@ func (s *DashboardService) RemoveDashboardCell(ctx context.Context, dashboardID,
|
|||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return CheckError(resp)
|
||||
return CheckError(resp, true)
|
||||
}
|
||||
|
||||
// UpdateDashboardCell replaces the dashboard cell with the provided ID.
|
||||
func (s *DashboardService) UpdateDashboardCell(ctx context.Context, dashboardID, cellID platform.ID, upd platform.CellUpdate) (*platform.Cell, error) {
|
||||
op := s.OpPrefix + platform.OpUpdateDashboardCell
|
||||
if err := upd.Valid(); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Op: op,
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
|
||||
u, err := newURL(s.Addr, dashboardCellIDPath(dashboardID, cellID))
|
||||
|
|
@ -1035,7 +1042,7 @@ func (s *DashboardService) UpdateDashboardCell(ctx context.Context, dashboardID,
|
|||
return nil, err
|
||||
}
|
||||
|
||||
if err := CheckError(resp); err != nil {
|
||||
if err := CheckError(resp, true); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
|
|
@ -1076,7 +1083,7 @@ func (s *DashboardService) ReplaceDashboardCells(ctx context.Context, id platfor
|
|||
return err
|
||||
}
|
||||
|
||||
if err := CheckError(resp); err != nil {
|
||||
if err := CheckError(resp, true); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -290,7 +290,10 @@ func TestService_handleGetDashboard(t *testing.T) {
|
|||
fields: fields{
|
||||
&mock.DashboardService{
|
||||
FindDashboardByIDF: func(ctx context.Context, id platform.ID) (*platform.Dashboard, error) {
|
||||
return nil, platform.ErrDashboardNotFound
|
||||
return nil, &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
}
|
||||
},
|
||||
},
|
||||
},
|
||||
|
|
@ -509,7 +512,10 @@ func TestService_handleDeleteDashboard(t *testing.T) {
|
|||
fields: fields{
|
||||
&mock.DashboardService{
|
||||
DeleteDashboardF: func(ctx context.Context, id platform.ID) error {
|
||||
return platform.ErrDashboardNotFound
|
||||
return &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
}
|
||||
},
|
||||
},
|
||||
},
|
||||
|
|
@ -679,7 +685,10 @@ func TestService_handlePatchDashboard(t *testing.T) {
|
|||
fields: fields{
|
||||
&mock.DashboardService{
|
||||
UpdateDashboardF: func(ctx context.Context, id platform.ID, upd platform.DashboardUpdate) (*platform.Dashboard, error) {
|
||||
return nil, platform.ErrDashboardNotFound
|
||||
return nil, &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
}
|
||||
},
|
||||
},
|
||||
},
|
||||
|
|
@ -1086,7 +1095,7 @@ func Test_dashboardCellIDPath(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (platform.DashboardService, func()) {
|
||||
func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (platform.DashboardService, string, func()) {
|
||||
t.Helper()
|
||||
svc := inmem.NewService()
|
||||
svc.IDGenerator = f.IDGenerator
|
||||
|
|
@ -1109,11 +1118,12 @@ func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (plat
|
|||
handler.DashboardService = svc
|
||||
server := httptest.NewServer(handler)
|
||||
client := DashboardService{
|
||||
Addr: server.URL,
|
||||
Addr: server.URL,
|
||||
OpPrefix: inmem.OpPrefix,
|
||||
}
|
||||
done := server.Close
|
||||
|
||||
return &client, done
|
||||
return &client, inmem.OpPrefix, done
|
||||
}
|
||||
|
||||
func TestDashboardService(t *testing.T) {
|
||||
|
|
|
|||
|
|
@ -8,22 +8,35 @@ import (
|
|||
"github.com/influxdata/platform"
|
||||
)
|
||||
|
||||
func (s *Service) loadDashboard(ctx context.Context, id platform.ID) (*platform.Dashboard, error) {
|
||||
func (s *Service) loadDashboard(ctx context.Context, id platform.ID) (*platform.Dashboard, *platform.Error) {
|
||||
i, ok := s.dashboardKV.Load(id.String())
|
||||
if !ok {
|
||||
return nil, fmt.Errorf("dashboard not found")
|
||||
return nil, &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
}
|
||||
}
|
||||
|
||||
d, ok := i.(*platform.Dashboard)
|
||||
if !ok {
|
||||
return nil, fmt.Errorf("type %T is not a dashboard", i)
|
||||
return nil, &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Msg: fmt.Sprintf("type %T is not a dashboard", i),
|
||||
}
|
||||
}
|
||||
return d, nil
|
||||
}
|
||||
|
||||
// FindDashboardByID returns a single dashboard by ID.
|
||||
func (s *Service) FindDashboardByID(ctx context.Context, id platform.ID) (*platform.Dashboard, error) {
|
||||
return s.loadDashboard(ctx, id)
|
||||
d, pe := s.loadDashboard(ctx, id)
|
||||
if pe != nil {
|
||||
return nil, &platform.Error{
|
||||
Op: OpPrefix + platform.OpFindDashboardByID,
|
||||
Err: pe,
|
||||
}
|
||||
}
|
||||
return d, nil
|
||||
}
|
||||
|
||||
func filterDashboardFn(filter platform.DashboardFilter) func(d *platform.Dashboard) bool {
|
||||
|
|
@ -43,16 +56,22 @@ func filterDashboardFn(filter platform.DashboardFilter) func(d *platform.Dashboa
|
|||
|
||||
// FindDashboards implements platform.DashboardService interface.
|
||||
func (s *Service) FindDashboards(ctx context.Context, filter platform.DashboardFilter, opts platform.FindOptions) ([]*platform.Dashboard, int, error) {
|
||||
var ds []*platform.Dashboard
|
||||
op := OpPrefix + platform.OpFindDashboards
|
||||
if len(filter.IDs) == 1 {
|
||||
d, err := s.FindDashboardByID(ctx, *filter.IDs[0])
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
if err != nil && platform.ErrorCode(err) != platform.ENotFound {
|
||||
return ds, 0, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
if d == nil {
|
||||
return ds, 0, nil
|
||||
}
|
||||
|
||||
return []*platform.Dashboard{d}, 1, nil
|
||||
}
|
||||
|
||||
var ds []*platform.Dashboard
|
||||
var err error
|
||||
filterF := filterDashboardFn(filter)
|
||||
s.dashboardKV.Range(func(k, v interface{}) bool {
|
||||
|
|
@ -76,7 +95,14 @@ func (s *Service) FindDashboards(ctx context.Context, filter platform.DashboardF
|
|||
func (s *Service) CreateDashboard(ctx context.Context, d *platform.Dashboard) error {
|
||||
d.ID = s.IDGenerator.ID()
|
||||
d.Meta.CreatedAt = s.time()
|
||||
return s.PutDashboardWithMeta(ctx, d)
|
||||
err := s.PutDashboardWithMeta(ctx, d)
|
||||
if err != nil {
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: platform.OpCreateDashboard,
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// PutDashboard implements platform.DashboardService interface.
|
||||
|
|
@ -93,21 +119,34 @@ func (s *Service) PutDashboardWithMeta(ctx context.Context, d *platform.Dashboar
|
|||
|
||||
// UpdateDashboard implements platform.DashboardService interface.
|
||||
func (s *Service) UpdateDashboard(ctx context.Context, id platform.ID, upd platform.DashboardUpdate) (*platform.Dashboard, error) {
|
||||
op := OpPrefix + platform.OpUpdateDashboard
|
||||
if err := upd.Valid(); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
d, err := s.FindDashboardByID(ctx, id)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
if err := upd.Apply(d); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
if err := s.PutDashboardWithMeta(ctx, d); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
return d, nil
|
||||
|
|
@ -115,26 +154,50 @@ func (s *Service) UpdateDashboard(ctx context.Context, id platform.ID, upd platf
|
|||
|
||||
// DeleteDashboard implements platform.DashboardService interface.
|
||||
func (s *Service) DeleteDashboard(ctx context.Context, id platform.ID) error {
|
||||
op := OpPrefix + platform.OpDeleteDashboard
|
||||
if _, err := s.FindDashboardByID(ctx, id); err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
s.dashboardKV.Delete(id.String())
|
||||
return s.deleteLabel(ctx, platform.LabelFilter{ResourceID: id})
|
||||
err := s.deleteLabel(ctx, platform.LabelFilter{ResourceID: id})
|
||||
if err != nil {
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// AddDashboardCell adds a new cell to the dashboard.
|
||||
func (s *Service) AddDashboardCell(ctx context.Context, id platform.ID, cell *platform.Cell, opts platform.AddDashboardCellOptions) error {
|
||||
op := OpPrefix + platform.OpAddDashboardCell
|
||||
d, err := s.FindDashboardByID(ctx, id)
|
||||
if err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
cell.ID = s.IDGenerator.ID()
|
||||
if err := s.createViewIfNotExists(ctx, cell, opts); err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
d.Cells = append(d.Cells, cell)
|
||||
return s.PutDashboardWithMeta(ctx, d)
|
||||
if err = s.PutDashboardWithMeta(ctx, d); err != nil {
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// PutDashboardCell replaces a dashboad cell with the cell contents.
|
||||
|
|
@ -155,9 +218,13 @@ func (s *Service) PutDashboardCell(ctx context.Context, id platform.ID, cell *pl
|
|||
|
||||
// RemoveDashboardCell removes a dashboard cell from the dashboard.
|
||||
func (s *Service) RemoveDashboardCell(ctx context.Context, dashboardID platform.ID, cellID platform.ID) error {
|
||||
op := OpPrefix + platform.OpRemoveDashboardCell
|
||||
d, err := s.FindDashboardByID(ctx, dashboardID)
|
||||
if err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
idx := -1
|
||||
|
|
@ -168,7 +235,11 @@ func (s *Service) RemoveDashboardCell(ctx context.Context, dashboardID platform.
|
|||
}
|
||||
}
|
||||
if idx == -1 {
|
||||
return platform.ErrCellNotFound
|
||||
return &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Op: op,
|
||||
Msg: platform.ErrCellNotFound,
|
||||
}
|
||||
}
|
||||
|
||||
if err := s.DeleteView(ctx, d.Cells[idx].ViewID); err != nil {
|
||||
|
|
@ -182,13 +253,19 @@ func (s *Service) RemoveDashboardCell(ctx context.Context, dashboardID platform.
|
|||
|
||||
// UpdateDashboardCell will remove a cell from a dashboard.
|
||||
func (s *Service) UpdateDashboardCell(ctx context.Context, dashboardID platform.ID, cellID platform.ID, upd platform.CellUpdate) (*platform.Cell, error) {
|
||||
op := OpPrefix + platform.OpUpdateDashboardCell
|
||||
if err := upd.Valid(); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
d, err := s.FindDashboardByID(ctx, dashboardID)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
idx := -1
|
||||
|
|
@ -199,17 +276,27 @@ func (s *Service) UpdateDashboardCell(ctx context.Context, dashboardID platform.
|
|||
}
|
||||
}
|
||||
if idx == -1 {
|
||||
return nil, platform.ErrCellNotFound
|
||||
return nil, &platform.Error{
|
||||
Msg: platform.ErrCellNotFound,
|
||||
Op: op,
|
||||
Code: platform.ENotFound,
|
||||
}
|
||||
}
|
||||
|
||||
if err := upd.Apply(d.Cells[idx]); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
cell := d.Cells[idx]
|
||||
|
||||
if err := s.PutDashboardWithMeta(ctx, d); err != nil {
|
||||
return nil, err
|
||||
return nil, &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
return cell, nil
|
||||
|
|
@ -217,9 +304,13 @@ func (s *Service) UpdateDashboardCell(ctx context.Context, dashboardID platform.
|
|||
|
||||
// ReplaceDashboardCells replaces many dashboard cells.
|
||||
func (s *Service) ReplaceDashboardCells(ctx context.Context, id platform.ID, cs []*platform.Cell) error {
|
||||
op := OpPrefix + platform.OpReplaceDashboardCells
|
||||
d, err := s.FindDashboardByID(ctx, id)
|
||||
if err != nil {
|
||||
return err
|
||||
return &platform.Error{
|
||||
Err: err,
|
||||
Op: op,
|
||||
}
|
||||
}
|
||||
|
||||
ids := map[string]*platform.Cell{}
|
||||
|
|
@ -229,16 +320,28 @@ func (s *Service) ReplaceDashboardCells(ctx context.Context, id platform.ID, cs
|
|||
|
||||
for _, cell := range cs {
|
||||
if !cell.ID.Valid() {
|
||||
return fmt.Errorf("cannot provide empty cell id")
|
||||
return &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Op: op,
|
||||
Msg: "cannot provide empty cell id",
|
||||
}
|
||||
}
|
||||
|
||||
cl, ok := ids[cell.ID.String()]
|
||||
if !ok {
|
||||
return fmt.Errorf("cannot replace cells that were not already present")
|
||||
return &platform.Error{
|
||||
Code: platform.EConflict,
|
||||
Op: op,
|
||||
Msg: "cannot replace cells that were not already present",
|
||||
}
|
||||
}
|
||||
|
||||
if cl.ViewID != cell.ViewID {
|
||||
return fmt.Errorf("cannot update view id in replace")
|
||||
return &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Op: op,
|
||||
Msg: "cannot update view id in replace",
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ import (
|
|||
platformtesting "github.com/influxdata/platform/testing"
|
||||
)
|
||||
|
||||
func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (platform.DashboardService, func()) {
|
||||
func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (platform.DashboardService, string, func()) {
|
||||
s := NewService()
|
||||
s.IDGenerator = f.IDGenerator
|
||||
ctx := context.Background()
|
||||
|
|
@ -23,40 +23,9 @@ func initDashboardService(f platformtesting.DashboardFields, t *testing.T) (plat
|
|||
t.Fatalf("failed to populate views")
|
||||
}
|
||||
}
|
||||
return s, func() {}
|
||||
return s, OpPrefix, func() {}
|
||||
}
|
||||
|
||||
func TestDashboardService_CreateDashboard(t *testing.T) {
|
||||
platformtesting.CreateDashboard(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_FindDashboardByID(t *testing.T) {
|
||||
platformtesting.FindDashboardByID(initDashboardService, t)
|
||||
}
|
||||
func TestDashboardService_FindDashboards(t *testing.T) {
|
||||
platformtesting.FindDashboards(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_DeleteDashboard(t *testing.T) {
|
||||
platformtesting.DeleteDashboard(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_UpdateDashboard(t *testing.T) {
|
||||
platformtesting.UpdateDashboard(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_AddDashboardCell(t *testing.T) {
|
||||
platformtesting.AddDashboardCell(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_RemoveDashboardCell(t *testing.T) {
|
||||
platformtesting.RemoveDashboardCell(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_UpdateDashboardCell(t *testing.T) {
|
||||
platformtesting.UpdateDashboardCell(initDashboardService, t)
|
||||
}
|
||||
|
||||
func TestDashboardService_ReplaceDashboardCells(t *testing.T) {
|
||||
platformtesting.ReplaceDashboardCells(initDashboardService, t)
|
||||
func TestDashboardService(t *testing.T) {
|
||||
platformtesting.DashboardService(initDashboardService, t)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -3,7 +3,6 @@ package testing
|
|||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"fmt"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
|
|
@ -24,10 +23,10 @@ func idPtr(id platform.ID) *platform.ID {
|
|||
}
|
||||
|
||||
var dashboardCmpOptions = cmp.Options{
|
||||
cmpopts.EquateEmpty(),
|
||||
cmp.Comparer(func(x, y []byte) bool {
|
||||
return bytes.Equal(x, y)
|
||||
}),
|
||||
cmpopts.EquateEmpty(),
|
||||
}
|
||||
|
||||
// DashboardFields will include the IDGenerator, and dashboards
|
||||
|
|
@ -40,11 +39,11 @@ type DashboardFields struct {
|
|||
|
||||
// DashboardService tests all the service functions.
|
||||
func DashboardService(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()), t *testing.T,
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()), t *testing.T,
|
||||
) {
|
||||
tests := []struct {
|
||||
name string
|
||||
fn func(init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
fn func(init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T)
|
||||
}{
|
||||
{
|
||||
|
|
@ -63,6 +62,10 @@ func DashboardService(
|
|||
name: "UpdateDashboard",
|
||||
fn: UpdateDashboard,
|
||||
},
|
||||
{
|
||||
name: "DeleteDashboard",
|
||||
fn: DeleteDashboard,
|
||||
},
|
||||
{
|
||||
name: "AddDashboardCell",
|
||||
fn: AddDashboardCell,
|
||||
|
|
@ -89,7 +92,7 @@ func DashboardService(
|
|||
|
||||
// CreateDashboard testing
|
||||
func CreateDashboard(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -187,19 +190,12 @@ func CreateDashboard(
|
|||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
err := s.CreateDashboard(ctx, tt.args.dashboard)
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error messages to match '%v' got '%v'", tt.wants.err, err.Error())
|
||||
}
|
||||
}
|
||||
defer s.DeleteDashboard(ctx, tt.args.dashboard.ID)
|
||||
|
||||
dashboards, _, err := s.FindDashboards(ctx, platform.DashboardFilter{}, platform.DefaultDashboardFindOptions)
|
||||
|
|
@ -215,7 +211,7 @@ func CreateDashboard(
|
|||
|
||||
// AddDashboardCell testing
|
||||
func AddDashboardCell(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -328,23 +324,59 @@ func AddDashboardCell(
|
|||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "add cell with id not exist",
|
||||
fields: DashboardFields{
|
||||
NowFn: func() time.Time { return time.Date(2009, time.November, 10, 24, 0, 0, 0, time.UTC) },
|
||||
IDGenerator: &mock.IDGenerator{
|
||||
IDFn: func() platform.ID {
|
||||
return MustIDBase16(dashTwoID)
|
||||
},
|
||||
},
|
||||
Dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
Name: "dashboard1",
|
||||
},
|
||||
},
|
||||
Views: []*platform.View{
|
||||
{
|
||||
ViewContents: platform.ViewContents{
|
||||
ID: MustIDBase16(dashTwoID),
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
args: args{
|
||||
dashboardID: MustIDBase16(threeID),
|
||||
cell: &platform.Cell{
|
||||
ViewID: MustIDBase16(dashTwoID),
|
||||
},
|
||||
},
|
||||
wants: wants{
|
||||
err: &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Op: platform.OpAddDashboardCell,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
},
|
||||
dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
Name: "dashboard1",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
err := s.AddDashboardCell(ctx, tt.args.dashboardID, tt.args.cell, platform.AddDashboardCellOptions{})
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error messages to match '%v' got '%v'", tt.wants.err, err.Error())
|
||||
}
|
||||
}
|
||||
defer s.DeleteDashboard(ctx, tt.args.dashboardID)
|
||||
|
||||
dashboards, _, err := s.FindDashboards(ctx, platform.DashboardFilter{}, platform.DefaultDashboardFindOptions)
|
||||
|
|
@ -360,7 +392,7 @@ func AddDashboardCell(
|
|||
|
||||
// FindDashboardByID testing
|
||||
func FindDashboardByID(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -401,24 +433,41 @@ func FindDashboardByID(
|
|||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "find dashboard by id not exists",
|
||||
fields: DashboardFields{
|
||||
Dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
Name: "dashboard1",
|
||||
},
|
||||
{
|
||||
ID: MustIDBase16(dashTwoID),
|
||||
Name: "dashboard2",
|
||||
},
|
||||
},
|
||||
},
|
||||
args: args{
|
||||
id: MustIDBase16(threeID),
|
||||
},
|
||||
wants: wants{
|
||||
err: &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Op: platform.OpFindDashboardByID,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
|
||||
dashboard, err := s.FindDashboardByID(ctx, tt.args.id)
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected errors to be equal '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
if diff := cmp.Diff(dashboard, tt.wants.dashboard, dashboardCmpOptions...); diff != "" {
|
||||
t.Errorf("dashboard is different -got/+want\ndiff %s", diff)
|
||||
|
|
@ -429,7 +478,7 @@ func FindDashboardByID(
|
|||
|
||||
// FindDashboards testing
|
||||
func FindDashboards(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -628,11 +677,35 @@ func FindDashboards(
|
|||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "find multiple dashboards by id not exists",
|
||||
fields: DashboardFields{
|
||||
Dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
Name: "abc",
|
||||
},
|
||||
{
|
||||
ID: MustIDBase16(dashTwoID),
|
||||
Name: "xyz",
|
||||
},
|
||||
},
|
||||
},
|
||||
args: args{
|
||||
IDs: []*platform.ID{
|
||||
idPtr(MustIDBase16(threeID)),
|
||||
},
|
||||
findOptions: platform.DefaultDashboardFindOptions,
|
||||
},
|
||||
wants: wants{
|
||||
dashboards: []*platform.Dashboard{},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
|
||||
|
|
@ -642,15 +715,7 @@ func FindDashboards(
|
|||
}
|
||||
|
||||
dashboards, _, err := s.FindDashboards(ctx, filter, tt.args.findOptions)
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected errors to be equal '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
if diff := cmp.Diff(dashboards, tt.wants.dashboards, dashboardCmpOptions...); diff != "" {
|
||||
t.Errorf("dashboards are different -got/+want\ndiff %s", diff)
|
||||
|
|
@ -661,7 +726,7 @@ func FindDashboards(
|
|||
|
||||
// DeleteDashboard testing
|
||||
func DeleteDashboard(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -722,7 +787,11 @@ func DeleteDashboard(
|
|||
ID: MustIDBase16(dashThreeID),
|
||||
},
|
||||
wants: wants{
|
||||
err: fmt.Errorf("dashboard not found"),
|
||||
err: &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Op: platform.OpDeleteDashboard,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
},
|
||||
dashboards: []*platform.Dashboard{
|
||||
{
|
||||
Name: "A",
|
||||
|
|
@ -739,19 +808,11 @@ func DeleteDashboard(
|
|||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
err := s.DeleteDashboard(ctx, tt.args.ID)
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error messages to match '%v' got '%v'", tt.wants.err, err.Error())
|
||||
}
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
filter := platform.DashboardFilter{}
|
||||
dashboards, _, err := s.FindDashboards(ctx, filter, platform.DefaultDashboardFindOptions)
|
||||
|
|
@ -767,7 +828,7 @@ func DeleteDashboard(
|
|||
|
||||
// UpdateDashboard testing
|
||||
func UpdateDashboard(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -876,11 +937,39 @@ func UpdateDashboard(
|
|||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "update with id not exist",
|
||||
fields: DashboardFields{
|
||||
NowFn: func() time.Time { return time.Date(2009, time.November, 10, 24, 0, 0, 0, time.UTC) },
|
||||
Dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
Name: "dashboard1",
|
||||
},
|
||||
{
|
||||
ID: MustIDBase16(dashTwoID),
|
||||
Name: "dashboard2",
|
||||
},
|
||||
},
|
||||
},
|
||||
args: args{
|
||||
id: MustIDBase16(threeID),
|
||||
description: "changed",
|
||||
name: "changed",
|
||||
},
|
||||
wants: wants{
|
||||
err: &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Op: platform.OpUpdateDashboard,
|
||||
Msg: platform.ErrDashboardNotFound,
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
|
||||
|
|
@ -893,15 +982,7 @@ func UpdateDashboard(
|
|||
}
|
||||
|
||||
dashboard, err := s.UpdateDashboard(ctx, tt.args.id, upd)
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error messages to match '%v' got '%v'", tt.wants.err, err.Error())
|
||||
}
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
if diff := cmp.Diff(dashboard, tt.wants.dashboard, dashboardCmpOptions...); diff != "" {
|
||||
t.Errorf("dashboard is different -got/+want\ndiff %s", diff)
|
||||
|
|
@ -912,7 +993,7 @@ func UpdateDashboard(
|
|||
|
||||
// RemoveDashboardCell testing
|
||||
func RemoveDashboardCell(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -989,19 +1070,12 @@ func RemoveDashboardCell(
|
|||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
err := s.RemoveDashboardCell(ctx, tt.args.dashboardID, tt.args.cellID)
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error messages to match '%v' got '%v'", tt.wants.err, err.Error())
|
||||
}
|
||||
}
|
||||
defer s.DeleteDashboard(ctx, tt.args.dashboardID)
|
||||
|
||||
dashboards, _, err := s.FindDashboards(ctx, platform.DashboardFilter{}, platform.DefaultDashboardFindOptions)
|
||||
|
|
@ -1017,7 +1091,7 @@ func RemoveDashboardCell(
|
|||
|
||||
// UpdateDashboardCell testing
|
||||
func UpdateDashboardCell(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -1094,7 +1168,7 @@ func UpdateDashboardCell(
|
|||
},
|
||||
},
|
||||
{
|
||||
name: "invalid cell update",
|
||||
name: "invalid cell update without attribute",
|
||||
fields: DashboardFields{
|
||||
NowFn: func() time.Time { return time.Date(2009, time.November, 10, 24, 0, 0, 0, time.UTC) },
|
||||
IDGenerator: &mock.IDGenerator{
|
||||
|
|
@ -1141,26 +1215,80 @@ func UpdateDashboardCell(
|
|||
},
|
||||
},
|
||||
},
|
||||
err: fmt.Errorf("must update at least one attribute"),
|
||||
err: &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Op: platform.OpUpdateDashboardCell,
|
||||
Msg: "must update at least one attribute",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "invalid cell update cell id not exist",
|
||||
fields: DashboardFields{
|
||||
NowFn: func() time.Time { return time.Date(2009, time.November, 10, 24, 0, 0, 0, time.UTC) },
|
||||
IDGenerator: &mock.IDGenerator{
|
||||
IDFn: func() platform.ID {
|
||||
return MustIDBase16(dashTwoID)
|
||||
},
|
||||
},
|
||||
Dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
Name: "dashboard1",
|
||||
Cells: []*platform.Cell{
|
||||
{
|
||||
ID: MustIDBase16(dashTwoID),
|
||||
ViewID: MustIDBase16(dashTwoID),
|
||||
},
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
ViewID: MustIDBase16(dashOneID),
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
args: args{
|
||||
dashboardID: MustIDBase16(dashOneID),
|
||||
cellID: MustIDBase16(fourID),
|
||||
cellUpdate: platform.CellUpdate{
|
||||
ViewID: MustIDBase16(threeID),
|
||||
},
|
||||
},
|
||||
wants: wants{
|
||||
dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
Name: "dashboard1",
|
||||
Cells: []*platform.Cell{
|
||||
{
|
||||
ID: MustIDBase16(dashTwoID),
|
||||
ViewID: MustIDBase16(dashTwoID),
|
||||
},
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
ViewID: MustIDBase16(dashOneID),
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
err: &platform.Error{
|
||||
Code: platform.ENotFound,
|
||||
Op: platform.OpUpdateDashboardCell,
|
||||
Msg: platform.ErrCellNotFound,
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
_, err := s.UpdateDashboardCell(ctx, tt.args.dashboardID, tt.args.cellID, tt.args.cellUpdate)
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error messages to match '%v' got '%v'", tt.wants.err, err.Error())
|
||||
}
|
||||
}
|
||||
defer s.DeleteDashboard(ctx, tt.args.dashboardID)
|
||||
|
||||
dashboards, _, err := s.FindDashboards(ctx, platform.DashboardFilter{}, platform.DefaultDashboardFindOptions)
|
||||
|
|
@ -1176,7 +1304,7 @@ func UpdateDashboardCell(
|
|||
|
||||
// ReplaceDashboardCells testing
|
||||
func ReplaceDashboardCells(
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, func()),
|
||||
init func(DashboardFields, *testing.T) (platform.DashboardService, string, func()),
|
||||
t *testing.T,
|
||||
) {
|
||||
type args struct {
|
||||
|
|
@ -1316,7 +1444,11 @@ func ReplaceDashboardCells(
|
|||
},
|
||||
},
|
||||
wants: wants{
|
||||
err: fmt.Errorf("cannot replace cells that were not already present"),
|
||||
err: &platform.Error{
|
||||
Code: platform.EConflict,
|
||||
Op: platform.OpReplaceDashboardCells,
|
||||
Msg: "cannot replace cells that were not already present",
|
||||
},
|
||||
dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
|
|
@ -1376,7 +1508,11 @@ func ReplaceDashboardCells(
|
|||
},
|
||||
},
|
||||
wants: wants{
|
||||
err: fmt.Errorf("cannot update view id in replace"),
|
||||
err: &platform.Error{
|
||||
Code: platform.EInvalid,
|
||||
Op: platform.OpReplaceDashboardCells,
|
||||
Msg: "cannot update view id in replace",
|
||||
},
|
||||
dashboards: []*platform.Dashboard{
|
||||
{
|
||||
ID: MustIDBase16(dashOneID),
|
||||
|
|
@ -1395,19 +1531,12 @@ func ReplaceDashboardCells(
|
|||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
s, done := init(tt.fields, t)
|
||||
s, opPrefix, done := init(tt.fields, t)
|
||||
defer done()
|
||||
ctx := context.Background()
|
||||
err := s.ReplaceDashboardCells(ctx, tt.args.dashboardID, tt.args.cells)
|
||||
if (err != nil) != (tt.wants.err != nil) {
|
||||
t.Fatalf("expected error '%v' got '%v'", tt.wants.err, err)
|
||||
}
|
||||
diffPlatformErrors(tt.name, err, tt.wants.err, opPrefix, t)
|
||||
|
||||
if err != nil && tt.wants.err != nil {
|
||||
if err.Error() != tt.wants.err.Error() {
|
||||
t.Fatalf("expected error messages to match '%v' got '%v'", tt.wants.err, err.Error())
|
||||
}
|
||||
}
|
||||
defer s.DeleteDashboard(ctx, tt.args.dashboardID)
|
||||
|
||||
dashboards, _, err := s.FindDashboards(ctx, platform.DashboardFilter{}, platform.DefaultDashboardFindOptions)
|
||||
|
|
|
|||
Loading…
Reference in New Issue