讲师中心 微信公众号
AI工具推荐 视频效率加速

C# Named Pipe Server Stream方法 C#如何创建命名管道服务器

云萱姑娘_3997

云萱姑娘_3997

发布时间:2026-02-08 02:53:16

|

964人浏览过

|

来源于php中文网

原创

NamedPipeServerStream 构造时管道名须为纯名称(如"MyPipe"),PipeDirection需匹配读写需求,maxNumberOfServerInstances>1才支持并发,PipeOptions.WriteThrough避免数据未刷出;WaitForConnectionAsync()异步但需确保实例未被释放且正确处理异常与Dispose。

c# named pipe server stream方法 c#如何创建命名管道服务器

NamedPipeServerStream 构造参数怎么设才不会立刻报错

创建 NamedPipeServerStream 时最常踩的坑是权限和管道名格式。Windows 默认只允许本地连接,若用 "\\.\pipe\MyPipe" 这种 UNC 格式会直接抛 ArgumentException;正确写法是纯名称,比如 "MyPipe"。另外,PipeDirection 和 PipeOptions 不匹配也会导致后续 WaitForConnectionAsync() 失败——例如设成 PipeDirection.In 却试图从服务端写入,就会卡住或抛 InvalidOperationException。

推荐初始化写法:

var server = new NamedPipeServerStream(
    "MyPipe",                    // 管道名,不带前缀
    PipeDirection.InOut,         // 必须双向,除非你真只读或只写
    maxNumberOfServerInstances: 10,
    PipeTransmissionMode.Message,
    PipeOptions.Asynchronous | PipeOptions.WriteThrough
);
  • maxNumberOfServerInstances 设为 1 表示单连接,>1 才支持并发客户端(但每个连接需单独实例)
  • PipeOptions.WriteThrough 能避免客户端读不到“未刷出”的数据,尤其在短连接场景下很关键
  • 不要设 PipeSecurity 除非你明确需要跨用户或网络访问——默认安全描述符已足够本地进程通信

WaitForConnectionAsync() 阻塞还是异步?为什么调了没反应

WaitForConnectionAsync() 是真正的异步方法,不会阻塞线程,但它**必须在调用前确保管道处于“等待”状态**。常见错误是:构造完 NamedPipeServerStream 就直接 await,却忘了它此时还没开始监听——实际上构造只是分配资源,监听动作发生在第一次 await WaitForConnectionAsync() 时。

另一个隐形陷阱:如果客户端已断开、服务端没及时 dispose 旧实例,新实例可能因命名冲突无法启动。建议用 try/catch 包裹,并在 finally 中确保 Dispose():

try
{
    await server.WaitForConnectionAsync();
    // 处理客户端逻辑
}
catch (OperationCanceledException) { /* 客户端断开 */ }
catch (IOException ex) when (ex.InnerException is PipeException) { /* 管道被强制关闭 */ }
finally
{
    server?.Dispose();
}
  • 不要在 WaitForConnectionAsync() 后反复 await 同一个实例——它是一次性的,连接断开后必须新建 NamedPipeServerStream
  • 若需长连接复用,应在连接建立后单独启 Task 处理读写,而不是循环调用 WaitForConnectionAsync()

Message 模式下 Read/Write 怎么保证边界不粘包

设 PipeTransmissionMode.Message 后,WriteAsync() 写入的每一段数据会被当做一个独立消息,ReadAsync() 也会按消息边界返回——但前提是客户端也用相同模式打开管道。否则服务端以为在收消息,客户端却以字节流方式发,就会出现读不完或提前截断。

Windows TTS (WSL2)
Windows TTS (WSL2)

在 Windows 11 上"直接发声"的 TTS(从 WSL2/TUI 调用 powershell.exe + System.Speech)。适用于用户说"说出来/读出来/语音播报/用TTS",或反馈"没声音/tts 生成的 mp3 是空的/播不出来",以及需要中文语音但 OpenClaw 内置 tts 不可用时。

下载

实操要点:

  • 服务端 ReadAsync() 前先调 reader.ReadMessageLengthAsync()(需自己封装,.NET 无内置),或更稳妥地:用固定长度头 + 内容的方式手动拆包
  • 务必检查 ReadAsync() 返回值——它可能只读到部分消息(尤其大消息+缓冲区小),不能假设一次读完
  • 写入时用 WriteAsync(buffer, 0, length) 显式传长度,别依赖 buffer.Length,避免写入脏内存

如何让服务端支持多个客户端同时连接

单个 NamedPipeServerStream 实例只能服务一个客户端。要支持并发,必须在每次成功连接后,立即新建一个新实例并再次调用 WaitForConnectionAsync(),形成“监听-接受-派生-再监听”的循环。

典型结构:

async Task ListenLoop()
{
    while (!cts.IsCancellationRequested)
    {
        var server = new NamedPipeServerStream("MyPipe", PipeDirection.InOut, ...);
        try
        {
            await server.WaitForConnectionAsync(cts.Token);
            _ = HandleClientAsync(server); // 启动独立 Task 处理该连接
        }
        catch (OperationCanceledException) { break; }
        catch (IOException) { /* 忽略连接失败,继续下一轮 */ }
    }
}
  • 别把 HandleClientAsync() 放 await 里——那会串行化连接,失去并发意义
  • 每个客户端连接的生命周期管理(超时、心跳、异常清理)必须由 HandleClientAsync() 自己负责,主循环只管接新连接
  • 注意 maxNumberOfServerInstances 参数上限,超出后新连接会被系统拒绝,错误码通常是 ERROR_PIPE_BUSY

