<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Kagent on DK Blog</title><link>/tags/kagent/</link><description>Recent content in Kagent on DK Blog</description><generator>Hugo -- gohugo.io</generator><language>zh-CN</language><lastBuildDate>Thu, 13 Nov 2025 21:34:00 +0800</lastBuildDate><atom:link href="/tags/kagent/index.xml" rel="self" type="application/rss+xml"/><item><title>kagent：在 Kubernetes 里跑一个完整的 AI Agent Case</title><link>/dkblog/023-kagent-kubernetes-ai-agent/</link><pubDate>Thu, 13 Nov 2025 21:34:00 +0800</pubDate><guid>/dkblog/023-kagent-kubernetes-ai-agent/</guid><description>&lt;img src="https://images.unsplash.com/photo-1544197150-b99a580bb7a8?auto=format&amp;fit=crop&amp;w=900&amp;q=60" alt="Featured image of post kagent：在 Kubernetes 里跑一个完整的 AI Agent Case" /&gt;&lt;p&gt;前面看 kagent 的时候，我只把它当成一个 Kubernetes native 的 Agent 框架来理解。后来再翻官方文档，发现更值得记录的是完整落地链路：CRD 怎么装，controller 怎么起来，模型配置怎么声明，MCPServer 怎么接进来，最后 Agent 怎么引用这些东西。&lt;/p&gt;
&lt;p&gt;这篇就按一个完整 case 记下来。目标不是让 agent 直接改生产集群，而是先做一个低风险的“集群观察 + 网页 fetch”助手：&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;可以调用 kagent 内置 Kubernetes 工具查资源。&lt;/li&gt;
&lt;li&gt;可以通过一个 MCPServer 抓取网页内容。&lt;/li&gt;
&lt;li&gt;Agent 使用显式的 &lt;code&gt;ModelConfig&lt;/code&gt;。&lt;/li&gt;
&lt;li&gt;所有对象都用 YAML 表达，方便放进 GitOps。&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="这个-case-里会出现哪些对象"&gt;&lt;a href="#%e8%bf%99%e4%b8%aa-case-%e9%87%8c%e4%bc%9a%e5%87%ba%e7%8e%b0%e5%93%aa%e4%ba%9b%e5%af%b9%e8%b1%a1" class="header-anchor"&gt;&lt;/a&gt;这个 case 里会出现哪些对象
&lt;/h2&gt;&lt;p&gt;先把关系画清楚：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-0-1"&gt;&lt;a class="lnlinks" href="#hl-0-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-0-2"&gt;&lt;a class="lnlinks" href="#hl-0-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-0-3"&gt;&lt;a class="lnlinks" href="#hl-0-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-0-4"&gt;&lt;a class="lnlinks" href="#hl-0-4"&gt;4&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-0-5"&gt;&lt;a class="lnlinks" href="#hl-0-5"&gt;5&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-0-6"&gt;&lt;a class="lnlinks" href="#hl-0-6"&gt;6&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-0-7"&gt;&lt;a class="lnlinks" href="#hl-0-7"&gt;7&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-0-8"&gt;&lt;a class="lnlinks" href="#hl-0-8"&gt;8&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-text" data-lang="text"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;Secret
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; -&amp;gt; ModelConfig
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; -&amp;gt; Agent
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; -&amp;gt; RemoteMCPServer: kagent-tool-server
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; -&amp;gt; MCPServer: mcp-website-fetcher
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kagent CRDs + kagent controller
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kmcp CRDs + kmcp controller
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;这里有两个容易混的对象：&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;RemoteMCPServer&lt;/code&gt;：kagent 里用来描述远程 MCP 服务的资源，内置的 &lt;code&gt;kagent-tool-server&lt;/code&gt; 就属于这一类。&lt;/li&gt;
&lt;li&gt;&lt;code&gt;MCPServer&lt;/code&gt;：kmcp 管理的 MCP server 资源，可以把一个 stdio MCP server 包成 Kubernetes 里的服务。&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;官方文档里的 First MCP Tool 示例就是用 &lt;code&gt;MCPServer&lt;/code&gt; 起了一个 fetch 工具，然后 Agent 通过 &lt;code&gt;tools&lt;/code&gt; 引用它。&lt;/p&gt;
&lt;h2 id="1-安装-crd-和-controller"&gt;&lt;a href="#1-%e5%ae%89%e8%a3%85-crd-%e5%92%8c-controller" class="header-anchor"&gt;&lt;/a&gt;1. 安装 CRD 和 controller
&lt;/h2&gt;&lt;p&gt;我更偏向用 Helm 装，因为这套东西更适合放到平台环境里，不只是本地 demo。&lt;/p&gt;
&lt;p&gt;先装 kagent CRD：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-1-1"&gt;&lt;a class="lnlinks" href="#hl-1-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-1-2"&gt;&lt;a class="lnlinks" href="#hl-1-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-1-3"&gt;&lt;a class="lnlinks" href="#hl-1-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;helm install kagent-crds oci://ghcr.io/kagent-dev/kagent/helm/kagent-crds &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --namespace kagent &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --create-namespace
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;再装 kagent controller 和 UI。这里用 OpenAI provider 举例，实际项目里可以换 Anthropic、Gemini、Azure OpenAI、Ollama 等。&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-2-1"&gt;&lt;a class="lnlinks" href="#hl-2-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-2-2"&gt;&lt;a class="lnlinks" href="#hl-2-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-2-3"&gt;&lt;a class="lnlinks" href="#hl-2-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-2-4"&gt;&lt;a class="lnlinks" href="#hl-2-4"&gt;4&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-2-5"&gt;&lt;a class="lnlinks" href="#hl-2-5"&gt;5&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-2-6"&gt;&lt;a class="lnlinks" href="#hl-2-6"&gt;6&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nb"&gt;export&lt;/span&gt; &lt;span class="nv"&gt;OPENAI_API_KEY&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;your-api-key&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;helm install kagent oci://ghcr.io/kagent-dev/kagent/helm/kagent &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --namespace kagent &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --set providers.default&lt;span class="o"&gt;=&lt;/span&gt;openAI &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --set providers.openAI.apiKey&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;&lt;/span&gt;&lt;span class="nv"&gt;$OPENAI_API_KEY&lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;官方安装文档里提到，kagent 0.7 之后默认包含 kmcp 子项目。如果你已经单独装了 kmcp，可以通过 chart 配置关掉内置 kmcp。对第一次试用来说，先用默认就行。&lt;/p&gt;
&lt;p&gt;确认 CRD 和 controller：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-3-1"&gt;&lt;a class="lnlinks" href="#hl-3-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-3-2"&gt;&lt;a class="lnlinks" href="#hl-3-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-3-3"&gt;&lt;a class="lnlinks" href="#hl-3-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-3-4"&gt;&lt;a class="lnlinks" href="#hl-3-4"&gt;4&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get crd &lt;span class="p"&gt;|&lt;/span&gt; grep kagent.dev
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get pods -n kagent
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get svc -n kagent
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;如果要单独安装 kmcp controller，官方文档给的是这条线：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-4-1"&gt;&lt;a class="lnlinks" href="#hl-4-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-4-2"&gt;&lt;a class="lnlinks" href="#hl-4-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-4-3"&gt;&lt;a class="lnlinks" href="#hl-4-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-4-4"&gt;&lt;a class="lnlinks" href="#hl-4-4"&gt;4&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-4-5"&gt;&lt;a class="lnlinks" href="#hl-4-5"&gt;5&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-4-6"&gt;&lt;a class="lnlinks" href="#hl-4-6"&gt;6&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-4-7"&gt;&lt;a class="lnlinks" href="#hl-4-7"&gt;7&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-4-8"&gt;&lt;a class="lnlinks" href="#hl-4-8"&gt;8&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;helm install kmcp-crds oci://ghcr.io/kagent-dev/kmcp/helm/kmcp-crds &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --namespace kmcp-system &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --create-namespace
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kmcp install
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get pods -n kmcp-system
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl logs -l app.kubernetes.io/name&lt;span class="o"&gt;=&lt;/span&gt;kmcp -n kmcp-system
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;这里要注意：不要在同一个集群里重复装两套 kmcp controller。要么用 kagent 默认带的，要么明确自己单独安装并在 kagent chart 里关掉。&lt;/p&gt;
&lt;h2 id="2-准备模型-secret-和-modelconfig"&gt;&lt;a href="#2-%e5%87%86%e5%a4%87%e6%a8%a1%e5%9e%8b-secret-%e5%92%8c-modelconfig" class="header-anchor"&gt;&lt;/a&gt;2. 准备模型 Secret 和 ModelConfig
&lt;/h2&gt;&lt;p&gt;Helm 安装时如果设置了 provider，通常会带默认配置。为了把流程讲完整，我这里单独写一个 &lt;code&gt;ModelConfig&lt;/code&gt;，后续 Agent 明确引用它。&lt;/p&gt;
&lt;p&gt;先创建 API key secret：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-5-1"&gt;&lt;a class="lnlinks" href="#hl-5-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-5-2"&gt;&lt;a class="lnlinks" href="#hl-5-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl -n kagent create secret generic openai-api-key &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --from-literal&lt;span class="o"&gt;=&lt;/span&gt;api-key&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;&lt;/span&gt;&lt;span class="nv"&gt;$OPENAI_API_KEY&lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;然后创建 &lt;code&gt;ModelConfig&lt;/code&gt;：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-6-1"&gt;&lt;a class="lnlinks" href="#hl-6-1"&gt; 1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-2"&gt;&lt;a class="lnlinks" href="#hl-6-2"&gt; 2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-3"&gt;&lt;a class="lnlinks" href="#hl-6-3"&gt; 3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-4"&gt;&lt;a class="lnlinks" href="#hl-6-4"&gt; 4&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-5"&gt;&lt;a class="lnlinks" href="#hl-6-5"&gt; 5&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-6"&gt;&lt;a class="lnlinks" href="#hl-6-6"&gt; 6&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-7"&gt;&lt;a class="lnlinks" href="#hl-6-7"&gt; 7&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-8"&gt;&lt;a class="lnlinks" href="#hl-6-8"&gt; 8&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-9"&gt;&lt;a class="lnlinks" href="#hl-6-9"&gt; 9&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-10"&gt;&lt;a class="lnlinks" href="#hl-6-10"&gt;10&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-11"&gt;&lt;a class="lnlinks" href="#hl-6-11"&gt;11&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-12"&gt;&lt;a class="lnlinks" href="#hl-6-12"&gt;12&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-13"&gt;&lt;a class="lnlinks" href="#hl-6-13"&gt;13&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-6-14"&gt;&lt;a class="lnlinks" href="#hl-6-14"&gt;14&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-yaml" data-lang="yaml"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;apiVersion&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;kagent.dev/v1alpha2&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;kind&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;ModelConfig&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;metadata&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;ops-openai-model&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;namespace&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;kagent&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;spec&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;provider&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;OpenAI&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;model&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;&amp;lt;your-openai-model&amp;gt;&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;apiKeySecret&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;openai-api-key&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;apiKeySecretKey&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;api-key&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;openAI&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;temperature&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;0.2&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;maxTokens&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="m"&gt;2048&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;timeout&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="m"&gt;60&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;我这里把 &lt;code&gt;model&lt;/code&gt; 写成占位符，是因为不同账号、网关或代理支持的模型可能不一样。实际落地时要改成你环境里可用的模型名。&lt;/p&gt;
&lt;p&gt;应用并检查：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-7-1"&gt;&lt;a class="lnlinks" href="#hl-7-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-7-2"&gt;&lt;a class="lnlinks" href="#hl-7-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-7-3"&gt;&lt;a class="lnlinks" href="#hl-7-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-7-4"&gt;&lt;a class="lnlinks" href="#hl-7-4"&gt;4&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl apply -f modelconfig.yaml
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get modelconfig -n kagent
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl describe modelconfig ops-openai-model -n kagent
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;&lt;code&gt;ModelConfig&lt;/code&gt; 里有几个字段比较关键：&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;provider&lt;/code&gt;：模型提供方，API 里支持 OpenAI、Anthropic、AzureOpenAI、Ollama、Gemini、Bedrock 等。&lt;/li&gt;
&lt;li&gt;&lt;code&gt;model&lt;/code&gt;：具体模型名。&lt;/li&gt;
&lt;li&gt;&lt;code&gt;apiKeySecret&lt;/code&gt; / &lt;code&gt;apiKeySecretKey&lt;/code&gt;：引用同 namespace 里的 Secret。&lt;/li&gt;
&lt;li&gt;&lt;code&gt;openAI&lt;/code&gt;：OpenAI provider 的额外参数，比如 temperature、maxTokens、timeout。&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;这个对象的价值是把模型配置从 Agent 里拆出来。多个 Agent 可以引用同一个 &lt;code&gt;ModelConfig&lt;/code&gt;，模型切换也更清楚。&lt;/p&gt;
&lt;h2 id="3-创建一个-mcpserver网页-fetch-工具"&gt;&lt;a href="#3-%e5%88%9b%e5%bb%ba%e4%b8%80%e4%b8%aa-mcpserver%e7%bd%91%e9%a1%b5-fetch-%e5%b7%a5%e5%85%b7" class="header-anchor"&gt;&lt;/a&gt;3. 创建一个 MCPServer：网页 fetch 工具
&lt;/h2&gt;&lt;p&gt;接下来创建一个最小 MCPServer。官方 First MCP Tool 文档里用的是 &lt;code&gt;mcp-server-fetch&lt;/code&gt;，通过 &lt;code&gt;uvx&lt;/code&gt; 启动 stdio MCP server，再由 kmcp controller 管理它的生命周期。&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-8-1"&gt;&lt;a class="lnlinks" href="#hl-8-1"&gt; 1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-2"&gt;&lt;a class="lnlinks" href="#hl-8-2"&gt; 2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-3"&gt;&lt;a class="lnlinks" href="#hl-8-3"&gt; 3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-4"&gt;&lt;a class="lnlinks" href="#hl-8-4"&gt; 4&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-5"&gt;&lt;a class="lnlinks" href="#hl-8-5"&gt; 5&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-6"&gt;&lt;a class="lnlinks" href="#hl-8-6"&gt; 6&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-7"&gt;&lt;a class="lnlinks" href="#hl-8-7"&gt; 7&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-8"&gt;&lt;a class="lnlinks" href="#hl-8-8"&gt; 8&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-9"&gt;&lt;a class="lnlinks" href="#hl-8-9"&gt; 9&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-10"&gt;&lt;a class="lnlinks" href="#hl-8-10"&gt;10&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-11"&gt;&lt;a class="lnlinks" href="#hl-8-11"&gt;11&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-12"&gt;&lt;a class="lnlinks" href="#hl-8-12"&gt;12&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-8-13"&gt;&lt;a class="lnlinks" href="#hl-8-13"&gt;13&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-yaml" data-lang="yaml"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;apiVersion&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;kagent.dev/v1alpha1&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;kind&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;MCPServer&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;metadata&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;mcp-website-fetcher&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;namespace&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;kagent&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;spec&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;deployment&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;cmd&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;uvx&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;args&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="l"&gt;mcp-server-fetch&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="m"&gt;3000&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;stdioTransport&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{}&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;transportType&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;stdio&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;应用：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-9-1"&gt;&lt;a class="lnlinks" href="#hl-9-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl apply -f mcp-website-fetcher.yaml
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;检查状态：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-10-1"&gt;&lt;a class="lnlinks" href="#hl-10-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-10-2"&gt;&lt;a class="lnlinks" href="#hl-10-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-10-3"&gt;&lt;a class="lnlinks" href="#hl-10-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-10-4"&gt;&lt;a class="lnlinks" href="#hl-10-4"&gt;4&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get mcpserver -n kagent
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl describe mcpserver mcp-website-fetcher -n kagent
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get pods -n kagent &lt;span class="p"&gt;|&lt;/span&gt; grep mcp-website-fetcher
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;如果 MCPServer 没起来，我会先看 kmcp controller 日志，而不是直接怀疑 Agent：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-11-1"&gt;&lt;a class="lnlinks" href="#hl-11-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl logs -l app.kubernetes.io/name&lt;span class="o"&gt;=&lt;/span&gt;kmcp -n kmcp-system
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;如果你用的是 kagent chart 内置 kmcp，controller 的 namespace 和 label 可能跟独立安装不同，直接用下面的方式先找：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-12-1"&gt;&lt;a class="lnlinks" href="#hl-12-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-12-2"&gt;&lt;a class="lnlinks" href="#hl-12-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get pods -A &lt;span class="p"&gt;|&lt;/span&gt; grep -i kmcp
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get deploy -A &lt;span class="p"&gt;|&lt;/span&gt; grep -i kmcp
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;h2 id="4-创建-agent同时引用-kubernetes-工具和-fetch-工具"&gt;&lt;a href="#4-%e5%88%9b%e5%bb%ba-agent%e5%90%8c%e6%97%b6%e5%bc%95%e7%94%a8-kubernetes-%e5%b7%a5%e5%85%b7%e5%92%8c-fetch-%e5%b7%a5%e5%85%b7" class="header-anchor"&gt;&lt;/a&gt;4. 创建 Agent：同时引用 Kubernetes 工具和 fetch 工具
&lt;/h2&gt;&lt;p&gt;现在创建 Agent。这个 Agent 做两件事：&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;用内置 &lt;code&gt;kagent-tool-server&lt;/code&gt; 查 Kubernetes 资源。&lt;/li&gt;
&lt;li&gt;用刚才的 &lt;code&gt;mcp-website-fetcher&lt;/code&gt; 抓网页内容。&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-13-1"&gt;&lt;a class="lnlinks" href="#hl-13-1"&gt; 1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-2"&gt;&lt;a class="lnlinks" href="#hl-13-2"&gt; 2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-3"&gt;&lt;a class="lnlinks" href="#hl-13-3"&gt; 3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-4"&gt;&lt;a class="lnlinks" href="#hl-13-4"&gt; 4&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-5"&gt;&lt;a class="lnlinks" href="#hl-13-5"&gt; 5&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-6"&gt;&lt;a class="lnlinks" href="#hl-13-6"&gt; 6&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-7"&gt;&lt;a class="lnlinks" href="#hl-13-7"&gt; 7&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-8"&gt;&lt;a class="lnlinks" href="#hl-13-8"&gt; 8&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-9"&gt;&lt;a class="lnlinks" href="#hl-13-9"&gt; 9&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-10"&gt;&lt;a class="lnlinks" href="#hl-13-10"&gt;10&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-11"&gt;&lt;a class="lnlinks" href="#hl-13-11"&gt;11&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-12"&gt;&lt;a class="lnlinks" href="#hl-13-12"&gt;12&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-13"&gt;&lt;a class="lnlinks" href="#hl-13-13"&gt;13&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-14"&gt;&lt;a class="lnlinks" href="#hl-13-14"&gt;14&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-15"&gt;&lt;a class="lnlinks" href="#hl-13-15"&gt;15&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-16"&gt;&lt;a class="lnlinks" href="#hl-13-16"&gt;16&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-17"&gt;&lt;a class="lnlinks" href="#hl-13-17"&gt;17&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-18"&gt;&lt;a class="lnlinks" href="#hl-13-18"&gt;18&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-19"&gt;&lt;a class="lnlinks" href="#hl-13-19"&gt;19&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-20"&gt;&lt;a class="lnlinks" href="#hl-13-20"&gt;20&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-21"&gt;&lt;a class="lnlinks" href="#hl-13-21"&gt;21&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-22"&gt;&lt;a class="lnlinks" href="#hl-13-22"&gt;22&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-23"&gt;&lt;a class="lnlinks" href="#hl-13-23"&gt;23&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-24"&gt;&lt;a class="lnlinks" href="#hl-13-24"&gt;24&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-25"&gt;&lt;a class="lnlinks" href="#hl-13-25"&gt;25&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-26"&gt;&lt;a class="lnlinks" href="#hl-13-26"&gt;26&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-27"&gt;&lt;a class="lnlinks" href="#hl-13-27"&gt;27&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-28"&gt;&lt;a class="lnlinks" href="#hl-13-28"&gt;28&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-29"&gt;&lt;a class="lnlinks" href="#hl-13-29"&gt;29&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-30"&gt;&lt;a class="lnlinks" href="#hl-13-30"&gt;30&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-31"&gt;&lt;a class="lnlinks" href="#hl-13-31"&gt;31&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-32"&gt;&lt;a class="lnlinks" href="#hl-13-32"&gt;32&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-33"&gt;&lt;a class="lnlinks" href="#hl-13-33"&gt;33&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-34"&gt;&lt;a class="lnlinks" href="#hl-13-34"&gt;34&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-35"&gt;&lt;a class="lnlinks" href="#hl-13-35"&gt;35&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-36"&gt;&lt;a class="lnlinks" href="#hl-13-36"&gt;36&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-37"&gt;&lt;a class="lnlinks" href="#hl-13-37"&gt;37&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-38"&gt;&lt;a class="lnlinks" href="#hl-13-38"&gt;38&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-39"&gt;&lt;a class="lnlinks" href="#hl-13-39"&gt;39&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-40"&gt;&lt;a class="lnlinks" href="#hl-13-40"&gt;40&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-41"&gt;&lt;a class="lnlinks" href="#hl-13-41"&gt;41&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-42"&gt;&lt;a class="lnlinks" href="#hl-13-42"&gt;42&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-43"&gt;&lt;a class="lnlinks" href="#hl-13-43"&gt;43&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-13-44"&gt;&lt;a class="lnlinks" href="#hl-13-44"&gt;44&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-yaml" data-lang="yaml"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;apiVersion&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;kagent.dev/v1alpha2&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;kind&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;Agent&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;metadata&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;ops-readonly-agent&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;namespace&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;kagent&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;spec&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;&lt;span class="sd"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; A read-only Kubernetes operations assistant. It can inspect Kubernetes
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; resources and fetch documentation pages, but it must not perform write
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; operations.&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;Declarative&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;declarative&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;modelConfig&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;ops-openai-model&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;stream&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;systemMessage&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;|-&lt;/span&gt;&lt;span class="sd"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; You are a Kubernetes operations assistant.
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; Rules:
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - Only use read-only tools.
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - Do not make up cluster state.
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - If a tool result is missing or ambiguous, say so.
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - Separate confirmed facts from guesses.
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - Never suggest deleting or modifying resources without human review.
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; Response format:
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - Summary
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - Evidence from tools
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - Possible causes
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="sd"&gt; - Next checks&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;tools&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;McpServer&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;mcpServer&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;apiGroup&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;kagent.dev&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;kind&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;RemoteMCPServer&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;kagent-tool-server&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;toolNames&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="l"&gt;k8s_get_available_api_resources&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="l"&gt;k8s_get_resources&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;McpServer&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;mcpServer&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;kind&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;MCPServer&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;mcp-website-fetcher&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;toolNames&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="l"&gt;fetch&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;应用：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-14-1"&gt;&lt;a class="lnlinks" href="#hl-14-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl apply -f ops-readonly-agent.yaml
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;检查 Agent：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-15-1"&gt;&lt;a class="lnlinks" href="#hl-15-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-15-2"&gt;&lt;a class="lnlinks" href="#hl-15-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-15-3"&gt;&lt;a class="lnlinks" href="#hl-15-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get agent -n kagent
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get agent ops-readonly-agent -n kagent -o yaml
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;官方示例里 Agent 的 status 会出现类似 &lt;code&gt;Accepted=True&lt;/code&gt;、&lt;code&gt;Ready=True&lt;/code&gt; 的 condition。如果这里不 Ready，优先看三类对象：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-16-1"&gt;&lt;a class="lnlinks" href="#hl-16-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-16-2"&gt;&lt;a class="lnlinks" href="#hl-16-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-16-3"&gt;&lt;a class="lnlinks" href="#hl-16-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get modelconfig ops-openai-model -n kagent -o yaml
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get mcpserver mcp-website-fetcher -n kagent -o yaml
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl get agent ops-readonly-agent -n kagent -o yaml
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;我会按这个顺序查：&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;code&gt;ModelConfig&lt;/code&gt; 是否能读到 secret。&lt;/li&gt;
&lt;li&gt;&lt;code&gt;MCPServer&lt;/code&gt; 是否已经被 kmcp controller 拉起来。&lt;/li&gt;
&lt;li&gt;&lt;code&gt;Agent&lt;/code&gt; 引用的 tool 名称是否存在。&lt;/li&gt;
&lt;li&gt;&lt;code&gt;Agent&lt;/code&gt; 的 namespace 是否能引用对应 MCP server。&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id="5-打开-ui-验证"&gt;&lt;a href="#5-%e6%89%93%e5%bc%80-ui-%e9%aa%8c%e8%af%81" class="header-anchor"&gt;&lt;/a&gt;5. 打开 UI 验证
&lt;/h2&gt;&lt;p&gt;本地打开 kagent UI：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-17-1"&gt;&lt;a class="lnlinks" href="#hl-17-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kubectl port-forward -n kagent svc/kagent-ui 8080:8080
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;然后访问：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-18-1"&gt;&lt;a class="lnlinks" href="#hl-18-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-text" data-lang="text"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;http://localhost:8080
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;可以先问几个低风险问题：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-19-1"&gt;&lt;a class="lnlinks" href="#hl-19-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-text" data-lang="text"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;列出当前集群里可以查询的 Kubernetes API resources。
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;再问一个会用到 fetch 的问题：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-20-1"&gt;&lt;a class="lnlinks" href="#hl-20-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-text" data-lang="text"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;帮我读取 https://kagent.dev/docs/kagent/getting-started/first-mcp-tool ，总结创建 MCPServer 和 Agent 的关键步骤。
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;如果 Agent 正常，它应该会调用对应工具，而不是直接编造结果。这个时候我会重点看 UI 里有没有展示 tool call、参数和返回内容。kagent 这类工具的价值不只是回答，还在于能不能复盘它怎么回答的。&lt;/p&gt;
&lt;h2 id="6-权限边界我不会一开始就给写权限"&gt;&lt;a href="#6-%e6%9d%83%e9%99%90%e8%be%b9%e7%95%8c%e6%88%91%e4%b8%8d%e4%bc%9a%e4%b8%80%e5%bc%80%e5%a7%8b%e5%b0%b1%e7%bb%99%e5%86%99%e6%9d%83%e9%99%90" class="header-anchor"&gt;&lt;/a&gt;6. 权限边界：我不会一开始就给写权限
&lt;/h2&gt;&lt;p&gt;这个 case 里我故意只选了只读工具。原因很简单：Agent 最容易出事故的不是回答错，而是拿着写权限执行错。&lt;/p&gt;
&lt;p&gt;如果未来要开放写操作，我会分三层：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-21-1"&gt;&lt;a class="lnlinks" href="#hl-21-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-21-2"&gt;&lt;a class="lnlinks" href="#hl-21-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-21-3"&gt;&lt;a class="lnlinks" href="#hl-21-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-text" data-lang="text"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;read_only get/list/watch/logs/events
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;reviewed 生成 YAML、生成 patch，但不 apply
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;approved 人工确认后才允许执行写操作
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;kagent 的 Tool 配置里支持 &lt;code&gt;requireApproval&lt;/code&gt;，可以把敏感工具列进去，让工具调用前停下来等人工确认。这个设计比“相信系统提示词不会乱来”靠谱。&lt;/p&gt;
&lt;p&gt;比如后续某个 MCP server 有一个 &lt;code&gt;restart_deployment&lt;/code&gt; 工具，我不会直接放开，而是会写成：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-22-1"&gt;&lt;a class="lnlinks" href="#hl-22-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-22-2"&gt;&lt;a class="lnlinks" href="#hl-22-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-22-3"&gt;&lt;a class="lnlinks" href="#hl-22-3"&gt;3&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-22-4"&gt;&lt;a class="lnlinks" href="#hl-22-4"&gt;4&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-22-5"&gt;&lt;a class="lnlinks" href="#hl-22-5"&gt;5&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-22-6"&gt;&lt;a class="lnlinks" href="#hl-22-6"&gt;6&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-22-7"&gt;&lt;a class="lnlinks" href="#hl-22-7"&gt;7&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-22-8"&gt;&lt;a class="lnlinks" href="#hl-22-8"&gt;8&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-22-9"&gt;&lt;a class="lnlinks" href="#hl-22-9"&gt;9&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-yaml" data-lang="yaml"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;tools&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;McpServer&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;mcpServer&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;kind&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;MCPServer&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;ops-actions&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;toolNames&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="l"&gt;restart_deployment&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;requireApproval&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="l"&gt;restart_deployment&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;h2 id="这套-case-的落地判断"&gt;&lt;a href="#%e8%bf%99%e5%a5%97-case-%e7%9a%84%e8%90%bd%e5%9c%b0%e5%88%a4%e6%96%ad" class="header-anchor"&gt;&lt;/a&gt;这套 case 的落地判断
&lt;/h2&gt;&lt;p&gt;如果只是本地试用，&lt;code&gt;kagent install --profile demo&lt;/code&gt; 更快。官方 quickstart 里这条命令会预装一些 demo agents 和 MCP tools：&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;div class="chroma"&gt;
&lt;table class="lntable"&gt;&lt;tr&gt;&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code&gt;&lt;span class="lnt" id="hl-23-1"&gt;&lt;a class="lnlinks" href="#hl-23-1"&gt;1&lt;/a&gt;
&lt;/span&gt;&lt;span class="lnt" id="hl-23-2"&gt;&lt;a class="lnlinks" href="#hl-23-2"&gt;2&lt;/a&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;
&lt;td class="lntd"&gt;
&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kagent install --profile demo
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;kagent dashboard
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;/div&gt;
&lt;/div&gt;&lt;p&gt;但如果要往团队环境里放，我更建议走 Helm + YAML：&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;CRD 和 controller 由平台侧统一安装。&lt;/li&gt;
&lt;li&gt;&lt;code&gt;ModelConfig&lt;/code&gt;、&lt;code&gt;MCPServer&lt;/code&gt;、&lt;code&gt;Agent&lt;/code&gt; 放进 Git 仓库。&lt;/li&gt;
&lt;li&gt;每个 Agent 的工具列表明确写出来。&lt;/li&gt;
&lt;li&gt;写操作默认要求人工确认。&lt;/li&gt;
&lt;li&gt;先把目标限定为“排查摘要”和“信息收集”，不要一上来自动修复。&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;kagent 这类项目让我感觉 Kubernetes 后面会多出一种新对象：不是 workload，也不是 controller，而是“会调用工具的运维助手”。但真正能不能用，不取决于它能不能聊天，而取决于工具边界、权限边界和运行记录是不是足够清楚。&lt;/p&gt;
&lt;h2 id="参考资料"&gt;&lt;a href="#%e5%8f%82%e8%80%83%e8%b5%84%e6%96%99" class="header-anchor"&gt;&lt;/a&gt;参考资料
&lt;/h2&gt;&lt;ul&gt;
&lt;li&gt;&lt;a class="link" href="https://kagent.dev/docs/kagent/introduction/installation" target="_blank" rel="noopener"
 &gt;kagent Installing kagent&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://kagent.dev/docs/kagent/getting-started/first-mcp-tool" target="_blank" rel="noopener"
 &gt;kagent First MCP Tool&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://kagent.dev/docs/kagent/resources/api-ref" target="_blank" rel="noopener"
 &gt;kagent API reference&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://kagent.dev/docs/kagent/examples/agents-mcp" target="_blank" rel="noopener"
 &gt;kagent Agents via MCP&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://www.kagent.dev/docs/kmcp/deploy/install-controller" target="_blank" rel="noopener"
 &gt;kmcp Install controller&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://www.cncf.io/projects/kagent/" target="_blank" rel="noopener"
 &gt;CNCF kagent 项目页&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://www.cncf.io/blog/2025/04/15/kagent-bringing-agentic-ai-to-cloud-native/" target="_blank" rel="noopener"
 &gt;CNCF Blog: kagent&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;</description></item></channel></rss>