.Net平台下,分布式文件存储的实现
2014-08-14 09:35 FuzhePan 阅读(6025) 评论(18) 编辑 收藏 举报遇到的问题
对于Web程序,使用一台服务器的时候,客户端上传的文件一般也都是存储在这台服务器上。但在集群环境中就行不通了,如果每个服务器都存储自己接受到的文件,就乱套了,数据库中明明有这个附件的记录,却找不到这个文件。于是,文件需要进行统一集中管理,并向集群中的服务器提供统一的路径。

基于NFS的分布式文件存储实现
Network File System 简称NFS,用人话说叫共享文件夹,可以实现分布式存储文件。只需要在文件服务器上共享文件夹,并指定相应账号的权限,并给Web服务器设置可以访问共享文件夹的账号和密码,web服务器就可以像操作本地文件一样操作文件服务器上的文件了。NFS下的文件访问路径有固定的格式,称为UNC(Universal Naming Convention),以“\\”开头。
要以UNC的方式访问NFS下的文件,需要用到windows提供的两个API:WNetAddConnection2 和 WNetCancelConnection2。WNetAddConnection2可以使用指定的账号和密码创建一个UNC的连接,然后程序可以直接访问该UNC下文件。
首先创建类FileServerConnection,用于管理连接,具体代码如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 | public class FileServerConnection { private string uncName; private string username; private string password; /// <summary> /// 构造器 /// </summary> /// <param name="uncName">完整的UNC路径</param> /// <param name="username">访问共享连接的用户名</param> /// <param name="password">访问共享连接的密码</param> public FileServerConnection( string uncName, string username, string password) { this .uncName = uncName; this .username = username; this .password = password; } /// <summary> /// 连接文件服务器 /// </summary> public void Connect() { var netResource = new NetResource { Scope = ResourceScope.GlobalNetwork, ResourceType = ResourceType.Disk, DisplayType = ResourceDisplayType.Share, RemoteName = this .uncName.TrimEnd( '\\' ) }; var result = WNetAddConnection2(netResource, password, username, 0); if (result != 0) throw new Win32Exception(result); } /// <summary> /// 释放连接 /// </summary> public void Disconnect() { WNetCancelConnection2( this .uncName, 0, true ); } [DllImport( "mpr.dll" )] private static extern int WNetAddConnection2(NetResource netResource, string password, string username, int flags); private static extern int WNetCancelConnection2( string name, int flags, bool force); } |
FileServerConnection中所用到的几个结构体代码如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 | [StructLayout(LayoutKind.Sequential)] public class NetResource { public ResourceScope Scope; public ResourceType ResourceType; public ResourceDisplayType DisplayType; public int Usage; public string LocalName; public string RemoteName; public string Comment; public string Provider; } public enum ResourceScope { Connected = 1, GlobalNetwork, Remembered, Recent, Context } ; public enum ResourceType { Any = 0, Disk = 1, Print = 2, Reserved = 8, } public enum ResourceDisplayType { Generic = 0x0, Domain = 0x01, Server = 0x02, Share = 0x03, File = 0x04, Group = 0x05, Network = 0x06, Root = 0x07, Shareadmin = 0x08, Directory = 0x09, Tree = 0x0a, Ndscontainer = 0x0b } |
然后在Web程序启动的时候,只需要创建一个FileServerConnection的实例,然后调用它的Connect方法。为了防止重复创建连接引发异常,可以Connect之前先DisConnect。具体调用代码如下:
1 2 3 | fsConnection= new FileServerConnection (storeRootPath, username, password); fsConnection.Disconnect(); fsConnection.Connect(); |
基于DFS分布式存储方案

【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· 展开说说关于C#中ORM框架的用法!
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?