mcp-server-kubernetes 2.9.2 → 2.9.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -5,4 +5,7 @@ export declare const cleanupSchema: {
5
5
  readonly type: "object";
6
6
  readonly properties: {};
7
7
  };
8
+ readonly annotations: {
9
+ readonly destructiveHint: true;
10
+ };
8
11
  };
@@ -5,4 +5,7 @@ export const cleanupSchema = {
5
5
  type: "object",
6
6
  properties: {},
7
7
  },
8
+ annotations: {
9
+ destructiveHint: true,
10
+ },
8
11
  };
package/dist/index.d.ts CHANGED
@@ -2,6 +2,9 @@
2
2
  declare const destructiveTools: ({
3
3
  name: string;
4
4
  description: string;
5
+ annotations: {
6
+ destructiveHint: boolean;
7
+ };
5
8
  inputSchema: {
6
9
  type: string;
7
10
  properties: {
@@ -25,6 +28,9 @@ declare const destructiveTools: ({
25
28
  } | {
26
29
  name: string;
27
30
  description: string;
31
+ annotations: {
32
+ destructiveHint: boolean;
33
+ };
28
34
  inputSchema: {
29
35
  type: string;
30
36
  properties: {
@@ -82,9 +88,15 @@ declare const destructiveTools: ({
82
88
  readonly type: "object";
83
89
  readonly properties: {};
84
90
  };
91
+ readonly annotations: {
92
+ readonly destructiveHint: true;
93
+ };
85
94
  } | {
86
95
  readonly name: "kubectl_delete";
87
96
  readonly description: "Delete Kubernetes resources by resource type, name, labels, or from a manifest file";
97
+ readonly annotations: {
98
+ readonly destructiveHint: true;
99
+ };
88
100
  readonly inputSchema: {
89
101
  readonly type: "object";
90
102
  readonly properties: {
@@ -146,6 +158,10 @@ declare const allTools: ({
146
158
  type: string;
147
159
  description: string;
148
160
  };
161
+ chart: {
162
+ type: string;
163
+ description: string;
164
+ };
149
165
  namespace: {
150
166
  type: "string";
151
167
  description: string;
@@ -156,12 +172,53 @@ declare const allTools: ({
156
172
  description: string;
157
173
  default: string;
158
174
  };
175
+ repo: {
176
+ type: string;
177
+ description: string;
178
+ };
179
+ values: {
180
+ type: string;
181
+ description: string;
182
+ };
183
+ valuesFile: {
184
+ type: string;
185
+ description: string;
186
+ };
159
187
  };
160
188
  required: string[];
161
189
  };
162
190
  } | {
163
191
  name: string;
164
192
  description: string;
193
+ annotations: {
194
+ destructiveHint: boolean;
195
+ };
196
+ inputSchema: {
197
+ type: string;
198
+ properties: {
199
+ name: {
200
+ type: string;
201
+ description: string;
202
+ };
203
+ namespace: {
204
+ type: "string";
205
+ description: string;
206
+ default: string;
207
+ };
208
+ context: {
209
+ type: "string";
210
+ description: string;
211
+ default: string;
212
+ };
213
+ };
214
+ required: string[];
215
+ };
216
+ } | {
217
+ name: string;
218
+ description: string;
219
+ annotations: {
220
+ destructiveHint: boolean;
221
+ };
165
222
  inputSchema: {
166
223
  type: string;
167
224
  properties: {
@@ -215,6 +272,9 @@ declare const allTools: ({
215
272
  } | {
216
273
  name: string;
217
274
  description: string;
275
+ annotations: {
276
+ readOnlyHint: boolean;
277
+ };
218
278
  inputSchema: {
219
279
  type: string;
220
280
  properties: {
@@ -248,6 +308,9 @@ declare const allTools: ({
248
308
  } | {
249
309
  name: string;
250
310
  description: string;
311
+ annotations: {
312
+ readOnlyHint: boolean;
313
+ };
251
314
  inputSchema: {
252
315
  type: string;
253
316
  properties: {
@@ -279,6 +342,53 @@ declare const allTools: ({
279
342
  };
280
343
  };
281
344
  };
345
+ } | {
346
+ name: string;
347
+ description: string;
348
+ inputSchema: {
349
+ type: string;
350
+ properties: {
351
+ name: {
352
+ type: string;
353
+ description: string;
354
+ };
355
+ namespace: {
356
+ type: "string";
357
+ description: string;
358
+ default: string;
359
+ };
360
+ command: {
361
+ anyOf: ({
362
+ type: string;
363
+ items?: undefined;
364
+ } | {
365
+ type: string;
366
+ items: {
367
+ type: string;
368
+ };
369
+ })[];
370
+ description: string;
371
+ };
372
+ container: {
373
+ type: string;
374
+ description: string;
375
+ };
376
+ shell: {
377
+ type: string;
378
+ description: string;
379
+ };
380
+ timeout: {
381
+ type: string;
382
+ description: string;
383
+ };
384
+ context: {
385
+ type: "string";
386
+ description: string;
387
+ default: string;
388
+ };
389
+ };
390
+ required: string[];
391
+ };
282
392
  } | {
283
393
  readonly name: "cleanup";
284
394
  readonly description: "Cleanup all managed resources";
@@ -286,6 +396,9 @@ declare const allTools: ({
286
396
  readonly type: "object";
287
397
  readonly properties: {};
288
398
  };
399
+ readonly annotations: {
400
+ readonly destructiveHint: true;
401
+ };
289
402
  } | {
290
403
  name: string;
291
404
  description: string;
@@ -322,9 +435,44 @@ declare const allTools: ({
322
435
  };
323
436
  required: string[];
324
437
  };
438
+ } | {
439
+ name: string;
440
+ description: string;
441
+ inputSchema: {
442
+ type: string;
443
+ properties: {
444
+ name: {
445
+ type: string;
446
+ description: string;
447
+ };
448
+ namespace: {
449
+ type: "string";
450
+ description: string;
451
+ default: string;
452
+ };
453
+ replicas: {
454
+ type: string;
455
+ description: string;
456
+ };
457
+ resourceType: {
458
+ type: string;
459
+ description: string;
460
+ default: string;
461
+ };
462
+ context: {
463
+ type: "string";
464
+ description: string;
465
+ default: string;
466
+ };
467
+ };
468
+ required: string[];
469
+ };
325
470
  } | {
326
471
  readonly name: "kubectl_context";
327
472
  readonly description: "Manage Kubernetes contexts - list, get, or set the current context";
473
+ readonly annotations: {
474
+ readonly readOnlyHint: true;
475
+ };
328
476
  readonly inputSchema: {
329
477
  readonly type: "object";
330
478
  readonly properties: {
@@ -360,6 +508,9 @@ declare const allTools: ({
360
508
  } | {
361
509
  readonly name: "kubectl_get";
362
510
  readonly description: "Get or list Kubernetes resources by resource type, name, and optionally namespace";
511
+ readonly annotations: {
512
+ readonly readOnlyHint: true;
513
+ };
363
514
  readonly inputSchema: {
364
515
  readonly type: "object";
365
516
  readonly properties: {
@@ -410,6 +561,9 @@ declare const allTools: ({
410
561
  } | {
411
562
  readonly name: "kubectl_describe";
412
563
  readonly description: "Describe Kubernetes resources by resource type, name, and optionally namespace";
564
+ readonly annotations: {
565
+ readonly readOnlyHint: true;
566
+ };
413
567
  readonly inputSchema: {
414
568
  readonly type: "object";
415
569
  readonly properties: {
@@ -479,6 +633,9 @@ declare const allTools: ({
479
633
  } | {
480
634
  readonly name: "kubectl_delete";
481
635
  readonly description: "Delete Kubernetes resources by resource type, name, labels, or from a manifest file";
636
+ readonly annotations: {
637
+ readonly destructiveHint: true;
638
+ };
482
639
  readonly inputSchema: {
483
640
  readonly type: "object";
484
641
  readonly properties: {
@@ -657,6 +814,9 @@ declare const allTools: ({
657
814
  } | {
658
815
  readonly name: "kubectl_logs";
659
816
  readonly description: "Get logs from Kubernetes resources like pods, deployments, or jobs";
817
+ readonly annotations: {
818
+ readonly readOnlyHint: true;
819
+ };
660
820
  readonly inputSchema: {
661
821
  readonly type: "object";
662
822
  readonly properties: {
@@ -717,6 +877,104 @@ declare const allTools: ({
717
877
  };
718
878
  readonly required: readonly ["resourceType", "name", "namespace"];
719
879
  };
880
+ } | {
881
+ name: string;
882
+ description: string;
883
+ inputSchema: {
884
+ type: string;
885
+ properties: {
886
+ resourceType: {
887
+ type: string;
888
+ description: string;
889
+ };
890
+ name: {
891
+ type: string;
892
+ description: string;
893
+ };
894
+ namespace: {
895
+ type: "string";
896
+ description: string;
897
+ default: string;
898
+ };
899
+ patchType: {
900
+ type: string;
901
+ description: string;
902
+ enum: string[];
903
+ default: string;
904
+ };
905
+ patchData: {
906
+ type: string;
907
+ description: string;
908
+ };
909
+ patchFile: {
910
+ type: string;
911
+ description: string;
912
+ };
913
+ dryRun: {
914
+ type: "boolean";
915
+ description: string;
916
+ default: boolean;
917
+ };
918
+ context: {
919
+ type: "string";
920
+ description: string;
921
+ default: string;
922
+ };
923
+ };
924
+ required: string[];
925
+ };
926
+ } | {
927
+ name: string;
928
+ description: string;
929
+ inputSchema: {
930
+ type: string;
931
+ properties: {
932
+ subCommand: {
933
+ type: string;
934
+ description: string;
935
+ enum: string[];
936
+ default: string;
937
+ };
938
+ resourceType: {
939
+ type: string;
940
+ description: string;
941
+ enum: string[];
942
+ default: string;
943
+ };
944
+ name: {
945
+ type: string;
946
+ description: string;
947
+ };
948
+ namespace: {
949
+ type: "string";
950
+ description: string;
951
+ default: string;
952
+ };
953
+ revision: {
954
+ type: string;
955
+ description: string;
956
+ };
957
+ toRevision: {
958
+ type: string;
959
+ description: string;
960
+ };
961
+ timeout: {
962
+ type: string;
963
+ description: string;
964
+ };
965
+ watch: {
966
+ type: string;
967
+ description: string;
968
+ default: boolean;
969
+ };
970
+ context: {
971
+ type: "string";
972
+ description: string;
973
+ default: string;
974
+ };
975
+ };
976
+ required: string[];
977
+ };
720
978
  } | {
721
979
  name: string;
722
980
  description: string;
@@ -725,5 +983,8 @@ declare const allTools: ({
725
983
  properties: {};
726
984
  required: never[];
727
985
  };
986
+ annotations: {
987
+ readOnlyHint: boolean;
988
+ };
728
989
  })[];
729
990
  export { allTools, destructiveTools };
@@ -123,6 +123,9 @@ export declare const upgradeHelmChartSchema: {
123
123
  export declare const uninstallHelmChartSchema: {
124
124
  name: string;
125
125
  description: string;
126
+ annotations: {
127
+ destructiveHint: boolean;
128
+ };
126
129
  inputSchema: {
127
130
  type: string;
128
131
  properties: {
@@ -8,7 +8,7 @@ import { execFileSync } from "child_process";
8
8
  import { writeFileSync, unlinkSync } from "fs";
9
9
  import { dump } from "js-yaml";
10
10
  import { getSpawnMaxBuffer } from "../config/max-buffer.js";
11
- import { contextParameter, namespaceParameter } from "../models/common-parameters.js";
11
+ import { contextParameter, namespaceParameter, } from "../models/common-parameters.js";
12
12
  /**
13
13
  * Schema for install_helm_chart tool.
14
14
  * - name: Release name
@@ -111,6 +111,9 @@ export const upgradeHelmChartSchema = {
111
111
  export const uninstallHelmChartSchema = {
112
112
  name: "uninstall_helm_chart",
113
113
  description: "Uninstall a Helm chart release",
114
+ annotations: {
115
+ destructiveHint: true,
116
+ },
114
117
  inputSchema: {
115
118
  type: "object",
116
119
  properties: {
@@ -186,7 +189,8 @@ async function installHelmChartTemplate(params) {
186
189
  "template",
187
190
  params.name,
188
191
  params.chart,
189
- "--namespace", params.namespace
192
+ "--namespace",
193
+ params.namespace,
190
194
  ];
191
195
  if (params.repo) {
192
196
  templateArgs.push("--repo", params.repo);
@@ -233,10 +237,10 @@ async function installHelmChartTemplate(params) {
233
237
  text: JSON.stringify({
234
238
  status: "installed",
235
239
  message: `Helm chart '${params.name}' installed successfully using template mode`,
236
- steps: steps
237
- })
238
- }
239
- ]
240
+ steps: steps,
241
+ }),
242
+ },
243
+ ],
240
244
  };
241
245
  }
242
246
  catch (error) {
@@ -247,10 +251,10 @@ async function installHelmChartTemplate(params) {
247
251
  text: JSON.stringify({
248
252
  status: "failed",
249
253
  error: `Failed to install Helm chart using template mode: ${error.message}`,
250
- steps: steps
251
- })
252
- }
253
- ]
254
+ steps: steps,
255
+ }),
256
+ },
257
+ ],
254
258
  };
255
259
  }
256
260
  }
@@ -271,7 +275,13 @@ export async function installHelmChart(params) {
271
275
  executeCommand("helm", ["repo", "add", repoName, params.repo]);
272
276
  executeCommand("helm", ["repo", "update"]);
273
277
  }
274
- const args = ["install", params.name, params.chart, "--namespace", params.namespace];
278
+ const args = [
279
+ "install",
280
+ params.name,
281
+ params.chart,
282
+ "--namespace",
283
+ params.namespace,
284
+ ];
275
285
  // Add create namespace flag if requested
276
286
  if (params.createNamespace !== false) {
277
287
  args.push("--create-namespace");
@@ -302,10 +312,10 @@ export async function installHelmChart(params) {
302
312
  type: "text",
303
313
  text: JSON.stringify({
304
314
  status: "installed",
305
- message: `Helm chart '${params.name}' installed successfully in namespace '${params.namespace}'`
306
- })
307
- }
308
- ]
315
+ message: `Helm chart '${params.name}' installed successfully in namespace '${params.namespace}'`,
316
+ }),
317
+ },
318
+ ],
309
319
  };
310
320
  }
311
321
  catch (error) {
@@ -315,10 +325,10 @@ export async function installHelmChart(params) {
315
325
  type: "text",
316
326
  text: JSON.stringify({
317
327
  status: "failed",
318
- error: `Failed to install Helm chart: ${error.message}`
319
- })
320
- }
321
- ]
328
+ error: `Failed to install Helm chart: ${error.message}`,
329
+ }),
330
+ },
331
+ ],
322
332
  };
323
333
  }
324
334
  }
@@ -335,7 +345,13 @@ export async function upgradeHelmChart(params) {
335
345
  executeCommand("helm", ["repo", "add", repoName, params.repo]);
336
346
  executeCommand("helm", ["repo", "update"]);
337
347
  }
338
- const args = ["upgrade", params.name, params.chart, "--namespace", params.namespace];
348
+ const args = [
349
+ "upgrade",
350
+ params.name,
351
+ params.chart,
352
+ "--namespace",
353
+ params.namespace,
354
+ ];
339
355
  // Add values file if provided
340
356
  if (params.valuesFile) {
341
357
  args.push("-f", params.valuesFile);
@@ -362,10 +378,10 @@ export async function upgradeHelmChart(params) {
362
378
  type: "text",
363
379
  text: JSON.stringify({
364
380
  status: "upgraded",
365
- message: `Helm chart '${params.name}' upgraded successfully in namespace '${params.namespace}'`
366
- })
367
- }
368
- ]
381
+ message: `Helm chart '${params.name}' upgraded successfully in namespace '${params.namespace}'`,
382
+ }),
383
+ },
384
+ ],
369
385
  };
370
386
  }
371
387
  catch (error) {
@@ -375,10 +391,10 @@ export async function upgradeHelmChart(params) {
375
391
  type: "text",
376
392
  text: JSON.stringify({
377
393
  status: "failed",
378
- error: `Failed to upgrade Helm chart: ${error.message}`
379
- })
380
- }
381
- ]
394
+ error: `Failed to upgrade Helm chart: ${error.message}`,
395
+ }),
396
+ },
397
+ ],
382
398
  };
383
399
  }
384
400
  }
@@ -389,17 +405,22 @@ export async function upgradeHelmChart(params) {
389
405
  */
390
406
  export async function uninstallHelmChart(params) {
391
407
  try {
392
- executeCommand("helm", ["uninstall", params.name, "--namespace", params.namespace]);
408
+ executeCommand("helm", [
409
+ "uninstall",
410
+ params.name,
411
+ "--namespace",
412
+ params.namespace,
413
+ ]);
393
414
  return {
394
415
  content: [
395
416
  {
396
417
  type: "text",
397
418
  text: JSON.stringify({
398
419
  status: "uninstalled",
399
- message: `Helm chart '${params.name}' uninstalled successfully from namespace '${params.namespace}'`
400
- })
401
- }
402
- ]
420
+ message: `Helm chart '${params.name}' uninstalled successfully from namespace '${params.namespace}'`,
421
+ }),
422
+ },
423
+ ],
403
424
  };
404
425
  }
405
426
  catch (error) {
@@ -409,10 +430,10 @@ export async function uninstallHelmChart(params) {
409
430
  type: "text",
410
431
  text: JSON.stringify({
411
432
  status: "failed",
412
- error: `Failed to uninstall Helm chart: ${error.message}`
413
- })
414
- }
415
- ]
433
+ error: `Failed to uninstall Helm chart: ${error.message}`,
434
+ }),
435
+ },
436
+ ],
416
437
  };
417
438
  }
418
439
  }
@@ -2,6 +2,9 @@ import { KubernetesManager } from "../types.js";
2
2
  export declare const kubectlContextSchema: {
3
3
  readonly name: "kubectl_context";
4
4
  readonly description: "Manage Kubernetes contexts - list, get, or set the current context";
5
+ readonly annotations: {
6
+ readonly readOnlyHint: true;
7
+ };
5
8
  readonly inputSchema: {
6
9
  readonly type: "object";
7
10
  readonly properties: {
@@ -4,6 +4,9 @@ import { getSpawnMaxBuffer } from "../config/max-buffer.js";
4
4
  export const kubectlContextSchema = {
5
5
  name: "kubectl_context",
6
6
  description: "Manage Kubernetes contexts - list, get, or set the current context",
7
+ annotations: {
8
+ readOnlyHint: true,
9
+ },
7
10
  inputSchema: {
8
11
  type: "object",
9
12
  properties: {
@@ -67,7 +70,11 @@ export async function kubectlContext(k8sManager, input) {
67
70
  const clusterPos = headerLine.indexOf("CLUSTER");
68
71
  const authInfoPos = headerLine.indexOf("AUTHINFO");
69
72
  const namespacePos = headerLine.indexOf("NAMESPACE");
70
- if (currentPos === -1 || namePos === -1 || clusterPos === -1 || authInfoPos === -1 || namespacePos === -1) {
73
+ if (currentPos === -1 ||
74
+ namePos === -1 ||
75
+ clusterPos === -1 ||
76
+ authInfoPos === -1 ||
77
+ namespacePos === -1) {
71
78
  throw new McpError(ErrorCode.InvalidParams, "Invalid kubectl output format");
72
79
  }
73
80
  const contexts = [];
@@ -2,6 +2,9 @@ import { KubernetesManager } from "../types.js";
2
2
  export declare const kubectlDeleteSchema: {
3
3
  readonly name: "kubectl_delete";
4
4
  readonly description: "Delete Kubernetes resources by resource type, name, labels, or from a manifest file";
5
+ readonly annotations: {
6
+ readonly destructiveHint: true;
7
+ };
5
8
  readonly inputSchema: {
6
9
  readonly type: "object";
7
10
  readonly properties: {
@@ -4,10 +4,13 @@ import * as fs from "fs";
4
4
  import * as path from "path";
5
5
  import * as os from "os";
6
6
  import { getSpawnMaxBuffer } from "../config/max-buffer.js";
7
- import { contextParameter, namespaceParameter } from "../models/common-parameters.js";
7
+ import { contextParameter, namespaceParameter, } from "../models/common-parameters.js";
8
8
  export const kubectlDeleteSchema = {
9
9
  name: "kubectl_delete",
10
10
  description: "Delete Kubernetes resources by resource type, name, labels, or from a manifest file",
11
+ annotations: {
12
+ destructiveHint: true,
13
+ },
11
14
  inputSchema: {
12
15
  type: "object",
13
16
  properties: {
@@ -2,6 +2,9 @@ import { KubernetesManager } from "../types.js";
2
2
  export declare const kubectlDescribeSchema: {
3
3
  readonly name: "kubectl_describe";
4
4
  readonly description: "Describe Kubernetes resources by resource type, name, and optionally namespace";
5
+ readonly annotations: {
6
+ readonly readOnlyHint: true;
7
+ };
5
8
  readonly inputSchema: {
6
9
  readonly type: "object";
7
10
  readonly properties: {
@@ -1,10 +1,13 @@
1
1
  import { execFileSync } from "child_process";
2
2
  import { McpError, ErrorCode } from "@modelcontextprotocol/sdk/types.js";
3
3
  import { getSpawnMaxBuffer } from "../config/max-buffer.js";
4
- import { namespaceParameter, contextParameter } from "../models/common-parameters.js";
4
+ import { namespaceParameter, contextParameter, } from "../models/common-parameters.js";
5
5
  export const kubectlDescribeSchema = {
6
6
  name: "kubectl_describe",
7
7
  description: "Describe Kubernetes resources by resource type, name, and optionally namespace",
8
+ annotations: {
9
+ readOnlyHint: true,
10
+ },
8
11
  inputSchema: {
9
12
  type: "object",
10
13
  properties: {
@@ -2,6 +2,9 @@ import { KubernetesManager } from "../types.js";
2
2
  export declare const kubectlGenericSchema: {
3
3
  name: string;
4
4
  description: string;
5
+ annotations: {
6
+ destructiveHint: boolean;
7
+ };
5
8
  inputSchema: {
6
9
  type: string;
7
10
  properties: {
@@ -1,10 +1,13 @@
1
1
  import { execFileSync } from "child_process";
2
2
  import { McpError, ErrorCode } from "@modelcontextprotocol/sdk/types.js";
3
3
  import { getSpawnMaxBuffer } from "../config/max-buffer.js";
4
- import { contextParameter, namespaceParameter } from "../models/common-parameters.js";
4
+ import { contextParameter, namespaceParameter, } from "../models/common-parameters.js";
5
5
  export const kubectlGenericSchema = {
6
6
  name: "kubectl_generic",
7
7
  description: "Execute any kubectl command with the provided arguments and flags",
8
+ annotations: {
9
+ destructiveHint: true,
10
+ },
8
11
  inputSchema: {
9
12
  type: "object",
10
13
  properties: {
@@ -2,6 +2,9 @@ import { KubernetesManager } from "../types.js";
2
2
  export declare const kubectlGetSchema: {
3
3
  readonly name: "kubectl_get";
4
4
  readonly description: "Get or list Kubernetes resources by resource type, name, and optionally namespace";
5
+ readonly annotations: {
6
+ readonly readOnlyHint: true;
7
+ };
5
8
  readonly inputSchema: {
6
9
  readonly type: "object";
7
10
  readonly properties: {
@@ -2,10 +2,13 @@ import { execFileSync } from "child_process";
2
2
  import { McpError, ErrorCode } from "@modelcontextprotocol/sdk/types.js";
3
3
  import { getSpawnMaxBuffer } from "../config/max-buffer.js";
4
4
  import * as yaml from "js-yaml";
5
- import { contextParameter, namespaceParameter } from "../models/common-parameters.js";
5
+ import { contextParameter, namespaceParameter, } from "../models/common-parameters.js";
6
6
  export const kubectlGetSchema = {
7
7
  name: "kubectl_get",
8
8
  description: "Get or list Kubernetes resources by resource type, name, and optionally namespace",
9
+ annotations: {
10
+ readOnlyHint: true,
11
+ },
9
12
  inputSchema: {
10
13
  type: "object",
11
14
  properties: {
@@ -41,7 +44,7 @@ export const kubectlGetSchema = {
41
44
  type: "string",
42
45
  description: "Sort events by a field (default: lastTimestamp). Only applicable for events.",
43
46
  },
44
- context: contextParameter
47
+ context: contextParameter,
45
48
  },
46
49
  required: ["resourceType", "name", "namespace"],
47
50
  },
@@ -282,7 +285,7 @@ function maskDataValues(obj) {
282
285
  return obj;
283
286
  }
284
287
  if (Array.isArray(obj)) {
285
- return obj.map(item => maskDataValues(item));
288
+ return obj.map((item) => maskDataValues(item));
286
289
  }
287
290
  if (typeof obj === "object") {
288
291
  const result = {};
@@ -311,7 +314,7 @@ function maskAllLeafValues(obj) {
311
314
  return obj;
312
315
  }
313
316
  if (Array.isArray(obj)) {
314
- return obj.map(item => maskAllLeafValues(item));
317
+ return obj.map((item) => maskAllLeafValues(item));
315
318
  }
316
319
  if (typeof obj === "object") {
317
320
  const result = {};
@@ -345,7 +348,7 @@ function maskSecretsData(output, format) {
345
348
  return yaml.dump(masked, {
346
349
  indent: 2,
347
350
  lineWidth: -1, // Don't wrap lines
348
- noRefs: true // Don't use references
351
+ noRefs: true, // Don't use references
349
352
  });
350
353
  }
351
354
  }
@@ -2,6 +2,9 @@ import { KubernetesManager } from "../types.js";
2
2
  export declare const kubectlLogsSchema: {
3
3
  readonly name: "kubectl_logs";
4
4
  readonly description: "Get logs from Kubernetes resources like pods, deployments, or jobs";
5
+ readonly annotations: {
6
+ readonly readOnlyHint: true;
7
+ };
5
8
  readonly inputSchema: {
6
9
  readonly type: "object";
7
10
  readonly properties: {
@@ -1,10 +1,13 @@
1
1
  import { execFileSync } from "child_process";
2
2
  import { McpError, ErrorCode } from "@modelcontextprotocol/sdk/types.js";
3
3
  import { getSpawnMaxBuffer } from "../config/max-buffer.js";
4
- import { contextParameter, namespaceParameter } from "../models/common-parameters.js";
4
+ import { contextParameter, namespaceParameter, } from "../models/common-parameters.js";
5
5
  export const kubectlLogsSchema = {
6
6
  name: "kubectl_logs",
7
7
  description: "Get logs from Kubernetes resources like pods, deployments, or jobs",
8
+ annotations: {
9
+ readOnlyHint: true,
10
+ },
8
11
  inputSchema: {
9
12
  type: "object",
10
13
  properties: {
@@ -2,6 +2,9 @@ import { ExplainResourceParams, ListApiResourcesParams } from "../models/kubectl
2
2
  export declare const explainResourceSchema: {
3
3
  name: string;
4
4
  description: string;
5
+ annotations: {
6
+ readOnlyHint: boolean;
7
+ };
5
8
  inputSchema: {
6
9
  type: string;
7
10
  properties: {
@@ -36,6 +39,9 @@ export declare const explainResourceSchema: {
36
39
  export declare const listApiResourcesSchema: {
37
40
  name: string;
38
41
  description: string;
42
+ annotations: {
43
+ readOnlyHint: boolean;
44
+ };
39
45
  inputSchema: {
40
46
  type: string;
41
47
  properties: {
@@ -4,6 +4,9 @@ import { contextParameter } from "../models/common-parameters.js";
4
4
  export const explainResourceSchema = {
5
5
  name: "explain_resource",
6
6
  description: "Get documentation for a Kubernetes resource or field",
7
+ annotations: {
8
+ readOnlyHint: true,
9
+ },
7
10
  inputSchema: {
8
11
  type: "object",
9
12
  properties: {
@@ -34,6 +37,9 @@ export const explainResourceSchema = {
34
37
  export const listApiResourcesSchema = {
35
38
  name: "list_api_resources",
36
39
  description: "List the API resources available in the cluster",
40
+ annotations: {
41
+ readOnlyHint: true,
42
+ },
37
43
  inputSchema: {
38
44
  type: "object",
39
45
  properties: {
@@ -20,6 +20,9 @@
20
20
  export declare const nodeManagementSchema: {
21
21
  name: string;
22
22
  description: string;
23
+ annotations: {
24
+ destructiveHint: boolean;
25
+ };
23
26
  inputSchema: {
24
27
  type: string;
25
28
  properties: {
@@ -22,6 +22,9 @@ import { getSpawnMaxBuffer } from "../config/max-buffer.js";
22
22
  export const nodeManagementSchema = {
23
23
  name: "node_management",
24
24
  description: "Manage Kubernetes nodes with cordon, drain, and uncordon operations",
25
+ annotations: {
26
+ destructiveHint: true,
27
+ },
25
28
  inputSchema: {
26
29
  type: "object",
27
30
  properties: {
@@ -101,7 +104,13 @@ const executeCommand = (command, args) => {
101
104
  */
102
105
  const getNodeStatus = (nodeName) => {
103
106
  try {
104
- const output = executeCommand("kubectl", ["get", "node", nodeName, "-o", "json"]);
107
+ const output = executeCommand("kubectl", [
108
+ "get",
109
+ "node",
110
+ nodeName,
111
+ "-o",
112
+ "json",
113
+ ]);
105
114
  return JSON.parse(output);
106
115
  }
107
116
  catch (error) {
@@ -115,7 +124,7 @@ const getNodeStatus = (nodeName) => {
115
124
  * @returns Promise with operation results
116
125
  */
117
126
  export async function nodeManagement(params) {
118
- const { operation, nodeName, force = false, gracePeriod = -1, deleteLocalData = false, ignoreDaemonsets = true, timeout = "0", dryRun = false, confirmDrain = false } = params;
127
+ const { operation, nodeName, force = false, gracePeriod = -1, deleteLocalData = false, ignoreDaemonsets = true, timeout = "0", dryRun = false, confirmDrain = false, } = params;
119
128
  try {
120
129
  switch (operation) {
121
130
  case "cordon":
@@ -131,7 +140,7 @@ export async function nodeManagement(params) {
131
140
  ignoreDaemonsets,
132
141
  timeout,
133
142
  dryRun,
134
- confirmDrain
143
+ confirmDrain,
135
144
  });
136
145
  default:
137
146
  throw new Error(`Unknown operation: ${operation}`);
@@ -142,9 +151,9 @@ export async function nodeManagement(params) {
142
151
  content: [
143
152
  {
144
153
  type: "text",
145
- text: `Node management operation failed: ${error.message}`
146
- }
147
- ]
154
+ text: `Node management operation failed: ${error.message}`,
155
+ },
156
+ ],
148
157
  };
149
158
  }
150
159
  }
@@ -163,9 +172,9 @@ async function handleCordonNode(nodeName) {
163
172
  content: [
164
173
  {
165
174
  type: "text",
166
- text: `Node '${nodeName}' is already cordoned (unschedulable)`
167
- }
168
- ]
175
+ text: `Node '${nodeName}' is already cordoned (unschedulable)`,
176
+ },
177
+ ],
169
178
  };
170
179
  }
171
180
  // Cordon the node
@@ -174,9 +183,9 @@ async function handleCordonNode(nodeName) {
174
183
  content: [
175
184
  {
176
185
  type: "text",
177
- text: `Successfully cordoned node '${nodeName}'. The node is now unschedulable.`
178
- }
179
- ]
186
+ text: `Successfully cordoned node '${nodeName}'. The node is now unschedulable.`,
187
+ },
188
+ ],
180
189
  };
181
190
  }
182
191
  catch (error) {
@@ -198,9 +207,9 @@ async function handleUncordonNode(nodeName) {
198
207
  content: [
199
208
  {
200
209
  type: "text",
201
- text: `Node '${nodeName}' is already uncordoned (schedulable)`
202
- }
203
- ]
210
+ text: `Node '${nodeName}' is already uncordoned (schedulable)`,
211
+ },
212
+ ],
204
213
  };
205
214
  }
206
215
  // Uncordon the node
@@ -209,9 +218,9 @@ async function handleUncordonNode(nodeName) {
209
218
  content: [
210
219
  {
211
220
  type: "text",
212
- text: `Successfully uncordoned node '${nodeName}'. The node is now schedulable.`
213
- }
214
- ]
221
+ text: `Successfully uncordoned node '${nodeName}'. The node is now schedulable.`,
222
+ },
223
+ ],
215
224
  };
216
225
  }
217
226
  catch (error) {
@@ -224,7 +233,7 @@ async function handleUncordonNode(nodeName) {
224
233
  * @returns Promise with drain operation results
225
234
  */
226
235
  async function handleDrainNode(params) {
227
- const { nodeName, force, gracePeriod, deleteLocalData, ignoreDaemonsets, timeout, dryRun, confirmDrain } = params;
236
+ const { nodeName, force, gracePeriod, deleteLocalData, ignoreDaemonsets, timeout, dryRun, confirmDrain, } = params;
228
237
  try {
229
238
  // Check if node exists and get current status
230
239
  const nodeStatus = getNodeStatus(nodeName);
@@ -234,9 +243,9 @@ async function handleDrainNode(params) {
234
243
  content: [
235
244
  {
236
245
  type: "text",
237
- text: `Node '${nodeName}' is already cordoned (unschedulable). Drain operation may not be necessary.`
238
- }
239
- ]
246
+ text: `Node '${nodeName}' is already cordoned (unschedulable). Drain operation may not be necessary.`,
247
+ },
248
+ ],
240
249
  };
241
250
  }
242
251
  // Check for confirmation if not in dry run mode
@@ -245,9 +254,9 @@ async function handleDrainNode(params) {
245
254
  content: [
246
255
  {
247
256
  type: "text",
248
- text: `Drain operation requires explicit confirmation. Set confirmDrain=true to proceed with draining node '${nodeName}'.`
249
- }
250
- ]
257
+ text: `Drain operation requires explicit confirmation. Set confirmDrain=true to proceed with draining node '${nodeName}'.`,
258
+ },
259
+ ],
251
260
  };
252
261
  }
253
262
  // Build drain command arguments
@@ -271,18 +280,18 @@ async function handleDrainNode(params) {
271
280
  content: [
272
281
  {
273
282
  type: "text",
274
- text: `Dry run drain operation for node '${nodeName}':\n\n${drainOutput}\n\nTo perform the actual drain, set dryRun=false and confirmDrain=true.`
275
- }
276
- ]
283
+ text: `Dry run drain operation for node '${nodeName}':\n\n${drainOutput}\n\nTo perform the actual drain, set dryRun=false and confirmDrain=true.`,
284
+ },
285
+ ],
277
286
  };
278
287
  }
279
288
  return {
280
289
  content: [
281
290
  {
282
291
  type: "text",
283
- text: `Successfully drained node '${nodeName}'.\n\n${drainOutput}`
284
- }
285
- ]
292
+ text: `Successfully drained node '${nodeName}'.\n\n${drainOutput}`,
293
+ },
294
+ ],
286
295
  };
287
296
  }
288
297
  catch (error) {
@@ -6,5 +6,8 @@ export declare const pingSchema: {
6
6
  properties: {};
7
7
  required: never[];
8
8
  };
9
+ annotations: {
10
+ readOnlyHint: boolean;
11
+ };
9
12
  };
10
13
  export declare function ping(): Promise<Record<string, never>>;
@@ -6,6 +6,9 @@ export const pingSchema = {
6
6
  properties: {},
7
7
  required: [],
8
8
  },
9
+ annotations: {
10
+ readOnlyHint: true,
11
+ },
9
12
  };
10
13
  export async function ping() {
11
14
  return {};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "mcp-server-kubernetes",
3
- "version": "2.9.2",
3
+ "version": "2.9.3",
4
4
  "description": "MCP server for interacting with Kubernetes clusters via kubectl",
5
5
  "license": "MIT",
6
6
  "type": "module",