mirror of
https://github.com/k8sgpt-ai/k8sgpt.git
synced 2025-09-01 07:19:19 +00:00
feat: add storage class names' check.
Signed-off-by: Aris Boutselis <aris.boutselis@senseon.io>
This commit is contained in:
@@ -25,6 +25,16 @@ func (StatefulSetAnalyzer) Analyze(a Analyzer) ([]Result, error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
failures = append(failures, fmt.Sprintf("StatefulSet uses the service %s/%s which does not exist.", sts.Namespace, serviceName))
|
failures = append(failures, fmt.Sprintf("StatefulSet uses the service %s/%s which does not exist.", sts.Namespace, serviceName))
|
||||||
}
|
}
|
||||||
|
if len(sts.Spec.VolumeClaimTemplates) > 0 {
|
||||||
|
for _, volumeClaimTemplate := range sts.Spec.VolumeClaimTemplates {
|
||||||
|
if volumeClaimTemplate.Spec.StorageClassName != nil {
|
||||||
|
_, err := a.Client.GetClient().StorageV1().StorageClasses().Get(a.Context, *volumeClaimTemplate.Spec.StorageClassName, metav1.GetOptions{})
|
||||||
|
if err != nil {
|
||||||
|
failures = append(failures, fmt.Sprintf("StatefulSet uses the storage class %s which does not exist.", *volumeClaimTemplate.Spec.StorageClassName))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
if len(failures) > 0 {
|
if len(failures) > 0 {
|
||||||
preAnalysis[fmt.Sprintf("%s/%s", sts.Namespace, sts.Name)] = PreAnalysis{
|
preAnalysis[fmt.Sprintf("%s/%s", sts.Namespace, sts.Name)] = PreAnalysis{
|
||||||
StatefulSet: sts,
|
StatefulSet: sts,
|
||||||
|
@@ -7,6 +7,8 @@ import (
|
|||||||
"github.com/k8sgpt-ai/k8sgpt/pkg/kubernetes"
|
"github.com/k8sgpt-ai/k8sgpt/pkg/kubernetes"
|
||||||
"github.com/magiconair/properties/assert"
|
"github.com/magiconair/properties/assert"
|
||||||
appsv1 "k8s.io/api/apps/v1"
|
appsv1 "k8s.io/api/apps/v1"
|
||||||
|
corev1 "k8s.io/api/core/v1"
|
||||||
|
"k8s.io/apimachinery/pkg/api/resource"
|
||||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||||
"k8s.io/client-go/kubernetes/fake"
|
"k8s.io/client-go/kubernetes/fake"
|
||||||
)
|
)
|
||||||
@@ -76,3 +78,69 @@ func TestStatefulSetAnalyzerWithoutService(t *testing.T) {
|
|||||||
t.Errorf("Error expected: '%v', not found in StatefulSet's analysis results", want)
|
t.Errorf("Error expected: '%v', not found in StatefulSet's analysis results", want)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestStatefulSetAnalyzerMissingStorageClass(t *testing.T) {
|
||||||
|
storageClassName := "example-sc"
|
||||||
|
clientset := fake.NewSimpleClientset(
|
||||||
|
&appsv1.StatefulSet{
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Name: "example",
|
||||||
|
Namespace: "default",
|
||||||
|
},
|
||||||
|
Spec: appsv1.StatefulSetSpec{
|
||||||
|
ServiceName: "example-svc",
|
||||||
|
VolumeClaimTemplates: []corev1.PersistentVolumeClaim{
|
||||||
|
{
|
||||||
|
TypeMeta: metav1.TypeMeta{
|
||||||
|
Kind: "PersistentVolumeClaim",
|
||||||
|
APIVersion: "v1",
|
||||||
|
},
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Name: "pvc-example",
|
||||||
|
},
|
||||||
|
Spec: corev1.PersistentVolumeClaimSpec{
|
||||||
|
StorageClassName: &storageClassName,
|
||||||
|
AccessModes: []corev1.PersistentVolumeAccessMode{
|
||||||
|
"ReadWriteOnce",
|
||||||
|
},
|
||||||
|
Resources: corev1.ResourceRequirements{
|
||||||
|
Requests: corev1.ResourceList{
|
||||||
|
corev1.ResourceStorage: resource.MustParse("1Gi"),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
statefulSetAnalyzer := StatefulSetAnalyzer{}
|
||||||
|
|
||||||
|
config := Analyzer{
|
||||||
|
Client: &kubernetes.Client{
|
||||||
|
Client: clientset,
|
||||||
|
},
|
||||||
|
Context: context.Background(),
|
||||||
|
Namespace: "default",
|
||||||
|
}
|
||||||
|
analysisResults, err := statefulSetAnalyzer.Analyze(config)
|
||||||
|
if err != nil {
|
||||||
|
t.Error(err)
|
||||||
|
}
|
||||||
|
var errorFound bool
|
||||||
|
want := "StatefulSet uses the storage class example-sc which does not exist."
|
||||||
|
|
||||||
|
for _, analysis := range analysisResults {
|
||||||
|
for _, got := range analysis.Error {
|
||||||
|
if want == got {
|
||||||
|
errorFound = true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if errorFound {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if !errorFound {
|
||||||
|
t.Errorf("Error expected: '%v', not found in StatefulSet's analysis results", want)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
Reference in New Issue
Block a user