| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | package api | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | import ( | 
					
						
							|  |  |  | 	"context" | 
					
						
							|  |  |  | 	"encoding/json" | 
					
						
							|  |  |  | 	"fmt" | 
					
						
							| 
									
										
										
										
											2022-08-10 21:37:51 +08:00
										 |  |  | 	"io" | 
					
						
							| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | 	"net/http" | 
					
						
							|  |  |  | 	"testing" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	"github.com/grafana/grafana/pkg/plugins" | 
					
						
							| 
									
										
										
										
											2022-08-10 17:56:48 +08:00
										 |  |  | 	"github.com/grafana/grafana/pkg/services/org" | 
					
						
							| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | 	"github.com/grafana/grafana/pkg/services/plugindashboards" | 
					
						
							| 
									
										
										
										
											2022-07-16 00:06:44 +08:00
										 |  |  | 	"github.com/grafana/grafana/pkg/services/quota/quotatest" | 
					
						
							| 
									
										
										
										
											2022-08-10 17:56:48 +08:00
										 |  |  | 	"github.com/grafana/grafana/pkg/services/user" | 
					
						
							| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | 	"github.com/grafana/grafana/pkg/web/webtest" | 
					
						
							|  |  |  | 	"github.com/stretchr/testify/require" | 
					
						
							|  |  |  | ) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | func TestGetPluginDashboards(t *testing.T) { | 
					
						
							|  |  |  | 	const existingPluginID = "existing-plugin" | 
					
						
							|  |  |  | 	pluginDashboardService := &pluginDashboardServiceMock{ | 
					
						
							|  |  |  | 		pluginDashboards: map[string][]*plugindashboards.PluginDashboard{ | 
					
						
							|  |  |  | 			existingPluginID: { | 
					
						
							|  |  |  | 				{ | 
					
						
							|  |  |  | 					PluginId: existingPluginID, | 
					
						
							|  |  |  | 					UID:      "a", | 
					
						
							|  |  |  | 					Title:    "A", | 
					
						
							|  |  |  | 				}, | 
					
						
							|  |  |  | 				{ | 
					
						
							|  |  |  | 					PluginId: existingPluginID, | 
					
						
							|  |  |  | 					UID:      "b", | 
					
						
							|  |  |  | 					Title:    "B", | 
					
						
							|  |  |  | 				}, | 
					
						
							|  |  |  | 			}, | 
					
						
							|  |  |  | 		}, | 
					
						
							|  |  |  | 		unexpectedErrors: map[string]error{ | 
					
						
							|  |  |  | 			"boom": fmt.Errorf("BOOM"), | 
					
						
							|  |  |  | 		}, | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	s := SetupAPITestServer(t, func(hs *HTTPServer) { | 
					
						
							|  |  |  | 		hs.pluginDashboardService = pluginDashboardService | 
					
						
							| 
									
										
										
										
											2022-07-16 00:06:44 +08:00
										 |  |  | 		hs.QuotaService = quotatest.NewQuotaServiceFake() | 
					
						
							| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | 	}) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	t.Run("Not signed in should return 404 Not Found", func(t *testing.T) { | 
					
						
							|  |  |  | 		req := s.NewGetRequest("/api/plugins/test/dashboards") | 
					
						
							|  |  |  | 		resp, err := s.Send(req) | 
					
						
							|  |  |  | 		require.NoError(t, err) | 
					
						
							|  |  |  | 		require.NoError(t, resp.Body.Close()) | 
					
						
							|  |  |  | 		require.Equal(t, http.StatusUnauthorized, resp.StatusCode) | 
					
						
							|  |  |  | 	}) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	t.Run("Signed in and not org admin should return 403 Forbidden", func(t *testing.T) { | 
					
						
							| 
									
										
										
										
											2022-08-10 17:56:48 +08:00
										 |  |  | 		user := &user.SignedInUser{ | 
					
						
							| 
									
										
										
										
											2022-08-11 19:28:55 +08:00
										 |  |  | 			UserID:  1, | 
					
						
							| 
									
										
										
										
											2022-08-10 17:56:48 +08:00
										 |  |  | 			OrgRole: org.RoleEditor, | 
					
						
							| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | 		} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 		resp, err := sendGetPluginDashboardsRequestForSignedInUser(t, s, existingPluginID, user) | 
					
						
							|  |  |  | 		require.NoError(t, err) | 
					
						
							|  |  |  | 		require.NoError(t, resp.Body.Close()) | 
					
						
							|  |  |  | 		require.Equal(t, http.StatusForbidden, resp.StatusCode) | 
					
						
							|  |  |  | 	}) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	t.Run("Signed in and org admin", func(t *testing.T) { | 
					
						
							| 
									
										
										
										
											2022-08-10 17:56:48 +08:00
										 |  |  | 		user := &user.SignedInUser{ | 
					
						
							| 
									
										
										
										
											2022-08-11 19:28:55 +08:00
										 |  |  | 			UserID:  1, | 
					
						
							|  |  |  | 			OrgID:   1, | 
					
						
							| 
									
										
										
										
											2022-08-10 17:56:48 +08:00
										 |  |  | 			OrgRole: org.RoleAdmin, | 
					
						
							| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | 		} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 		t.Run("When plugin doesn't exist should return 404 Not Found", func(t *testing.T) { | 
					
						
							|  |  |  | 			resp, err := sendGetPluginDashboardsRequestForSignedInUser(t, s, "not-exists", user) | 
					
						
							|  |  |  | 			require.NoError(t, err) | 
					
						
							|  |  |  | 			require.NoError(t, resp.Body.Close()) | 
					
						
							|  |  |  | 			require.Equal(t, http.StatusNotFound, resp.StatusCode) | 
					
						
							|  |  |  | 		}) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 		t.Run("When result is unexpected error should return 500 Internal Server Error", func(t *testing.T) { | 
					
						
							|  |  |  | 			resp, err := sendGetPluginDashboardsRequestForSignedInUser(t, s, "boom", user) | 
					
						
							|  |  |  | 			require.NoError(t, err) | 
					
						
							|  |  |  | 			require.NoError(t, resp.Body.Close()) | 
					
						
							|  |  |  | 			require.Equal(t, http.StatusInternalServerError, resp.StatusCode) | 
					
						
							|  |  |  | 		}) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 		t.Run("When plugin exists should return 200 OK with expected payload", func(t *testing.T) { | 
					
						
							|  |  |  | 			resp, err := sendGetPluginDashboardsRequestForSignedInUser(t, s, existingPluginID, user) | 
					
						
							|  |  |  | 			require.NoError(t, err) | 
					
						
							|  |  |  | 			require.Equal(t, http.StatusOK, resp.StatusCode) | 
					
						
							| 
									
										
										
										
											2022-08-10 21:37:51 +08:00
										 |  |  | 			bytes, err := io.ReadAll(resp.Body) | 
					
						
							| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | 			require.NoError(t, err) | 
					
						
							|  |  |  | 			require.NoError(t, resp.Body.Close()) | 
					
						
							|  |  |  | 			var listResp []*plugindashboards.PluginDashboard | 
					
						
							|  |  |  | 			err = json.Unmarshal(bytes, &listResp) | 
					
						
							|  |  |  | 			require.NoError(t, err) | 
					
						
							|  |  |  | 			require.NotNil(t, listResp) | 
					
						
							|  |  |  | 			require.Len(t, listResp, 2) | 
					
						
							|  |  |  | 			require.Equal(t, pluginDashboardService.pluginDashboards[existingPluginID], listResp) | 
					
						
							|  |  |  | 		}) | 
					
						
							|  |  |  | 	}) | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2022-08-10 17:56:48 +08:00
										 |  |  | func sendGetPluginDashboardsRequestForSignedInUser(t *testing.T, s *webtest.Server, pluginID string, user *user.SignedInUser) (*http.Response, error) { | 
					
						
							| 
									
										
										
										
											2022-03-11 01:38:04 +08:00
										 |  |  | 	t.Helper() | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	req := s.NewGetRequest(fmt.Sprintf("/api/plugins/%s/dashboards", pluginID)) | 
					
						
							|  |  |  | 	webtest.RequestWithSignedInUser(req, user) | 
					
						
							|  |  |  | 	return s.Send(req) | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | type pluginDashboardServiceMock struct { | 
					
						
							|  |  |  | 	plugindashboards.Service | 
					
						
							|  |  |  | 	pluginDashboards map[string][]*plugindashboards.PluginDashboard | 
					
						
							|  |  |  | 	unexpectedErrors map[string]error | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | func (m *pluginDashboardServiceMock) ListPluginDashboards(ctx context.Context, req *plugindashboards.ListPluginDashboardsRequest) (*plugindashboards.ListPluginDashboardsResponse, error) { | 
					
						
							|  |  |  | 	if pluginDashboards, exists := m.pluginDashboards[req.PluginID]; exists { | 
					
						
							|  |  |  | 		return &plugindashboards.ListPluginDashboardsResponse{ | 
					
						
							|  |  |  | 			Items: pluginDashboards, | 
					
						
							|  |  |  | 		}, nil | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	if err, exists := m.unexpectedErrors[req.PluginID]; exists { | 
					
						
							|  |  |  | 		return nil, err | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	return nil, plugins.NotFoundError{PluginID: req.PluginID} | 
					
						
							|  |  |  | } |