Stats: use dashboard stats rather than list (#99130)
This commit is contained in:
@@ -180,11 +180,10 @@ func (dr *DashboardServiceImpl) Count(ctx context.Context, scopeParams *quota.Sc
|
||||
total := int64(0)
|
||||
for _, org := range orgs {
|
||||
ctx = identity.WithRequester(ctx, getDashboardBackgroundRequester(org.ID))
|
||||
dashs, err := dr.listDashboardsThroughK8s(ctx, org.ID)
|
||||
orgDashboards, err := dr.CountDashboardsInOrg(ctx, org.ID)
|
||||
if err != nil {
|
||||
return u, err
|
||||
return nil, err
|
||||
}
|
||||
orgDashboards := int64(len(dashs))
|
||||
total += orgDashboards
|
||||
|
||||
tag, err := quota.NewTag(dashboards.QuotaTargetSrv, dashboards.QuotaTarget, quota.OrgScope)
|
||||
@@ -206,6 +205,28 @@ func (dr *DashboardServiceImpl) Count(ctx context.Context, scopeParams *quota.Sc
|
||||
return dr.dashboardStore.Count(ctx, scopeParams)
|
||||
}
|
||||
|
||||
func (dr *DashboardServiceImpl) CountDashboardsInOrg(ctx context.Context, orgID int64) (int64, error) {
|
||||
if dr.features.IsEnabledGlobally(featuremgmt.FlagKubernetesCliDashboards) {
|
||||
resp, err := dr.k8sclient.getSearcher().GetStats(ctx, &resource.ResourceStatsRequest{
|
||||
Namespace: dr.k8sclient.getNamespace(orgID),
|
||||
Kinds: []string{
|
||||
v0alpha1.GROUP + "/" + v0alpha1.DashboardResourceInfo.GetName(),
|
||||
},
|
||||
})
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
if len(resp.Stats) != 1 {
|
||||
return 0, fmt.Errorf("expected 1 stat, got %d", len(resp.Stats))
|
||||
}
|
||||
|
||||
return resp.Stats[0].Count, nil
|
||||
}
|
||||
|
||||
return dr.dashboardStore.CountInOrg(ctx, orgID)
|
||||
}
|
||||
|
||||
func readQuotaConfig(cfg *setting.Cfg) (*quota.Map, error) {
|
||||
limits := "a.Map{}
|
||||
|
||||
|
||||
@@ -271,6 +271,11 @@ func (m *mockResourceIndexClient) Search(ctx context.Context, req *resource.Reso
|
||||
return args.Get(0).(*resource.ResourceSearchResponse), args.Error(1)
|
||||
}
|
||||
|
||||
func (m *mockResourceIndexClient) GetStats(ctx context.Context, in *resource.ResourceStatsRequest, opts ...grpc.CallOption) (*resource.ResourceStatsResponse, error) {
|
||||
args := m.Called(in)
|
||||
return args.Get(0).(*resource.ResourceStatsResponse), args.Error(1)
|
||||
}
|
||||
|
||||
type mockResourceInterface struct {
|
||||
mock.Mock
|
||||
dynamic.ResourceInterface
|
||||
@@ -1779,44 +1784,17 @@ func TestQuotaCount(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
dashboardUnstructuredOrg1 := unstructured.UnstructuredList{
|
||||
Items: []unstructured.Unstructured{{
|
||||
Object: map[string]any{
|
||||
"metadata": map[string]any{
|
||||
"name": "uid",
|
||||
},
|
||||
"spec": map[string]any{
|
||||
"test": "test",
|
||||
"version": int64(1),
|
||||
"title": "testing slugify",
|
||||
},
|
||||
},
|
||||
}},
|
||||
}
|
||||
dashboardUnstructuredOrg2 := unstructured.UnstructuredList{
|
||||
Items: []unstructured.Unstructured{{
|
||||
Object: map[string]any{
|
||||
"metadata": map[string]any{
|
||||
"name": "uid",
|
||||
},
|
||||
"spec": map[string]any{
|
||||
"test": "test",
|
||||
"version": int64(1),
|
||||
"title": "testing slugify",
|
||||
},
|
||||
countOrg1 := resource.ResourceStatsResponse{
|
||||
Stats: []*resource.ResourceStatsResponse_Stats{
|
||||
{
|
||||
Count: 1,
|
||||
},
|
||||
},
|
||||
}
|
||||
countOrg2 := resource.ResourceStatsResponse{
|
||||
Stats: []*resource.ResourceStatsResponse_Stats{
|
||||
{
|
||||
Object: map[string]any{
|
||||
"metadata": map[string]any{
|
||||
"name": "uid2",
|
||||
},
|
||||
"spec": map[string]any{
|
||||
"test": "test2",
|
||||
"version": int64(1),
|
||||
"title": "testing slugify2",
|
||||
},
|
||||
},
|
||||
Count: 2,
|
||||
},
|
||||
},
|
||||
}
|
||||
@@ -1833,13 +1811,11 @@ func TestQuotaCount(t *testing.T) {
|
||||
})
|
||||
|
||||
t.Run("Should use Kubernetes client if feature flags are enabled", func(t *testing.T) {
|
||||
ctx, k8sClientMock, k8sResourceMock := setupK8sDashboardTests(service)
|
||||
ctx, k8sClientMock, _ := setupK8sDashboardTests(service)
|
||||
orgSvc := orgtest.FakeOrgService{ExpectedOrgs: orgs}
|
||||
service.orgService = &orgSvc
|
||||
k8sClientMock.On("getClient", mock.Anything, int64(1)).Return(k8sResourceMock, true).Once()
|
||||
k8sClientMock.On("getClient", mock.Anything, int64(2)).Return(k8sResourceMock, true).Once()
|
||||
k8sResourceMock.On("List", mock.Anything, mock.Anything).Return(&dashboardUnstructuredOrg2, nil).Once()
|
||||
k8sResourceMock.On("List", mock.Anything, mock.Anything).Return(&dashboardUnstructuredOrg1, nil).Once()
|
||||
k8sClientMock.searcher.On("GetStats", mock.Anything).Return(&countOrg2, nil).Once()
|
||||
k8sClientMock.searcher.On("GetStats", mock.Anything).Return(&countOrg1, nil).Once()
|
||||
|
||||
result, err := service.Count(ctx, query)
|
||||
require.NoError(t, err)
|
||||
@@ -1858,6 +1834,38 @@ func TestQuotaCount(t *testing.T) {
|
||||
})
|
||||
}
|
||||
|
||||
func TestCountDashboardsInOrg(t *testing.T) {
|
||||
fakeStore := dashboards.FakeDashboardStore{}
|
||||
defer fakeStore.AssertExpectations(t)
|
||||
service := &DashboardServiceImpl{
|
||||
cfg: setting.NewCfg(),
|
||||
dashboardStore: &fakeStore,
|
||||
}
|
||||
count := resource.ResourceStatsResponse{
|
||||
Stats: []*resource.ResourceStatsResponse_Stats{
|
||||
{
|
||||
Count: 3,
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
t.Run("Should fallback to dashboard store if Kubernetes feature flags are not enabled", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures()
|
||||
fakeStore.On("CountInOrg", mock.Anything, mock.Anything).Return(nil, nil).Once()
|
||||
_, err := service.CountDashboardsInOrg(context.Background(), 1)
|
||||
require.NoError(t, err)
|
||||
fakeStore.AssertExpectations(t)
|
||||
})
|
||||
|
||||
t.Run("Should use Kubernetes client if feature flags are enabled", func(t *testing.T) {
|
||||
ctx, k8sClientMock, _ := setupK8sDashboardTests(service)
|
||||
k8sClientMock.searcher.On("GetStats", mock.Anything).Return(&count, nil).Once()
|
||||
result, err := service.CountDashboardsInOrg(ctx, 1)
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, result, int64(3))
|
||||
})
|
||||
}
|
||||
|
||||
func TestLegacySaveCommandToUnstructured(t *testing.T) {
|
||||
namespace := "test-namespace"
|
||||
t.Run("successfully converts save command to unstructured", func(t *testing.T) {
|
||||
|
||||
Reference in New Issue
Block a user