From 26cfd2b74f3ef904aec643a17df238f03ace7913 Mon Sep 17 00:00:00 2001 From: vikram yadav Date: Wed, 14 Apr 2021 19:56:39 -0400 Subject: [PATCH] Expose client state as an interface from service [#2305] Signed-off-by: vikram yadav --- cmd/octant-sample-plugin/main.go | 4 +- pkg/plugin/client_state.go | 72 ++++++++++++++++++++++++++++++ pkg/plugin/javascript.go | 8 ++-- pkg/plugin/service/handler.go | 14 +++--- pkg/plugin/service/handler_test.go | 40 ++++++++++------- pkg/plugin/service/router.go | 8 ++-- pkg/plugin/service/service.go | 7 ++- 7 files changed, 114 insertions(+), 39 deletions(-) create mode 100644 pkg/plugin/client_state.go diff --git a/cmd/octant-sample-plugin/main.go b/cmd/octant-sample-plugin/main.go index d185179fc5..a0ed91ff83 100644 --- a/cmd/octant-sample-plugin/main.go +++ b/cmd/octant-sample-plugin/main.go @@ -180,8 +180,8 @@ func handleAction(request *service.ActionRequest) error { if actionValue == pluginActionName { // Sending an alert needs a clientID from the request context - alert := action.CreateAlert(action.AlertTypeInfo, fmt.Sprintf("My client ID is: %s", request.ClientState.ClientID), action.DefaultAlertExpiration) - request.DashboardClient.SendAlert(request.Context(), request.ClientState.ClientID, alert) + alert := action.CreateAlert(action.AlertTypeInfo, fmt.Sprintf("My client ID is: %s", request.ClientState.ClientID()), action.DefaultAlertExpiration) + request.DashboardClient.SendAlert(request.Context(), request.ClientState.ClientID(), alert) } return nil diff --git a/pkg/plugin/client_state.go b/pkg/plugin/client_state.go new file mode 100644 index 0000000000..725d55c2de --- /dev/null +++ b/pkg/plugin/client_state.go @@ -0,0 +1,72 @@ +package plugin + +import ( + "context" + + ocontext "github.com/vmware-tanzu/octant/internal/context" +) + +type ClientState interface { + ClientID() string + Filters() []Filter + Namespace() string + ContextName() string +} + +func ClientStateFrom(ctx context.Context) clientState { + cs := ocontext.ClientStateFrom(ctx) + filters := []Filter{} + + for _, f := range cs.Filters { + filters = append(filters, clientFilter{key: f.Key, value: f.Value}) + } + + return clientState{ + clientID: cs.ClientID, + filters: filters, + namespace: cs.Namespace, + contextName: cs.ContextName, + } +} + +type Filter interface { + Key() string + Value() string +} + +var _ ClientState = (*clientState)(nil) + +type clientState struct { + clientID string + filters []Filter + namespace string + contextName string +} + +func (c clientState) ClientID() string { + return c.clientID +} +func (c clientState) Filters() []Filter { + return c.filters +} +func (c clientState) Namespace() string { + return c.namespace +} +func (c clientState) ContextName() string { + return c.contextName +} + +var _ Filter = (*clientFilter)(nil) + +type clientFilter struct { + key string + value string +} + +func (cf clientFilter) Key() string { + return cf.key +} + +func (cf clientFilter) Value() string { + return cf.value +} diff --git a/pkg/plugin/javascript.go b/pkg/plugin/javascript.go index 023a9b9455..4699fddf83 100644 --- a/pkg/plugin/javascript.go +++ b/pkg/plugin/javascript.go @@ -14,8 +14,6 @@ import ( "github.com/vmware-tanzu/octant/internal/util/json" - ocontext "github.com/vmware-tanzu/octant/internal/context" - "github.com/dop251/goja" "github.com/dop251/goja_nodejs/eventloop" "k8s.io/apimachinery/pkg/runtime" @@ -237,7 +235,7 @@ func (t *jsPlugin) Content(ctx context.Context, contentPath string) (component.C errCh := make(chan error) t.loop.RunOnLoop(func(vm *goja.Runtime) { - clientState := ocontext.ClientStateFrom(ctx) + clientState := ClientStateFrom(ctx) handler, err := vm.RunString("_concretePlugin.contentHandler") if err != nil { @@ -458,7 +456,7 @@ func (t *jsPlugin) HandleAction(ctx context.Context, actionPath string, payload errCh := make(chan error) t.loop.RunOnLoop(func(vm *goja.Runtime) { - clientState := ocontext.ClientStateFrom(ctx) + clientState := ClientStateFrom(ctx) handler, err := vm.RunString("_concretePlugin.actionHandler") if err != nil { @@ -571,7 +569,7 @@ func (t *jsPlugin) objectRequestCall(ctx context.Context, handlerName string, ob var response *goja.Object t.loop.RunOnLoop(func(vm *goja.Runtime) { - clientState := ocontext.ClientStateFrom(ctx) + clientState := ClientStateFrom(ctx) handler, err := vm.RunString(fmt.Sprintf("_concretePlugin.%s", handlerName)) if err != nil { diff --git a/pkg/plugin/service/handler.go b/pkg/plugin/service/handler.go index 4ca2c52fb1..69344bfdb8 100644 --- a/pkg/plugin/service/handler.go +++ b/pkg/plugin/service/handler.go @@ -4,8 +4,6 @@ import ( "context" "sync" - ocontext "github.com/vmware-tanzu/octant/internal/context" - "github.com/pkg/errors" "k8s.io/apimachinery/pkg/runtime" @@ -62,8 +60,6 @@ func (p *Handler) Register(ctx context.Context, dashboardAPIAddress string) (plu // Print prints components for an object. func (p *Handler) Print(ctx context.Context, object runtime.Object) (plugin.PrintResponse, error) { - clientState := ocontext.ClientStateFrom(ctx) - if p.HandlerFuncs.Print == nil { return plugin.PrintResponse{}, nil } @@ -72,7 +68,7 @@ func (p *Handler) Print(ctx context.Context, object runtime.Object) (plugin.Prin baseRequest: newBaseRequest(ctx, p.name), DashboardClient: p.dashboardClient, Object: object, - ClientState: clientState, + ClientState: plugin.ClientStateFrom(ctx), } return p.HandlerFuncs.Print(request) @@ -88,7 +84,7 @@ func (p *Handler) PrintTabs(ctx context.Context, object runtime.Object) ([]plugi baseRequest: newBaseRequest(ctx, p.name), DashboardClient: p.dashboardClient, Object: object, - ClientState: ocontext.ClientStateFrom(ctx), + ClientState: plugin.ClientStateFrom(ctx), } var tabResponses []plugin.TabResponse @@ -112,7 +108,7 @@ func (p *Handler) ObjectStatus(ctx context.Context, object runtime.Object) (plug baseRequest: newBaseRequest(ctx, p.name), DashboardClient: p.dashboardClient, Object: object, - ClientState: ocontext.ClientStateFrom(ctx), + ClientState: plugin.ClientStateFrom(ctx), } return p.HandlerFuncs.ObjectStatus(request) @@ -129,7 +125,7 @@ func (p *Handler) HandleAction(ctx context.Context, actionName string, payload a DashboardClient: p.dashboardClient, ActionName: actionName, Payload: payload, - ClientState: ocontext.ClientStateFrom(ctx), + ClientState: plugin.ClientStateFrom(ctx), } return p.HandlerFuncs.HandleAction(request) @@ -144,7 +140,7 @@ func (p *Handler) Navigation(ctx context.Context) (navigation.Navigation, error) request := &NavigationRequest{ baseRequest: newBaseRequest(ctx, p.name), DashboardClient: p.dashboardClient, - ClientState: ocontext.ClientStateFrom(ctx), + ClientState: plugin.ClientStateFrom(ctx), } return p.HandlerFuncs.Navigation(request) diff --git a/pkg/plugin/service/handler_test.go b/pkg/plugin/service/handler_test.go index d23819b4d9..4e6180a225 100644 --- a/pkg/plugin/service/handler_test.go +++ b/pkg/plugin/service/handler_test.go @@ -109,6 +109,10 @@ func TestHandler_Print_using_supplied_function(t *testing.T) { Filters: []octant.Filter{{Key: "foo", Value: "bar"}}, } + ctx := context.Background() + ctx = ocontext.WithClientState(ctx, clientState) + pluginClientState := plugin.ClientStateFrom(ctx) + dashboardClient := fake.NewMockDashboard(controller) ran := false @@ -118,15 +122,13 @@ func TestHandler_Print_using_supplied_function(t *testing.T) { ran = true assert.Equal(t, dashboardClient, r.DashboardClient) assert.Equal(t, pod, r.Object) - assert.Equal(t, clientState, r.ClientState) + assert.Equal(t, pluginClientState, r.ClientState) return plugin.PrintResponse{}, nil }, }, dashboardClient: dashboardClient, } - ctx := context.Background() - ctx = ocontext.WithClientState(ctx, clientState) got, err := h.Print(ctx, pod) require.NoError(t, err) @@ -167,6 +169,10 @@ func TestHandler_PrintTabs_using_supplied_function(t *testing.T) { Filters: []octant.Filter{{Key: "foo", Value: "bar"}}, } + ctx := context.Background() + ctx = ocontext.WithClientState(ctx, clientState) + pluginClientState := plugin.ClientStateFrom(ctx) + dashboardClient := fake.NewMockDashboard(controller) ran := false @@ -179,15 +185,13 @@ func TestHandler_PrintTabs_using_supplied_function(t *testing.T) { ran = true assert.Equal(t, dashboardClient, r.DashboardClient) assert.Equal(t, pod, r.Object) - assert.Equal(t, clientState, r.ClientState) + assert.Equal(t, pluginClientState, r.ClientState) return plugin.TabResponse{}, nil }, }, }, } - ctx := context.Background() - ctx = ocontext.WithClientState(ctx, clientState) got, err := h.PrintTabs(ctx, pod) require.NoError(t, err) @@ -231,6 +235,10 @@ func TestHandler_ObjectStatus_using_supplied_function(t *testing.T) { Filters: []octant.Filter{{Key: "foo", Value: "bar"}}, } + ctx := context.Background() + ctx = ocontext.WithClientState(ctx, clientState) + pluginClientState := plugin.ClientStateFrom(ctx) + ran := false h := Handler{ @@ -240,14 +248,12 @@ func TestHandler_ObjectStatus_using_supplied_function(t *testing.T) { ran = true assert.Equal(t, dashboardClient, r.DashboardClient) assert.Equal(t, pod, r.Object) - assert.Equal(t, clientState, r.ClientState) + assert.Equal(t, pluginClientState, r.ClientState) return plugin.ObjectStatusResponse{}, nil }, }, } - ctx := context.Background() - ctx = ocontext.WithClientState(ctx, clientState) got, err := h.ObjectStatus(ctx, pod) require.NoError(t, err) @@ -288,6 +294,10 @@ func TestHandler_HandleAction_using_supplied_function(t *testing.T) { Filters: []octant.Filter{{Key: "foo", Value: "bar"}}, } + ctx := context.Background() + ctx = ocontext.WithClientState(ctx, clientState) + pluginClientState := plugin.ClientStateFrom(ctx) + ran := false h := Handler{ @@ -297,15 +307,13 @@ func TestHandler_HandleAction_using_supplied_function(t *testing.T) { ran = true assert.Equal(t, dashboardClient, r.DashboardClient) assert.Equal(t, payload, r.Payload) - assert.Equal(t, clientState, r.ClientState) + assert.Equal(t, pluginClientState, r.ClientState) return nil }, }, } - ctx := context.Background() - ctx = ocontext.WithClientState(ctx, clientState) err := h.HandleAction(ctx, actionName, payload) assert.NoError(t, err) assert.True(t, ran) @@ -341,6 +349,10 @@ func TestHandler_Navigation_using_supplied_function(t *testing.T) { Filters: []octant.Filter{{Key: "foo", Value: "bar"}}, } + ctx := context.Background() + ctx = ocontext.WithClientState(ctx, clientState) + pluginClientState := plugin.ClientStateFrom(ctx) + ran := false h := Handler{ @@ -349,14 +361,12 @@ func TestHandler_Navigation_using_supplied_function(t *testing.T) { Navigation: func(r *NavigationRequest) (navigation.Navigation, error) { ran = true assert.Equal(t, dashboardClient, r.DashboardClient) - assert.Equal(t, clientState, r.ClientState) + assert.Equal(t, pluginClientState, r.ClientState) return navigation.Navigation{}, nil }, }, } - ctx := context.Background() - ctx = ocontext.WithClientState(ctx, clientState) got, err := h.Navigation(ctx) require.NoError(t, err) diff --git a/pkg/plugin/service/router.go b/pkg/plugin/service/router.go index 09ef3922d6..c48f9bdb64 100644 --- a/pkg/plugin/service/router.go +++ b/pkg/plugin/service/router.go @@ -5,7 +5,7 @@ import ( "github.com/gobwas/glob" - ocontext "github.com/vmware-tanzu/octant/internal/context" + "github.com/vmware-tanzu/octant/pkg/plugin" "github.com/vmware-tanzu/octant/pkg/view/component" ) @@ -16,7 +16,7 @@ type Request interface { Context() context.Context DashboardClient() Dashboard Path() string - ClientState() ocontext.ClientState + ClientState() plugin.ClientState } var _ Request = (*request)(nil) @@ -30,11 +30,11 @@ type request struct { path string - clientState ocontext.ClientState + clientState plugin.ClientState } // ClientState returns the octant plugin state -func (r *request) ClientState() ocontext.ClientState { +func (r *request) ClientState() plugin.ClientState { return r.clientState } diff --git a/pkg/plugin/service/service.go b/pkg/plugin/service/service.go index b9facba1d3..2d16802c30 100644 --- a/pkg/plugin/service/service.go +++ b/pkg/plugin/service/service.go @@ -13,7 +13,6 @@ import ( "github.com/pkg/errors" "k8s.io/apimachinery/pkg/runtime" - ocontext "github.com/vmware-tanzu/octant/internal/context" "github.com/vmware-tanzu/octant/pkg/action" "github.com/vmware-tanzu/octant/pkg/navigation" "github.com/vmware-tanzu/octant/pkg/plugin" @@ -156,7 +155,7 @@ type PrintRequest struct { DashboardClient Dashboard Object runtime.Object - ClientState ocontext.ClientState + ClientState plugin.ClientState } // ActionRequest is a request for actions. @@ -166,7 +165,7 @@ type ActionRequest struct { DashboardClient Dashboard ActionName string Payload action.Payload - ClientState ocontext.ClientState + ClientState plugin.ClientState } // NavigationRequest is a request for navigation. @@ -174,7 +173,7 @@ type NavigationRequest struct { baseRequest DashboardClient Dashboard - ClientState ocontext.ClientState + ClientState plugin.ClientState } type HandlerPrinterFunc func(request *PrintRequest) (plugin.PrintResponse, error)