@@ -6,17 +6,20 @@ import (
66 "github.com/manusa/kubernetes-mcp-server/pkg/helm"
77 v1 "k8s.io/api/core/v1"
88 "k8s.io/apimachinery/pkg/api/meta"
9+ "k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
910 "k8s.io/apimachinery/pkg/runtime"
11+ "k8s.io/apimachinery/pkg/runtime/schema"
1012 "k8s.io/client-go/discovery"
1113 "k8s.io/client-go/discovery/cached/memory"
1214 "k8s.io/client-go/dynamic"
13- "k8s.io/client-go/kubernetes"
15+ clientgokubernetes "k8s.io/client-go/kubernetes"
1416 _ "k8s.io/client-go/plugin/pkg/client/auth/oidc"
1517 "k8s.io/client-go/rest"
1618 "k8s.io/client-go/restmapper"
1719 "k8s.io/client-go/tools/clientcmd"
1820 clientcmdapi "k8s.io/client-go/tools/clientcmd/api"
1921 "k8s.io/klog/v2"
22+ "k8s.io/metrics/pkg/apis/metrics"
2023 "strings"
2124)
2225
@@ -26,23 +29,51 @@ const (
2629
2730type CloseWatchKubeConfig func () error
2831
29- type Kubernetes struct {
32+ type Kubernetes interface {
33+ WatchKubeConfig (onKubeConfigChange func () error )
34+ Close ()
35+ Derived (ctx context.Context ) DerivedKubernetes
36+ ConfigurationView (minify bool ) (runtime.Object , error )
37+ IsOpenShift (ctx context.Context ) bool
38+ }
39+
40+ type DerivedKubernetes interface {
41+ IsOpenShift (ctx context.Context ) bool
42+ CacheInvalidate ()
43+ NewHelm () * helm.Helm
44+ EventsList (ctx context.Context , namespace string ) ([]map [string ]any , error )
45+ NamespacesList (ctx context.Context , options ResourceListOptions ) (runtime.Unstructured , error )
46+ PodsListInAllNamespaces (ctx context.Context , options ResourceListOptions ) (runtime.Unstructured , error )
47+ PodsListInNamespace (ctx context.Context , namespace string , options ResourceListOptions ) (runtime.Unstructured , error )
48+ PodsGet (ctx context.Context , namespace , name string ) (* unstructured.Unstructured , error )
49+ PodsDelete (ctx context.Context , namespace , name string ) (string , error )
50+ PodsLog (ctx context.Context , namespace , name , container string ) (string , error )
51+ PodsRun (ctx context.Context , namespace , name , image string , port int32 ) ([]* unstructured.Unstructured , error )
52+ PodsTop (ctx context.Context , options PodsTopOptions ) (* metrics.PodMetricsList , error )
53+ PodsExec (ctx context.Context , namespace , name , container string , command []string ) (string , error )
54+ ProjectsList (ctx context.Context , options ResourceListOptions ) (runtime.Unstructured , error )
55+ ResourcesList (ctx context.Context , gvk * schema.GroupVersionKind , namespace string , options ResourceListOptions ) (runtime.Unstructured , error )
56+ ResourcesGet (ctx context.Context , gvk * schema.GroupVersionKind , namespace , name string ) (* unstructured.Unstructured , error )
57+ ResourcesCreateOrUpdate (ctx context.Context , resource string ) ([]* unstructured.Unstructured , error )
58+ ResourcesDelete (ctx context.Context , gvk * schema.GroupVersionKind , namespace , name string ) error
59+ }
60+
61+ type kubernetes struct {
3062 // Kubeconfig path override
3163 Kubeconfig string
3264 cfg * rest.Config
3365 clientCmdConfig clientcmd.ClientConfig
3466 CloseWatchKubeConfig CloseWatchKubeConfig
3567 scheme * runtime.Scheme
3668 parameterCodec runtime.ParameterCodec
37- clientSet kubernetes .Interface
69+ clientSet clientgokubernetes .Interface
3870 discoveryClient discovery.CachedDiscoveryInterface
3971 deferredDiscoveryRESTMapper * restmapper.DeferredDiscoveryRESTMapper
4072 dynamicClient * dynamic.DynamicClient
41- Helm * helm.Helm
4273}
4374
44- func NewKubernetes (kubeconfig string ) (* Kubernetes , error ) {
45- k8s := & Kubernetes {
75+ func NewKubernetes (kubeconfig string ) (Kubernetes , error ) {
76+ k8s := & kubernetes {
4677 Kubeconfig : kubeconfig ,
4778 }
4879 if err := resolveKubernetesConfigurations (k8s ); err != nil {
@@ -53,7 +84,7 @@ func NewKubernetes(kubeconfig string) (*Kubernetes, error) {
5384 // return &impersonateRoundTripper{original}
5485 //})
5586 var err error
56- k8s .clientSet , err = kubernetes .NewForConfig (k8s .cfg )
87+ k8s .clientSet , err = clientgokubernetes .NewForConfig (k8s .cfg )
5788 if err != nil {
5889 return nil , err
5990 }
@@ -68,11 +99,10 @@ func NewKubernetes(kubeconfig string) (*Kubernetes, error) {
6899 return nil , err
69100 }
70101 k8s .parameterCodec = runtime .NewParameterCodec (k8s .scheme )
71- k8s .Helm = helm .NewHelm (k8s )
72102 return k8s , nil
73103}
74104
75- func (k * Kubernetes ) WatchKubeConfig (onKubeConfigChange func () error ) {
105+ func (k * kubernetes ) WatchKubeConfig (onKubeConfigChange func () error ) {
76106 if k .clientCmdConfig == nil {
77107 return
78108 }
@@ -108,21 +138,21 @@ func (k *Kubernetes) WatchKubeConfig(onKubeConfigChange func() error) {
108138 k .CloseWatchKubeConfig = watcher .Close
109139}
110140
111- func (k * Kubernetes ) Close () {
141+ func (k * kubernetes ) Close () {
112142 if k .CloseWatchKubeConfig != nil {
113143 _ = k .CloseWatchKubeConfig ()
114144 }
115145}
116146
117- func (k * Kubernetes ) ToDiscoveryClient () (discovery.CachedDiscoveryInterface , error ) {
147+ func (k * kubernetes ) ToDiscoveryClient () (discovery.CachedDiscoveryInterface , error ) {
118148 return k .discoveryClient , nil
119149}
120150
121- func (k * Kubernetes ) ToRESTMapper () (meta.RESTMapper , error ) {
151+ func (k * kubernetes ) ToRESTMapper () (meta.RESTMapper , error ) {
122152 return k .deferredDiscoveryRESTMapper , nil
123153}
124154
125- func (k * Kubernetes ) Derived (ctx context.Context ) * Kubernetes {
155+ func (k * kubernetes ) Derived (ctx context.Context ) DerivedKubernetes {
126156 authorization , ok := ctx .Value (AuthorizationHeader ).(string )
127157 if ! ok || ! strings .HasPrefix (authorization , "Bearer " ) {
128158 return k
@@ -142,14 +172,14 @@ func (k *Kubernetes) Derived(ctx context.Context) *Kubernetes {
142172 return k
143173 }
144174 clientCmdApiConfig .AuthInfos = make (map [string ]* clientcmdapi.AuthInfo )
145- derived := & Kubernetes {
175+ derived := & kubernetes {
146176 Kubeconfig : k .Kubeconfig ,
147177 clientCmdConfig : clientcmd .NewDefaultClientConfig (clientCmdApiConfig , nil ),
148178 cfg : derivedCfg ,
149179 scheme : k .scheme ,
150180 parameterCodec : k .parameterCodec ,
151181 }
152- derived .clientSet , err = kubernetes .NewForConfig (derived .cfg )
182+ derived .clientSet , err = clientgokubernetes .NewForConfig (derived .cfg )
153183 if err != nil {
154184 return k
155185 }
@@ -159,6 +189,19 @@ func (k *Kubernetes) Derived(ctx context.Context) *Kubernetes {
159189 if err != nil {
160190 return k
161191 }
162- derived .Helm = helm .NewHelm (derived )
163192 return derived
164193}
194+
195+ func (k * kubernetes ) CacheInvalidate () {
196+ if k .discoveryClient != nil {
197+ k .discoveryClient .Invalidate ()
198+ }
199+ if k .deferredDiscoveryRESTMapper != nil {
200+ k .deferredDiscoveryRESTMapper .Reset ()
201+ }
202+ }
203+
204+ func (k * kubernetes ) NewHelm () * helm.Helm {
205+ // This is a derived Kubernetes, so it already has the Helm initialized
206+ return helm .NewHelm (k )
207+ }
0 commit comments