Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(api): role/clusterole/podlist endpoints #8881

Merged
merged 6 commits into from
Apr 5, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
1 change: 0 additions & 1 deletion .github/workflows/cd-helm.yml
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@ jobs:
with:
version: v3.12.1
- uses: helm/chart-testing-action@v2.6.1
- run: ct lint --config=.ct.yml --target-branch ${{ github.event.repository.default_branch }}
- uses: helm/kind-action@v1.9.0
with:
node_image: kindest/node:v1.29.0
Expand Down
3 changes: 2 additions & 1 deletion modules/api/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,8 @@ fix-go: $(PRE)
.PHONY: run
run: build
@$(API_DIST_BINARY) \
--kubeconfig=$(KUBECONFIG)
--kubeconfig=$(KUBECONFIG) \
--metrics-provider=none

.PHONY: schema
schema: --ensure-kind-cluster build --swagger
Expand Down
12 changes: 12 additions & 0 deletions modules/api/pkg/handler/apihandler.go
Original file line number Diff line number Diff line change
Expand Up @@ -994,6 +994,12 @@ func CreateHTTPAPIHandler(iManager integration.Manager) (*restful.Container, err
Returns(http.StatusOK, "OK", clusterrolebinding.ClusterRoleBindingDetail{}))

// Role
apiV1Ws.Route(
apiV1Ws.GET("/role").To(apiHandler.handleGetRoleList).
// docs
Doc("returns a list of Roles from all namespace").
Writes(role.RoleList{}).
Returns(http.StatusOK, "OK", role.RoleList{}))
apiV1Ws.Route(
apiV1Ws.GET("/role/{namespace}").To(apiHandler.handleGetRoleList).
// docs
Expand All @@ -1011,6 +1017,12 @@ func CreateHTTPAPIHandler(iManager integration.Manager) (*restful.Container, err
Returns(http.StatusOK, "OK", role.RoleDetail{}))

// RoleBinding
apiV1Ws.Route(
apiV1Ws.GET("/rolebinding").To(apiHandler.handleGetRoleBindingList).
// docs
Doc("returns a list of RoleBindings from all namespace").
Writes(rolebinding.RoleBindingList{}).
Returns(http.StatusOK, "OK", rolebinding.RoleBindingList{}))
apiV1Ws.Route(
apiV1Ws.GET("/rolebinding/{namespace}").To(apiHandler.handleGetRoleBindingList).
// docs
Expand Down
21 changes: 15 additions & 6 deletions modules/api/pkg/resource/dataselect/dataselect.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,10 @@
package dataselect

import (
"log"
"sort"

"k8s.io/klog/v2"

metricapi "k8s.io/dashboard/api/pkg/integration/metric/api"
"k8s.io/dashboard/errors"
)
Expand Down Expand Up @@ -129,7 +130,7 @@ func (self *DataSelector) getMetrics(metricClient metricapi.MetricClient) (
metricPromises := make([]metricapi.MetricPromises, 0)

if metricClient == nil {
return metricPromises, errors.NewInternal("No metric client provided. Skipping metrics.")
return metricPromises, nil
}

metricNames := self.DataSelectQuery.MetricQuery.MetricNames
Expand All @@ -142,7 +143,7 @@ func (self *DataSelector) getMetrics(metricClient metricapi.MetricClient) (
// make sure data cells support metrics
metricDataCell, ok := dataCell.(MetricDataCell)
if !ok {
log.Printf("Data cell does not implement MetricDataCell. Skipping. %v", dataCell)
klog.V(0).InfoS("Data cell does not implement MetricDataCell. Skipping.", "dataCell", dataCell)
continue
}

Expand All @@ -162,7 +163,11 @@ func (self *DataSelector) getMetrics(metricClient metricapi.MetricClient) (
func (self *DataSelector) GetMetrics(metricClient metricapi.MetricClient) *DataSelector {
metricPromisesList, err := self.getMetrics(metricClient)
if err != nil {
log.Print(err)
klog.ErrorS(err, "error during getting metrics")
return self
}

if len(metricPromisesList) == 0 {
return self
}

Expand All @@ -180,13 +185,17 @@ func (self *DataSelector) GetMetrics(metricClient metricapi.MetricClient) *DataS
func (self *DataSelector) GetCumulativeMetrics(metricClient metricapi.MetricClient) *DataSelector {
metricPromisesList, err := self.getMetrics(metricClient)
if err != nil {
log.Print(err)
klog.ErrorS(err, "error during getting metrics")
return self
}

if len(metricPromisesList) == 0 {
return self
}

metricNames := self.DataSelectQuery.MetricQuery.MetricNames
if metricNames == nil {
log.Print("No metrics specified. Skipping metrics.")
klog.V(1).Info("Metrics names not provided. Skipping.")
return self
}

Expand Down
3 changes: 3 additions & 0 deletions modules/api/pkg/resource/node/detail.go
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,7 @@ type NodeDetail struct {
Node `json:",inline"`

// NodePhase is the current lifecycle phase of the node.
// Deprecated
Phase v1.NodePhase `json:"phase"`

// PodCIDR represents the pod IP range assigned to the node.
Expand Down Expand Up @@ -339,8 +340,10 @@ func toNodeDetail(node v1.Node, pods *pod.PodList, eventList *common.EventList,
Node: Node{
ObjectMeta: types.NewObjectMeta(node.ObjectMeta),
TypeMeta: types.NewTypeMeta(types.ResourceKindNode),
Ready: getNodeConditionStatus(node, v1.NodeReady),
AllocatedResources: allocatedResources,
},
// TODO: Remove deprecated field
Phase: node.Status.Phase,
ProviderID: node.Spec.ProviderID,
PodCIDR: node.Spec.PodCIDR,
Expand Down
1 change: 1 addition & 0 deletions modules/api/pkg/resource/node/detail_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@ func TestGetNodeDetail(t *testing.T) {
PodCapacity: 0,
PodFraction: 0,
},
Ready: v1.ConditionUnknown,
},
PodCIDR: "127.0.0.1",
ProviderID: "ID-1",
Expand Down
44 changes: 29 additions & 15 deletions modules/api/pkg/resource/pod/common_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -40,9 +40,10 @@ func TestToPodPodStatusFailed(t *testing.T) {
}

expected := Pod{
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: string(v1.PodFailed),
Warnings: []common.Event{},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: string(v1.PodFailed),
Warnings: []common.Event{},
ContainerStatuses: make([]ContainerStatus, 0),
}

actual := toPod(pod, &MetricsByPod{}, []common.Event{})
Expand All @@ -67,9 +68,10 @@ func TestToPodPodStatusSucceeded(t *testing.T) {
}

expected := Pod{
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: string(v1.PodSucceeded),
Warnings: []common.Event{},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: string(v1.PodSucceeded),
Warnings: []common.Event{},
ContainerStatuses: make([]ContainerStatus, 0),
}

actual := toPod(pod, &MetricsByPod{}, []common.Event{})
Expand Down Expand Up @@ -98,9 +100,10 @@ func TestToPodPodStatusRunning(t *testing.T) {
}

expected := Pod{
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: string(v1.PodRunning),
Warnings: []common.Event{},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: string(v1.PodRunning),
Warnings: []common.Event{},
ContainerStatuses: make([]ContainerStatus, 0),
}

actual := toPod(pod, &MetricsByPod{}, []common.Event{})
Expand All @@ -125,9 +128,10 @@ func TestToPodPodStatusPending(t *testing.T) {
}

expected := Pod{
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: string(v1.PodPending),
Warnings: []common.Event{},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: string(v1.PodPending),
Warnings: []common.Event{},
ContainerStatuses: make([]ContainerStatus, 0),
}

actual := toPod(pod, &MetricsByPod{}, []common.Event{})
Expand Down Expand Up @@ -165,6 +169,14 @@ func TestToPodContainerStates(t *testing.T) {
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Status: "Terminated",
Warnings: []common.Event{},
ContainerStatuses: []ContainerStatus{
{
State: Terminated,
},
{
State: Waiting,
},
},
}

actual := toPod(pod, &MetricsByPod{}, []common.Event{})
Expand All @@ -184,8 +196,9 @@ func TestToPod(t *testing.T) {
{
pod: &v1.Pod{}, metrics: &MetricsByPod{},
expected: Pod{
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Warnings: []common.Event{},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Warnings: []common.Event{},
ContainerStatuses: make([]ContainerStatus, 0),
},
}, {
pod: &v1.Pod{
Expand All @@ -199,7 +212,8 @@ func TestToPod(t *testing.T) {
Name: "test-pod",
Namespace: "test-namespace",
},
Warnings: []common.Event{},
Warnings: []common.Event{},
ContainerStatuses: make([]ContainerStatus, 0),
},
},
}
Expand Down
63 changes: 63 additions & 0 deletions modules/api/pkg/resource/pod/container.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
// Copyright 2017 The Kubernetes Authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package pod

import (
v1 "k8s.io/api/core/v1"
)

type ContainerStatus struct {
Name string `json:"name"`
State ContainerState `json:"state"`
Ready bool `json:"ready"`
}

type ContainerState string

const (
Waiting ContainerState = "Waiting"
Running ContainerState = "Running"
Terminated ContainerState = "Terminated"
Unknown ContainerState = "Unknown"
)

func ToContainerStatuses(containerStatuses []v1.ContainerStatus) []ContainerStatus {
result := make([]ContainerStatus, len(containerStatuses))
for i, c := range containerStatuses {
result[i] = ContainerStatus{
Name: c.Name,
State: toContainerState(c.State),
Ready: c.Ready,
}
}

return result
}

func toContainerState(state v1.ContainerState) ContainerState {
if state.Waiting != nil {
return Waiting
}

if state.Terminated != nil {
return Terminated
}

if state.Running != nil {
return Running
}

return Unknown
}
17 changes: 10 additions & 7 deletions modules/api/pkg/resource/pod/list.go
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,8 @@ type Pod struct {

// ContainerImages holds a list of the Pod images.
ContainerImages []string `json:"containerImages"`

ContainerStatuses []ContainerStatus `json:"containerStatuses"`
}

var EmptyPodList = &PodList{
Expand Down Expand Up @@ -155,13 +157,14 @@ func ToPodList(pods []v1.Pod, events []v1.Event, nonCriticalErrors []error, dsQu

func toPod(pod *v1.Pod, metrics *MetricsByPod, warnings []common.Event) Pod {
podDetail := Pod{
ObjectMeta: types.NewObjectMeta(pod.ObjectMeta),
TypeMeta: types.NewTypeMeta(types.ResourceKindPod),
Warnings: warnings,
Status: getPodStatus(*pod),
RestartCount: getRestartCount(*pod),
NodeName: pod.Spec.NodeName,
ContainerImages: common.GetContainerImages(&pod.Spec),
ObjectMeta: types.NewObjectMeta(pod.ObjectMeta),
TypeMeta: types.NewTypeMeta(types.ResourceKindPod),
Warnings: warnings,
Status: getPodStatus(*pod),
RestartCount: getRestartCount(*pod),
NodeName: pod.Spec.NodeName,
ContainerImages: common.GetContainerImages(&pod.Spec),
ContainerStatuses: ToContainerStatuses(append(pod.Status.InitContainerStatuses, pod.Status.ContainerStatuses...)),
}

if m, exists := metrics.MetricsMap[pod.UID]; exists {
Expand Down
5 changes: 3 additions & 2 deletions modules/api/pkg/resource/pod/list_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -102,8 +102,9 @@ func TestGetPodListFromChannels(t *testing.T) {
Labels: map[string]string{"key": "value"},
CreationTimestamp: metav1.Unix(111, 222),
},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Warnings: []common.Event{},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Warnings: []common.Event{},
ContainerStatuses: make([]pod.ContainerStatus, 0),
}},
Errors: []error{},
},
Expand Down
5 changes: 3 additions & 2 deletions modules/api/pkg/resource/service/pods_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -58,8 +58,9 @@ func TestGetServicePods(t *testing.T) {
Name: "pod-1",
UID: "test-uid",
Namespace: "ns-1"},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Warnings: []common.Event{},
TypeMeta: types.TypeMeta{Kind: types.ResourceKindPod},
Warnings: []common.Event{},
ContainerStatuses: make([]pod.ContainerStatus, 0),
},
},
Errors: []error{},
Expand Down