实际最难的不是启动服务器,而是客户端意外退出时服务端能否干净回收资源——NamedPipeServerStream 的 dispose 时机、是否 await 了所有 pending IO、有没有残留的未完成 Task,这些细节稍有疏忽就会导致句柄泄漏或后续连接失败。

热门AI工具

更多
豆包大模型

豆包大模型是一款由字节跳动推出的企业级大语言模型服务平台。

咔片AIPPT

一款在线AI演示文稿制作工具,可根据主题和内容需求辅助生成PPT结构与页面,提高演示材料制作效率。

讯飞智作

讯飞智作是一款AI视频创作工具,AI文本配音工具,数字人课程、营销视频制作。

WorkBuddy

一款AI办公效率工具,主要用于腾讯云推出的AI原生桌面智能体工作台,适合需要提升相关任务效率的用户。

蛙蛙写作

一款AI论文写作工具,主要用于超级AI智能写作助手,适合需要提升相关任务效率的用户。

Lovart
Lovart Hot

一款面向视觉设计创作的AI设计平台,可通过智能体和画布工作流辅助制作海报、Logo、网页、PPT及其他视觉内容。

切问学术

切问学术是一款AI论文写作工具,复旦大学NLP团队推出的AI学术智能体。

讯飞绘文

讯飞绘文是一款由科大讯飞推出的一站式 AIGC 内容运营平台。

DeepSeek

DeepSeek是一款面向对话、写作、编程和推理场景的AI大模型工具。

相关专题

更多
length函数用法
length函数用法

length函数用于返回指定字符串的字符数或字节数。可以用于计算字符串的长度,以便在查询和处理字符串数据时进行操作和判断。 需要注意的是length函数计算的是字符串的字符数,而不是字节数。对于多字节字符集,一个字符可能由多个字节组成。因此,length函数在计算字符串长度时会将多字节字符作为一个字符来计算。更多关于length函数的用法,大家可以阅读本专题下面的文章。

1847

2023.09.19

线程和进程的区别
线程和进程的区别

线程和进程的区别:线程是进程的一部分,用于实现并发和并行操作,而线程共享进程的资源,通信更方便快捷,切换开销较小。本专题为大家提供线程和进程区别相关的各种文章、以及下载和课程。

4178

2023.08.10

windows查看端口占用情况
windows查看端口占用情况

Windows端口可以认为是计算机与外界通讯交流的出入口。逻辑意义上的端口一般是指TCP/IP协议中的端口,端口号的范围从0到65535,比如用于浏览网页服务的80端口,用于FTP服务的21端口等等。怎么查看windows端口占用情况呢?php中文网给大家带来了相关的教程以及文章,欢迎大家前来阅读学习。

3239

2023.07.26

查看端口占用情况windows
查看端口占用情况windows

端口占用是指与端口关联的软件占用端口而使得其他应用程序无法使用这些端口,端口占用问题是计算机系统编程领域的一个常见问题,端口占用的根本原因可能是操作系统的一些错误,服务器也可能会出现端口占用问题。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

2798

2023.07.27

windows照片无法显示
windows照片无法显示

当我们尝试打开一张图片时,可能会出现一个错误提示,提示说"Windows照片查看器无法显示此图片,因为计算机上的可用内存不足",本专题为大家提供windows照片无法显示相关的文章,帮助大家解决该问题。

1488

2023.08.01

windows查看端口被占用的情况
windows查看端口被占用的情况

windows查看端口被占用的情况的方法:1、使用Windows自带的资源监视器;2、使用命令提示符查看端口信息;3、使用任务管理器查看占用端口的进程。本专题为大家提供windows查看端口被占用的情况的相关的文章、下载、课程内容,供大家免费下载体验。

2579

2023.08.02

windows无法访问共享电脑
windows无法访问共享电脑

在现代社会中,共享电脑是办公室和家庭的重要组成部分。然而,有时我们可能会遇到Windows无法访问共享电脑的问题。这个问题可能会导致数据无法共享,影响工作和生活的正常进行。php中文网给大家带来了相关的教程以及文章,欢迎大家前来阅读学习。

3290

2023.08.08

windows自动更新
windows自动更新

Windows操作系统的自动更新功能可以确保系统及时获取最新的补丁和安全更新,以提高系统的稳定性和安全性。然而,有时候我们可能希望暂时或永久地关闭Windows的自动更新功能。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

1617

2023.08.10

OpenJDK JVM参数怎么调优
OpenJDK JVM参数怎么调优

Java应用运行缓慢,如何调整JVM参数?本专题介绍OpenJDK JVM性能调优的基本流程,涵盖性能指标确认、运行数据采集、内存配置和垃圾回收分析,帮助你先定位瓶颈,再通过对照测试验证效果,避免直接套用参数而影响应用稳定性。

60

2026.10.16

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
Python uv官方安装与入门文档
Python uv官方安装与入门文档

共0课时 | 0人学习

Buffalo框架快速入门指南
Buffalo框架快速入门指南

共0课时 | 0人学习

Conan 2 安装指南
Conan 2 安装指南

共0课时 | 0人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn