C#訪問共享目錄總結


在各種業務需求中,我們經常要訪問一個在網絡中的目錄,讀取其中的文件或者是在其目錄中創建文件,在.Net中我們主要使用mpr.dll中的WNetAddConnection2和WNetCancelConnection2來實現,下面是代碼引入。

        [DllImport("mpr.dll")]
        private static extern int WNetAddConnection2(NetResource netResource,
            string password, string username, int flags);

        [DllImport("mpr.dll")]
        private static extern int WNetCancelConnection2(string name, int flags,
            bool force);

在上述代碼中使用到的NetResource 我們可以定義如下:

var netResource = new NetResource
            {
                Scope = ResourceScope.GlobalNetwork,
                ResourceType = ResourceType.Disk,
                DisplayType = ResourceDisplayType.Share,
                RemoteName = networkName
            };

參數RemoteName就是遠程網絡路徑。比如@"\\10.5.5.5\Public\Test"。

using System;
using System.ComponentModel;
using System.Runtime.InteropServices;
using System.Net;

namespace Phoenix.Modules.Common.Service.Uploads
{
    public class ConnectToSharedFolder : IDisposable
    {
        readonly string _networkName;

        public ConnectToSharedFolder(string networkName, NetworkCredential credentials)
        {
            _networkName = networkName;

            var netResource = new NetResource
            {
                Scope = ResourceScope.GlobalNetwork,
                ResourceType = ResourceType.Disk,
                DisplayType = ResourceDisplayType.Share,
                RemoteName = networkName
            };

            var userName = string.IsNullOrEmpty(credentials.Domain)
                ? credentials.UserName
                : $@"{credentials.Domain}\{credentials.UserName}";

            var result = WNetAddConnection2(
                netResource,
                credentials.Password,
                userName,
                0);

            if (result != 0)
            {
                throw new Win32Exception(result, "Error connecting to remote share");
            }
        }

        ~ConnectToSharedFolder()
        {
            Dispose(false);
        }

        public void Dispose()
        {
            Dispose(true);
            GC.SuppressFinalize(this);
        }

        protected virtual void Dispose(bool disposing)
        {
            WNetCancelConnection2(_networkName, 0, true);
        }

        [DllImport("mpr.dll")]
        private static extern int WNetAddConnection2(NetResource netResource,
            string password, string username, int flags);

        [DllImport("mpr.dll")]
        private static extern int WNetCancelConnection2(string name, int flags,
            bool force);

        [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 : int
        {
            Connected = 1,
            GlobalNetwork,
            Remembered,
            Recent,
            Context
        };

        public enum ResourceType : int
        {
            Any = 0,
            Disk = 1,
            Print = 2,
            Reserved = 8,
        }

        public enum ResourceDisplayType : int
        {
            Generic = 0x0,
            Domain = 0x01,
            Server = 0x02,
            Share = 0x03,
            File = 0x04,
            Group = 0x05,
            Network = 0x06,
            Root = 0x07,
            Shareadmin = 0x08,
            Directory = 0x09,
            Tree = 0x0a,
            Ndscontainer = 0x0b
        }
    }
}
ConnectToSharedFolder

引入ConnectToSharedFolder、NetResource、ResourceScope,就可以直接添加代碼寫入文件了。

using Phoenix.Modules.Common.Service.Uploads;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleApp4_networkDic
{
    class Program
    {
        public static string networkPath = @"\\10.5.5.5\test";

        static NetworkCredential credentials = new NetworkCredential(@"test", "May");

        public static string myNetworkPath = string.Empty;

        static void Main(string[] args)
        {
            string filename = "test.txt";
            FileUpload(filename);
            Console.ReadKey();
        }

        public static void  FileUpload(string UploadURL)
        {
            try
            {
                using (new ConnectToSharedFolder(networkPath, credentials))
                {
                    var fileList = Directory.GetDirectories(networkPath);
                    foreach (var item in fileList) { if (item.Contains("{ClientDocument}")) { myNetworkPath = item; } }
                    myNetworkPath = networkPath+@"\" + UploadURL;

                    using (FileStream fileStream = File.Create(myNetworkPath))
                    {
                        var file = System.Text.Encoding.UTF8.GetBytes("this is a test");
                        fileStream.Write(file, 0, file.Length);
                        fileStream.Flush();
                        fileStream.Close();
                    }
                }
            }
            catch (Exception ex)
            {
            }
            
        }
    }

}
測試代碼

 

這樣就可以訪問和讀取網絡中的路徑了,在測試中一直遇到在調用wnetaddconnection2方法的時候返回error 53的錯誤,看代碼中也是沒有錯誤,直接訪問所用的測試目標網絡文件也是可以的,然后再google一搜,就是我們在傳遞網絡目標文件路徑的時候后面不能有“\”,把“\”去掉然后再訪問就沒有問題了。

原文鏈接https://social.msdn.microsoft.com/Forums/windows/en-US/5f8224d4-c36a-4051-a8e5-7b2e4d817986/wnetaddconnection2-fails-with-error-code-53?forum=peertopeer。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM