文章目录
-
- 一、被Python"霸凌"的日子,该结束了
- 二、这俩"大杀器"到底是啥?
-
- [2.1 OpenClaw:给AI装上"手脚"的本地代理](#2.1 OpenClaw:给AI装上"手脚"的本地代理)
- [2.2 C# Runner:让AI安全地"动"起来](# Runner:让AI安全地"动"起来)
- [三、环境准备:就装.NET 9,别的不要](#三、环境准备:就装.NET 9,别的不要)
- [四、实战第一弹:手写C# Runner,让AI能跑代码](# Runner,让AI能跑代码)
- 五、实战第二弹:接入OpenClaw,给Agent装上"手脚"
- [六、双剑合璧:用Microsoft Agent Framework当"大脑"](#六、双剑合璧:用Microsoft Agent Framework当"大脑")
- 七、工业级部署:安全不是儿戏
-
- [7.1 代码执行沙箱化](#7.1 代码执行沙箱化)
- [7.2 权限分级控制](#7.2 权限分级控制)
- [7.3 审计日志不可少](#7.3 审计日志不可少)
- 八、跑起来看看效果
- 九、这方案牛在哪?咱们聊聊现实
- 十、坑与避坑指南
-
- [坑1:MCP SDK还是预览版](#坑1:MCP SDK还是预览版)
- 坑2:OpenClaw的Node.js依赖
- 坑3:Docker性能损耗
- 坑4:AI幻觉
- 结语:.NET开发者的AI春天
一、被Python"霸凌"的日子,该结束了
说实话,搞AI开发的兄弟们这两年过得有点憋屈。你想啊,咱.NET开发者好歹也是企业级应用的中流砥柱,银行系统、政务平台、工业控制,哪个离得开C#?可一到AI这波浪潮,画风突然变了------打开GitHub,满屏的pip install;看个教程,上来就是conda activate;想本地跑个AI Agent,得先装个3.8GB的Anaconda,再跟numpy、pandas的版本冲突斗智斗勇。
我就想让AI帮我写个Excel报表自动化,结果光配环境就折腾到凌晨三点。更崩溃的是企业级部署,客户那边都是Windows Server,IIS跑得好好的,你突然说要塞个Python进去跑AI,运维大哥那个眼神能杀人:"Python?那玩意儿内存泄漏了咋整?GIL锁卡死了咋整?" 这话我没法接,只能默默去改Dockerfile。
转机出现在2026年3月。微软和Anthropic搞的MCP(Model Context Protocol)协议终于出了官方C# SDK,而腾讯开源的OpenClaw也在C#社区里长出了原生支持的枝丫。今天咱就整点硬核的:不用一行Python,纯.NET 9环境,搭一个能写代码、能上网、有记忆的工业级AI Agent。
二、这俩"大杀器"到底是啥?
2.1 OpenClaw:给AI装上"手脚"的本地代理
OpenClaw在国内开发者圈子里有个接地气的外号------"龙虾",因为Claw就是爪子,加上它那红色的Logo像煮熟的虾。这玩意儿本质上是一个跑在你自己电脑上的个人AI代理框架,基于TypeScript/Node.js开发,但别被技术栈吓到,它对外暴露的是标准化接口。
OpenClaw最牛的地方在于它有个"心跳机制"------每30分钟唤醒一次自己,主动执行任务。它能接管终端命令、管理文件、控制浏览器、发邮件、管日历,甚至帮你值机。更重要的是,它的记忆系统直接用Markdown文件存储,理由是"LLM天生对Markdown友好,而且人类打开文件夹就能看懂它记住了啥"。
2026年被称为OpenClaw开启的"AI Agent个人端开源部署元年",它支持多市场深度适配、技能模块化封装,还能无缝对接飞书、钉钉等IM工具。
2.2 C# Runner:让AI安全地"动"起来
C# Runner可以理解为大语言模型的"沙盒执行器"。它采用基于Docker的Host-Worker架构:每个Worker都是独立的轻量级Docker容器,已加载Roslyn编译环境,负责实际编译和执行C#代码;Host则维护着一个Worker资源池,实现毫秒级响应。
核心特性就三个:安全性(代码在独立Docker容器中执行,彻底隔离)、性能(Worker预热与池化,内存中编译执行)、丰富功能(支持HTTP REST API与MCP接口)。
三、环境准备:就装.NET 9,别的不要
工欲善其事,必先利其器。咱这套方案的优势就是"轻",不需要Python环境,不需要Java运行时,只要.NET 9 SDK和Docker Desktop。
检查.NET版本,确保是9.0以上
bash
dotnet --version
安装核心NuGet包
bash
dotnet add package ModelContextProtocol --version 0.1.0-preview.6
dotnet add package Microsoft.SemanticKernel --version 1.40.0
dotnet add package Microsoft.Agents.AI.OpenAI --version 1.0.0-preview.251219.1
这里要重点说说MCP(Model Context Protocol)。你可以把它当成AI的"USB-C口"------以前每个AI工具都要写专门的驱动,现在有了这个协议,AI模型就像插USB-C一样,插上就能用外部工具。官方C# SDK刚发预览版,NuGet上直接搜ModelContextProtocol就能拉到。
OpenClaw的部署也简单,2026年的版本已经支持一键脚本安装:
一键安装OpenClaw(Windows PowerShell)
powershell
iwr -useb https://openclaw.dev/install.ps1 | iex
验证安装
bash
openclaw --version
四、实战第一弹:手写C# Runner,让AI能跑代码
很多教程一上来就给你整Kubernetes,咱不整那个。直接用MCP的stdio(标准输入输出)通信,就像以前写命令行工具一样,简单粗暴但好用。
新建一个CodeRunnerTool.cs,这玩意儿就是咱们的"代码解释器":
csharp
using ModelContextProtocol.Server;
using System.ComponentModel;
using System.Diagnostics;
[McpServerToolType] // 标记这是个工具箱
public static class CSharpRunner
{
[McpServerTool, Description("执行C#代码片段并返回输出结果")]
public static async Task<string> ExecuteCode(
[Description("完整的C#代码字符串")] string code)
{
// 搞个临时文件存代码
var tempFile = Path.Combine(Path.GetTempPath(), $"ai_{Guid.NewGuid()}.cs");
await File.WriteAllTextAsync(tempFile, $@"
using System;
using System.Linq;
using System.Collections.Generic;
class Program {{
static void Main() {{
{code}
}}
}}");
try
{
// 直接用dotnet run执行,不需要预编译
var process = new Process
{
StartInfo = new ProcessStartInfo
{
FileName = "dotnet",
Arguments = $"run --property:OutputType=Exe {tempFile}",
RedirectStandardOutput = true,
RedirectStandardError = true,
UseShellExecute = false,
CreateNoWindow = true
}
};
process.Start();
var output = await process.StandardOutput.ReadToEndAsync();
var error = await process.StandardError.ReadToEndAsync();
await Task.Run(() => process.WaitForExit(5000)); // 最多等5秒,防止死循环
if (!string.IsNullOrEmpty(error) && !error.Contains("Build succeeded"))
return $"执行报错:{error}";
return $"执行结果:\n{output}";
}
catch (Exception ex)
{
return $"出幺蛾子了:{ex.Message}";
}
finally
{
if (File.Exists(tempFile)) File.Delete(tempFile);
}
}
}
然后在Program.cs里注册这个服务:
csharp
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using ModelContextProtocol.Server;
var builder = Host.CreateApplicationBuilder(args);
// 日志输出到stderr,MCP协议规定stdout留给数据传输
builder.Logging.AddConsole(consoleLogOptions =>
{
consoleLogOptions.LogToStandardErrorThreshold = LogLevel.Trace;
});
builder.Services
.AddMcpServer()
.WithStdioServerTransport() // 用标准输入输出通信,最简单粗暴
.WithToolsFromAssembly(); // 自动扫描上面那个[CSharpRunner]类
await builder.Build().RunAsync();
这时候程序会卡住等输入,这就是MCP的stdio模式在工作。别急着关,后面让Agent对接它。
五、实战第二弹:接入OpenClaw,给Agent装上"手脚"
光有代码执行能力还不够,AI得能上网、能查资料、能操作浏览器。这时候就需要OpenClaw出场了。咱们给它写个C#包装器,让它能被Semantic Kernel调用。
csharp
using Microsoft.SemanticKernel;
using System.ComponentModel;
using System.Diagnostics;
public class OpenClawPlugin
{
private readonly string _openClawPath;
public OpenClawPlugin()
{
_openClawPath = Environment.GetEnvironmentVariable("OPENCLAW_PATH") ?? "openclaw";
}
[KernelFunction, Description("使用OpenClaw控制浏览器访问网页并获取内容")]
public async Task<string> BrowseWebAsync(
[Description("要访问的URL")] string url,
[Description("任务描述,如'获取新闻标题'")] string task)
{
var process = new Process
{
StartInfo = new ProcessStartInfo
{
FileName = _openClawPath,
Arguments = $"browse \"{url}\" --task \"{task}\" --format markdown",
RedirectStandardOutput = true,
RedirectStandardError = true,
UseShellExecute = false
}
};
process.Start();
var output = await process.StandardOutput.ReadToEndAsync();
await Task.Run(() => process.WaitForExit(30000)); // 给30秒,毕竟要开浏览器
return string.IsNullOrEmpty(output) ? "浏览器操作失败" : output;
}
[KernelFunction, Description("执行本地系统命令,需谨慎使用")]
public async Task<string> ExecuteCommandAsync(
[Description("命令内容")] string command)
{
// 安全检查:禁止危险命令
var dangerousKeywords = new[] { "rm", "del", "format", "mkfs", "dd" };
if (dangerousKeywords.Any(k => command.Contains(k)))
{
return "❌ 检测到危险命令,已拒绝执行";
}
var process = new Process
{
StartInfo = new ProcessStartInfo
{
FileName = "cmd.exe",
Arguments = $"/c {command}",
RedirectStandardOutput = true,
UseShellExecute = false,
CreateNoWindow = true
}
};
process.Start();
var output = await process.StandardOutput.ReadToEndAsync();
await Task.Run(() => process.WaitForExit(10000));
return $"命令执行结果:\n{output}";
}
}
六、双剑合璧:用Microsoft Agent Framework当"大脑"
现在有俩工具了:C# Runner(执行代码)和OpenClaw(操作浏览器)。得有个大脑来调度它们。Microsoft Agent Framework(MAF)就是干这个的,它是微软2026年推出的新框架,用来替代Semantic Kernel和AutoGen,提供线程级的对话状态管理、C#方法原生注册为AI工具、内置多智能体协作等能力。
新建AgentBrain.cs:
csharp
using Microsoft.Agents.AI;
using Microsoft.Extensions.AI;
using OpenAI;
using ModelContextProtocol.Client;
public class IndustrialAgent : IDisposable
{
private AIAgent _agent;
private AgentThread _thread;
private IMcpClient _mcpClient;
public async Task InitializeAsync()
{
// 1. 配置大模型,这里用DeepSeek或者OpenAI都行
var chatClient = new OpenAIClient(
Environment.GetEnvironmentVariable("AI_API_KEY"))
.GetChatClient("deepseek-chat")
.AsIChatClient();
// 2. 创建Agent,设定人设
_agent = chatClient.CreateAIAgent(instructions: """
你是一个工业级.NET AI助手,拥有两个核心能力:
1. 通过C# Runner执行代码解决计算、数据处理问题
2. 通过OpenClaw上网查资料、操作浏览器
执行原则:
- 遇到数学计算、数据处理,优先写C#代码执行,不要口算
- 需要实时信息时,主动调用浏览器工具
- 涉及文件操作、系统命令时,必须检查安全性
- 用中文回复,语气专业但易懂
""");
// 3. 创建持久化线程(记忆功能)
_thread = _agent.GetNewThread();
// 4. 连接MCP服务器(C# Runner)
var serverConfig = new McpServerConfig
{
Id = "csharp-runner",
Name = "C# Code Runner",
TransportType = TransportTypes.StdIo,
TransportOptions = new Dictionary<string, string>
{
["command"] = "dotnet",
["arguments"] = "run --project ./CSharpRunner.csproj"
}
};
_mcpClient = await McpClientFactory.CreateAsync(serverConfig, new McpClientOptions());
// 把MCP工具转成Agent可用的函数
var tools = await _mcpClient.GetAIFunctionsAsync();
foreach (var tool in tools)
{
// 注册到Agent的工具库
_agent.RegisterTool(tool);
}
}
public async Task<string> ChatAsync(string userInput)
{
// Agent会自动决定要不要调用工具,不需要人工干预
var response = await _agent.RunAsync(userInput, _thread);
return response.ToString();
}
public void Dispose()
{
_mcpClient?.DisposeAsync().AsTask().Wait();
}
}
七、工业级部署:安全不是儿戏
上面代码能跑,但真要上生产环境,还得加点"保险"。工业级AI Agent最怕的就是安全问题------万一AI抽风执行了rm -rf /,或者把敏感数据发到外网,那可不是闹着玩的。
7.1 代码执行沙箱化
C# Runner的Docker方案是首选:
docker-compose.yml
yaml
version: '3.8'
services:
csharp-runner-host:
image: csharprunner/host:latest
ports:
- 5000:5000
environment:
- WORKER_POOL_SIZE=5
- MAX_EXECUTION_TIME=30
- ENABLE_NETWORK_ISOLATION=true
volumes:
- /var/run/docker.sock:/var/run/docker.sock
每个Worker容器都是独立的,代码执行完立即销毁,就算有恶意代码也跑不出容器。
7.2 权限分级控制
OpenClaw支持细粒度的技能权限配置:
bash
# 在OpenClaw配置中限制危险操作
openclaw skill config file-manager --permission "read-only"
openclaw skill config browser --permission "limited-domains" --allowed-domains "github.com,stackoverflow.com"
openclaw skill config system --permission "deny-all"
7.3 审计日志不可少
工业级应用必须有迹可循:
csharp
public class AuditingAgentDecorator : IChatClient
{
private readonly IChatClient _inner;
private readonly ILogger _logger;
public async Task<ChatResponse> GetResponseAsync(
IEnumerable<ChatMessage> messages,
ChatOptions? options = null)
{
// 记录用户输入
_logger.LogInformation("User input: {Input}",
string.Join("\n", messages.Select(m => m.Text)));
var stopwatch = Stopwatch.StartNew();
var response = await _inner.GetResponseAsync(messages, options);
stopwatch.Stop();
// 记录AI输出和执行时间
_logger.LogInformation("Agent response ({ElapsedMs}ms): {Response}",
stopwatch.ElapsedMilliseconds,
response.Text);
return response;
}
}
八、跑起来看看效果
写个简单的Console程序测试一下:
csharp
class Program
{
static async Task Main(string[] args)
{
Console.WriteLine("🚀 启动工业级C# AI Agent...");
var agent = new IndustrialAgent();
await agent.InitializeAsync();
Console.WriteLine("✅ Agent初始化完成,开始对话(输入exit退出):\n");
while (true)
{
Console.Write("你:");
var input = Console.ReadLine();
if (input?.ToLower() == "exit") break;
Console.Write("Agent:");
var response = await agent.ChatAsync(input);
Console.WriteLine(response);
Console.WriteLine();
}
agent.Dispose();
}
}
场景1:代码执行
输入:"帮我算一下从1到100所有素数的和"
Agent会生成C#代码,通过MCP调用C# Runner执行,返回结果1060。
场景2:上网+代码结合
输入:"查一下今天茅台的股价,如果高于1500就计算买入100股需要多少钱"
Agent先调用OpenClaw浏览器工具查股价,再调用C# Runner做乘法,全程不需要人工干预。
场景3:拒绝危险操作
输入:"帮我删除C盘Windows文件夹"
Agent会识别出这是危险操作,直接拒绝:"❌ 检测到危险命令,已拒绝执行"。
九、这方案牛在哪?咱们聊聊现实
首先,全栈C#。从Agent大脑到代码执行再到浏览器控制,全是.NET生态,不需要在Python和C#之间来回切换,调试起来爽歪歪。
其次,真·本地部署。OpenClaw跑在本地,C# Runner可以用Docker跑在本地,数据不会流出你的机器,这对金融、医疗等敏感行业简直是刚需。
再次,扩展性极强。MCP协议是开放标准,今天接了C# Runner,明天可以接Python Runner、Java Runner,甚至是公司内部的遗留系统。
最后,成本可控。不用买天价的OpenAI GPT-4额度,本地跑DeepSeek或者通义千问,配合OpenClaw的自动化能力,一个月省下的API费用够吃好几顿大餐。
十、坑与避坑指南
坑1:MCP SDK还是预览版
目前ModelContextProtocol的C# SDK是0.1.0-preview.6,API可能会变。生产环境建议锁定版本,或者等正式版。
坑2:OpenClaw的Node.js依赖
虽然咱用C#写Agent,但OpenClaw底层是Node.js,Windows上装Node.js有时会有权限问题。建议用nvm-windows管理Node版本,别直接装安装包。
坑3:Docker性能损耗
C# Runner用Docker隔离虽然安全,但启动一个Worker要几十毫秒。高并发场景下建议预热池子,保持几个Worker常驻内存。
坑4:AI幻觉
Agent框架再牛,底层大模型还是会幻觉。涉及金钱、安全的关键操作,必须加人工确认环节,别完全让AI自动执行。
结语:.NET开发者的AI春天
2026年,AI开发的门槛正在快速降低,但生态碎片化的问题也在加剧。微软押注MCP协议,推出Agent Framework,本质上是在解决"AI工具怎么跟世界交互"的问题。OpenClaw的开源,则让个人开发者也能拥有企业级的Agent能力。
对.NET开发者来说,这是一个好消息:我们不需要抛弃多年的工程经验去转Python,用熟悉的C#、熟悉的Visual Studio、熟悉的Windows生态,照样能搭出高大上的AI Agent。
代码已经贴在上面了,感兴趣的兄弟可以直接复制粘贴试试。有问题欢迎在评论区交流,咱们一起把这套方案打磨得更稳、更强。毕竟,AI时代,C#程序员也不能掉队,对吧?