2017-01-03 83 views
0

我试图复制映射的网络驱动器上的文件夹(不是文件,而是整个目录),并在同一个不同的名称中粘贴它的新版本位置。如果我使用本地驱动器,下面的代码很好用;但是,使用网络驱动器时出现身份验证错误。在映射的网络驱动器中复制并粘贴一个文件夹programmaticaly

DirectoryCopy(@"\\mappedserver\test", @"\\mappedserver\test2", true); 

“类型‘System.IO.IOException’未处理的异常出现在mscorlib.dll

附加信息:用户名或密码不正确。”

我使用了以下MSDN文档:Link并稍加修改以适合我的需要。

private static void DirectoryCopy(
    string sourceDirName, string destDirName, bool copySubDirs) 
    { 
     DirectoryInfo dir = new DirectoryInfo(sourceDirName); 
     DirectoryInfo[] dirs = dir.GetDirectories(); 

     // If the source directory does not exist, throw an exception. 
     if (!dir.Exists) 
     { 
      throw new DirectoryNotFoundException(
       "Source directory does not exist or could not be found: " 
       + sourceDirName); 
     } 

     // If the destination directory does not exist, create it. 
     if (!Directory.Exists(destDirName)) 
     { 
      Directory.CreateDirectory(destDirName); 
     } 


     // Get the file contents of the directory to copy. 
     FileInfo[] files = dir.GetFiles(); 

     foreach (FileInfo file in files) 
     { 
      // Create the path to the new copy of the file. 
      string temppath = Path.Combine(destDirName, file.Name); 

      // Copy the file. 
      file.CopyTo(temppath, false); 
     } 

     // If copySubDirs is true, copy the subdirectories. 
     if (copySubDirs) 
     { 

      foreach (DirectoryInfo subdir in dirs) 
      { 
       // Create the subdirectory. 
       string temppath = Path.Combine(destDirName, subdir.Name); 

       // Copy the subdirectories. 
       DirectoryCopy(subdir.FullName, temppath, copySubDirs); 
      } 
     } 
    } 

一个流行的解决方案似乎是给文件夹完全访问权限,但不幸的是,这并没有改变。

如何提供用户名和密码?我真的不想把管理员用户名和密码放在应用程序的任何地方,这怎么能做到呢?我的搜索主要是空的。

+1

运行应用程序的用户的用户(或用户上下文)是什么?我将开始朝这个方向进行调查...... – Bestter

+0

每个用户都有完全权限,可以在安装用户帐户时读取/写入/修改映射网络驱动器上的文件和文件夹。我试过以管理员的身份运行VS和程序,但由于我提供的用户名或密码没有做任何事情(并非完全意外)。 – A1raa

回答

1

一旦我需要从远程PC复制文件。我发现这个类:

public class NetworkShareAccesser : IDisposable 
{ 
    private string _remoteUncName; 
    private string _remoteComputerName; 

    private string RemoteComputerName 
    { 
     get { return _remoteComputerName; } 
     set 
     { 
      _remoteComputerName = value; 
      _remoteUncName = @"\\" + _remoteComputerName; 
     } 
    } 

    private string UserName { get; set; } 
    private string Password { get; set; } 

    #region Consts 

    private const int RESOURCE_CONNECTED = 0x00000001; 
    private const int RESOURCE_GLOBALNET = 0x00000002; 
    private const int RESOURCE_REMEMBERED = 0x00000003; 

    private const int RESOURCETYPE_ANY = 0x00000000; 
    private const int RESOURCETYPE_DISK = 0x00000001; 
    private const int RESOURCETYPE_PRINT = 0x00000002; 

    private const int RESOURCEDISPLAYTYPE_GENERIC = 0x00000000; 
    private const int RESOURCEDISPLAYTYPE_DOMAIN = 0x00000001; 
    private const int RESOURCEDISPLAYTYPE_SERVER = 0x00000002; 
    private const int RESOURCEDISPLAYTYPE_SHARE = 0x00000003; 
    private const int RESOURCEDISPLAYTYPE_FILE = 0x00000004; 
    private const int RESOURCEDISPLAYTYPE_GROUP = 0x00000005; 

    private const int RESOURCEUSAGE_CONNECTABLE = 0x00000001; 
    private const int RESOURCEUSAGE_CONTAINER = 0x00000002; 


    private const int CONNECT_INTERACTIVE = 0x00000008; 
    private const int CONNECT_PROMPT = 0x00000010; 
    private const int CONNECT_REDIRECT = 0x00000080; 
    private const int CONNECT_UPDATE_PROFILE = 0x00000001; 
    private const int CONNECT_COMMANDLINE = 0x00000800; 
    private const int CONNECT_CMD_SAVECRED = 0x00001000; 

    private const int CONNECT_LOCALDRIVE = 0x00000100; 

    #endregion 

    #region Errors 

    private const int NO_ERROR = 0; 

