@@ -62,9 +62,10 @@ type MCPServerOptions struct {
6262
6363func  NewMCPServerOptions (streams  genericiooptions.IOStreams ) * MCPServerOptions  {
6464	return  & MCPServerOptions {
65- 		IOStreams :  streams ,
66- 		Profile :    "full" ,
67- 		ListOutput : "table" ,
65+ 		IOStreams :    streams ,
66+ 		Profile :      "full" ,
67+ 		ListOutput :   "table" ,
68+ 		StaticConfig : & config.StaticConfig {},
6869	}
6970}
7071
@@ -76,7 +77,7 @@ func NewMCPServer(streams genericiooptions.IOStreams) *cobra.Command {
7677		Long :    long ,
7778		Example : examples ,
7879		RunE : func (c  * cobra.Command , args  []string ) error  {
79- 			if  err  :=  o .Complete (); err  !=  nil  {
80+ 			if  err  :=  o .Complete (c ); err  !=  nil  {
8081				return  err 
8182			}
8283			if  err  :=  o .Validate (); err  !=  nil  {
@@ -98,16 +99,14 @@ func NewMCPServer(streams genericiooptions.IOStreams) *cobra.Command {
9899	cmd .Flags ().StringVar (& o .SSEBaseUrl , "sse-base-url" , o .SSEBaseUrl , "SSE public base URL to use when sending the endpoint message (e.g. https://example.com)" )
99100	cmd .Flags ().StringVar (& o .Kubeconfig , "kubeconfig" , o .Kubeconfig , "Path to the kubeconfig file to use for authentication" )
100101	cmd .Flags ().StringVar (& o .Profile , "profile" , o .Profile , "MCP profile to use (one of: " + strings .Join (mcp .ProfileNames , ", " )+ ")" )
101- 	cmd .Flags ().StringVar (& o .ListOutput , "list-output" , o .ListOutput , "Output format for resource list operations (one of: " + strings .Join (output .Names , ", " )+ ")" )
102+ 	cmd .Flags ().StringVar (& o .ListOutput , "list-output" , o .ListOutput , "Output format for resource list operations (one of: " + strings .Join (output .Names , ", " )+ "). Defaults to table. " )
102103	cmd .Flags ().BoolVar (& o .ReadOnly , "read-only" , o .ReadOnly , "If true, only tools annotated with readOnlyHint=true are exposed" )
103104	cmd .Flags ().BoolVar (& o .DisableDestructive , "disable-destructive" , o .DisableDestructive , "If true, tools annotated with destructiveHint=true are disabled" )
104105
105106	return  cmd 
106107}
107108
108- func  (m  * MCPServerOptions ) Complete () error  {
109- 	m .initializeLogging ()
110- 
109+ func  (m  * MCPServerOptions ) Complete (cmd  * cobra.Command ) error  {
111110	if  m .ConfigPath  !=  ""  {
112111		cnf , err  :=  config .ReadConfig (m .ConfigPath )
113112		if  err  !=  nil  {
@@ -116,16 +115,47 @@ func (m *MCPServerOptions) Complete() error {
116115		m .StaticConfig  =  cnf 
117116	}
118117
118+ 	m .loadFlags (cmd )
119+ 
120+ 	m .initializeLogging ()
121+ 
119122	return  nil 
120123}
121124
125+ func  (m  * MCPServerOptions ) loadFlags (cmd  * cobra.Command ) {
126+ 	if  cmd .Flag ("log-level" ).Changed  {
127+ 		m .StaticConfig .LogLevel  =  m .LogLevel 
128+ 	}
129+ 	if  cmd .Flag ("sse-port" ).Changed  {
130+ 		m .StaticConfig .SSEPort  =  m .SSEPort 
131+ 	}
132+ 	if  cmd .Flag ("http-port" ).Changed  {
133+ 		m .StaticConfig .HTTPPort  =  m .HttpPort 
134+ 	}
135+ 	if  cmd .Flag ("sse-base-url" ).Changed  {
136+ 		m .StaticConfig .SSEBaseURL  =  m .SSEBaseUrl 
137+ 	}
138+ 	if  cmd .Flag ("kubeconfig" ).Changed  {
139+ 		m .StaticConfig .KubeConfig  =  m .Kubeconfig 
140+ 	}
141+ 	if  cmd .Flag ("list-output" ).Changed  ||  m .StaticConfig .ListOutput  ==  ""  {
142+ 		m .StaticConfig .ListOutput  =  m .ListOutput 
143+ 	}
144+ 	if  cmd .Flag ("read-only" ).Changed  {
145+ 		m .StaticConfig .ReadOnly  =  m .ReadOnly 
146+ 	}
147+ 	if  cmd .Flag ("disable-destructive" ).Changed  {
148+ 		m .StaticConfig .DisableDestructive  =  m .DisableDestructive 
149+ 	}
150+ }
151+ 
122152func  (m  * MCPServerOptions ) initializeLogging () {
123153	flagSet  :=  flag .NewFlagSet ("klog" , flag .ContinueOnError )
124154	klog .InitFlags (flagSet )
125155	loggerOptions  :=  []textlogger.ConfigOption {textlogger .Output (m .Out )}
126- 	if  m .LogLevel  >=  0  {
127- 		loggerOptions  =  append (loggerOptions , textlogger .Verbosity (m .LogLevel ))
128- 		_  =  flagSet .Parse ([]string {"--v" , strconv .Itoa (m .LogLevel )})
156+ 	if  m .StaticConfig . LogLevel  >=  0  {
157+ 		loggerOptions  =  append (loggerOptions , textlogger .Verbosity (m .StaticConfig . LogLevel ))
158+ 		_  =  flagSet .Parse ([]string {"--v" , strconv .Itoa (m .StaticConfig . LogLevel )})
129159	}
130160	logger  :=  textlogger .NewLogger (textlogger .NewConfig (loggerOptions ... ))
131161	klog .SetLoggerWithOptions (logger )
@@ -140,16 +170,16 @@ func (m *MCPServerOptions) Run() error {
140170	if  profile  ==  nil  {
141171		return  fmt .Errorf ("Invalid profile name: %s, valid names are: %s\n " , m .Profile , strings .Join (mcp .ProfileNames , ", " ))
142172	}
143- 	listOutput  :=  output .FromString (m .ListOutput )
173+ 	listOutput  :=  output .FromString (m .StaticConfig . ListOutput )
144174	if  listOutput  ==  nil  {
145- 		return  fmt .Errorf ("Invalid output name: %s, valid names are: %s\n " , m .ListOutput , strings .Join (output .Names , ", " ))
175+ 		return  fmt .Errorf ("Invalid output name: %s, valid names are: %s\n " , m .StaticConfig . ListOutput , strings .Join (output .Names , ", " ))
146176	}
147177	klog .V (1 ).Info ("Starting kubernetes-mcp-server" )
148178	klog .V (1 ).Infof (" - Config: %s" , m .ConfigPath )
149179	klog .V (1 ).Infof (" - Profile: %s" , profile .GetName ())
150180	klog .V (1 ).Infof (" - ListOutput: %s" , listOutput .GetName ())
151- 	klog .V (1 ).Infof (" - Read-only mode: %t" , m .ReadOnly )
152- 	klog .V (1 ).Infof (" - Disable destructive tools: %t" , m .DisableDestructive )
181+ 	klog .V (1 ).Infof (" - Read-only mode: %t" , m .StaticConfig . ReadOnly )
182+ 	klog .V (1 ).Infof (" - Disable destructive tools: %t" , m .StaticConfig . DisableDestructive )
153183
154184	if  m .Version  {
155185		_ , _  =  fmt .Fprintf (m .Out , "%s\n " , version .Version )
@@ -158,9 +188,9 @@ func (m *MCPServerOptions) Run() error {
158188	mcpServer , err  :=  mcp .NewServer (mcp.Configuration {
159189		Profile :            profile ,
160190		ListOutput :         listOutput ,
161- 		ReadOnly :           m .ReadOnly ,
162- 		DisableDestructive : m .DisableDestructive ,
163- 		Kubeconfig :         m .Kubeconfig ,
191+ 		ReadOnly :           m .StaticConfig . ReadOnly ,
192+ 		DisableDestructive : m .StaticConfig . DisableDestructive ,
193+ 		Kubeconfig :         m .StaticConfig . KubeConfig ,
164194		StaticConfig :       m .StaticConfig ,
165195	})
166196	if  err  !=  nil  {
@@ -170,19 +200,19 @@ func (m *MCPServerOptions) Run() error {
170200
171201	ctx  :=  context .Background ()
172202
173- 	if  m .SSEPort  >  0  {
174- 		sseServer  :=  mcpServer .ServeSse (m .SSEBaseUrl )
203+ 	if  m .StaticConfig . SSEPort  >  0  {
204+ 		sseServer  :=  mcpServer .ServeSse (m .StaticConfig . SSEBaseURL )
175205		defer  func () { _  =  sseServer .Shutdown (ctx ) }()
176- 		klog .V (0 ).Infof ("SSE server starting on port %d and path /sse" , m .SSEPort )
177- 		if  err  :=  sseServer .Start (fmt .Sprintf (":%d" , m .SSEPort )); err  !=  nil  {
206+ 		klog .V (0 ).Infof ("SSE server starting on port %d and path /sse" , m .StaticConfig . SSEPort )
207+ 		if  err  :=  sseServer .Start (fmt .Sprintf (":%d" , m .StaticConfig . SSEPort )); err  !=  nil  {
178208			return  fmt .Errorf ("failed to start SSE server: %w\n " , err )
179209		}
180210	}
181211
182- 	if  m .HttpPort  >  0  {
212+ 	if  m .StaticConfig . HTTPPort  >  0  {
183213		httpServer  :=  mcpServer .ServeHTTP ()
184- 		klog .V (0 ).Infof ("Streaming HTTP server starting on port %d and path /mcp" , m .HttpPort )
185- 		if  err  :=  httpServer .Start (fmt .Sprintf (":%d" , m .HttpPort )); err  !=  nil  {
214+ 		klog .V (0 ).Infof ("Streaming HTTP server starting on port %d and path /mcp" , m .StaticConfig . HTTPPort )
215+ 		if  err  :=  httpServer .Start (fmt .Sprintf (":%d" , m .StaticConfig . HTTPPort )); err  !=  nil  {
186216			return  fmt .Errorf ("failed to start streaming HTTP server: %w\n " , err )
187217		}
188218	}
0 commit comments