    private const int ERROR_ACCESS_DENIED = 5; 
    private const int ERROR_ALREADY_ASSIGNED = 85; 
    private const int ERROR_BAD_DEVICE = 1200; 
    private const int ERROR_BAD_NET_NAME = 67; 
    private const int ERROR_BAD_PROVIDER = 1204; 
    private const int ERROR_CANCELLED = 1223; 
    private const int ERROR_EXTENDED_ERROR = 1208; 
    private const int ERROR_INVALID_ADDRESS = 487; 
    private const int ERROR_INVALID_PARAMETER = 87; 
    private const int ERROR_INVALID_PASSWORD = 1216; 
    private const int ERROR_MORE_DATA = 234; 
    private const int ERROR_NO_MORE_ITEMS = 259; 
    private const int ERROR_NO_NET_OR_BAD_PATH = 1203; 
    private const int ERROR_NO_NETWORK = 1222; 

    private const int ERROR_BAD_PROFILE = 1206; 
    private const int ERROR_CANNOT_OPEN_PROFILE = 1205; 
    private const int ERROR_DEVICE_IN_USE = 2404; 
    private const int ERROR_NOT_CONNECTED = 2250; 
    private const int ERROR_OPEN_FILES = 2401; 

    #endregion 

    #region PInvoke Signatures 

    [DllImport("Mpr.dll")] 
    private static extern int WNetUseConnection(
     IntPtr hwndOwner, 
     NETRESOURCE lpNetResource, 
     string lpPassword, 
     string lpUserID, 
     int dwFlags, 
     string lpAccessName, 
     string lpBufferSize, 
     string lpResult 
     ); 

    [DllImport("Mpr.dll")] 
    private static extern int WNetCancelConnection2(
     string lpName, 
     int dwFlags, 
     bool fForce 
     ); 

    [StructLayout(LayoutKind.Sequential)] 
    private class NETRESOURCE 
    { 
     public int dwScope = 0; 
     public int dwType = 0; 
     public int dwDisplayType = 0; 
     public int dwUsage = 0; 
     public string lpLocalName = ""; 
     public string lpRemoteName = ""; 
     public string lpComment = ""; 
     public string lpProvider = ""; 
    } 

    #endregion 

    /// <summary> 
    /// Creates a NetworkShareAccesser for the given computer name. The user will be promted to enter credentials 
    /// </summary> 
    /// <param name="remoteComputerName"></param> 
    /// <returns></returns> 
    public static NetworkShareAccesser Access(string remoteComputerName) 
    { 
     return new NetworkShareAccesser(remoteComputerName); 
    } 

    /// <summary> 
    /// Creates a NetworkShareAccesser for the given computer name using the given domain/computer name, username and password 
    /// </summary> 
    /// <param name="remoteComputerName"></param> 
    /// <param name="domainOrComuterName"></param> 
    /// <param name="userName"></param> 
    /// <param name="password"></param> 
    public static NetworkShareAccesser Access(string remoteComputerName, string domainOrComuterName, string userName, string password) 
    { 
     return new NetworkShareAccesser(remoteComputerName, domainOrComuterName + @"\" + userName, password); 
    } 

    /// <summary> 
    /// Creates a NetworkShareAccesser for the given computer name using the given username (format: domainOrComputername\Username) and password 
    /// </summary> 
    /// <param name="remoteComputerName"></param> 
    /// <param name="userName"></param> 
    /// <param name="password"></param> 
    public static NetworkShareAccesser Access(string remoteComputerName, string userName, string password) 
    { 
     return new NetworkShareAccesser(remoteComputerName, userName, password); 
    } 

    private NetworkShareAccesser(string remoteComputerName) 
    { 
     RemoteComputerName = remoteComputerName; 

     ConnectToShare(_remoteUncName, null, null, true); 
    } 

    private NetworkShareAccesser(string remoteComputerName, string userName, string password) 
    { 
     RemoteComputerName = remoteComputerName; 
     UserName = userName; 
     Password = password; 

     ConnectToShare(_remoteUncName, UserName, Password, false); 
    } 

    private void ConnectToShare(string remoteUnc, string username, string password, bool promptUser) 
    { 
     NETRESOURCE nr = new NETRESOURCE 
     { 
      dwType = RESOURCETYPE_DISK, 
      lpRemoteName = remoteUnc 
     }; 

     if (promptUser) 
     { 
      WNetUseConnection(IntPtr.Zero, nr, "", "", CONNECT_INTERACTIVE | CONNECT_PROMPT, null, null, null); 
     } 
     else 
     { 
      WNetUseConnection(IntPtr.Zero, nr, password, username, 0, null, null, null); 
     } 
    } 

    private void DisconnectFromShare(string remoteUnc) 
    { 
     WNetCancelConnection2(remoteUnc, CONNECT_UPDATE_PROFILE, false);   
    } 

    /// <summary> 
    /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources. 
    /// </summary> 
    /// <filterpriority>2</filterpriority> 
    public void Dispose() 
    { 
     DisconnectFromShare(_remoteUncName); 
    } 
} 

它会帮助你连接远程PC,当你有它的凭据。你可以这样使用它:

using (NetworkShareAccesser.Access("1.1.1.1","domain","login","password")) 
{ 
    //Here you have access to remote pc and you can perform your actions 
} 

希望这是你在找什么。

+0

工作就像一个魅力!这正是我正在寻找的 - 一种使用远程PC验证凭据并执行一组选定操作的方法。你在哪里找到那门课?我搜索了大部分的早晨,空了。 – A1raa

+0

@A1raa,很好,这是你正在寻找。几年前我发现了它,所以恐怕我还没有,那是在哪里。 – Sasha

相关问题