C#winforms程序:需要将文件复制到另一台Windows PC上

时间:2016-03-24 17:53:01

标签: c# .net windows file-transfer

我正在尝试编写一个c#winform程序,可以将一些文件复制到另一台Windows PC上。两台PC都运行Windows 7,但目标没有共享文件夹。 我没有运行scp将文件复制到Linux机器上的问题,但在Windows中没有SSH服务器等我:-( 我将获得远程PC的登录详细信息(IP地址,用户名和密码),但我不熟悉在Windows环境中通常如何进行此操作。 该程序的目标是自动将一些更新文件部署到多台机器。我们将无法使用Windows共享来传输这些文件,因为这不比手动登录和通过vnc复制文件快。

1 个答案:

答案 0 :(得分:0)

在互联网上进行了一些研究并对Windows XP机器进行了实验(它是我碰巧在其上使用本地管理员帐户的唯一机器 - 希望它可以在Windows 7机器上正常运行)。 / p>

最终我意识到远程分享是正确的前进方式 - 感谢那些发表评论的人: - )

请注意在示例代码中我使用了一个名为mDisplay的类实例 - 它用于处理我的显示内容,例如显示错误消息或结果,而不是手头问题的核心。

第一个问题 - 如何在没有人工干预的情况下在远程计算机上创建共享。

public bool CreateShare(string ipAddress, string username, string password, string remoteFolder, string sharename)
{
    bool result = false;

    try
    {
        // Create management scope and connect to the remote machine
        ConnectionOptions options = new ConnectionOptions();
        options.Username = username;
        options.Password = password;
        string path = string.Format(@"\\{0}\root\cimv2", ipAddress);
        ManagementScope scope = new ManagementScope(path, options);
        scope.Connect();

        // http://www.c-sharpcorner.com/forums/creating-a-remote-share-using-wmi-in-c-sharp
        ManagementPath winSharePath = new ManagementPath("Win32_Share");
        ManagementClass winShareClass = new ManagementClass(scope, winSharePath, null);
        ManagementBaseObject shareParams = winShareClass.GetMethodParameters("Create");
        shareParams["Path"] = remoteFolder;
        shareParams["Name"] = sharename;
        shareParams["Type"] = 0;
        shareParams["Description"] = "Temporary folder share";
        ManagementBaseObject winShareResult = winShareClass.InvokeMethod("Create", shareParams, null);

        result = true;
    }
    catch (Exception ex)
    {
        mDisplay.showError("FAILED to create share: " + ex.Message.ToString());
    }

    return result;
}

第二个问题 - 将文件从本地计算机复制到远程计算机

感谢How to create a recursive function to copy all files and folders代码的基础。 我的版本不一定是最有效或最紧凑的工作方式,但它对我有用。

public bool CopyFiles(bool overwrite, string ipAddress, string sharename, string copySource)
{
    bool result = false;

    string path = string.Format(@"\\{0}\{1}", ipAddress, sharename);

    if (!Directory.Exists(path))
    {
        mDisplay.appendToResults("Share doesn't exist \"" + path + "\" - are you sure it mapped ok?");
        return result;
    }

    if (!Directory.Exists(copySource))
    {
        mDisplay.appendToResults("Source folder \"" + copySource + "\" doesn't exist, need to specify where to copy file(s) from");
        return result;
    }

    recursivelyCopyContents(copySource, overwrite, path);
    result = true;

    return result;
}
private void recursivelyCopyContents(string sourceDirName, bool overwrite, string destDirName)
{
    try
    {
        // Get the subdirectories for the specified directory.
        DirectoryInfo dir = new DirectoryInfo(sourceDirName);

        if (!dir.Exists)
        {
            throw new DirectoryNotFoundException(
                "Source directory does not exist or could not be found: "
                + sourceDirName);
        }

        DirectoryInfo[] dirs = dir.GetDirectories();
        // If the destination directory doesn't exist, create it.
        if (!Directory.Exists(destDirName))
        {
            mDisplay.appendToResults("Creating folder " + destDirName);
            Directory.CreateDirectory(destDirName);
        }

        // Get the files in the directory and copy them to the new location.
        FileInfo[] files = dir.GetFiles();
        foreach (FileInfo file in files)
        {
            string temppath = Path.Combine(destDirName, file.Name);

            string info = "Copying " + file.Name + " -> " + temppath;


            if (!overwrite && File.Exists(temppath))
            {
                // Not overwriting - so show it already exists
                mDisplay.appendToResults(info + " (already exists)");
            }
            else
            {
                file.CopyTo(temppath, overwrite);
                mDisplay.appendToResults(info + " OK");
            }
        }

        foreach (DirectoryInfo subdir in dirs)
        {
            string temppath = Path.Combine(destDirName, subdir.Name);
            recursivelyCopyContents(subdir.FullName, overwrite, temppath);
        }
    }
    catch (Exception ex)
    {
        mDisplay.showError("Problem encountered during copy : " + ex.Message);
    }
}

最后 - 删除我之前创建的远程共享,不要让它留在远程计算机上。

public bool RemoveShare(string username, string password, string ipAddress, string sharename)
{
    bool result = false;

    try
    {
        // Create management scope and connect to the remote machine
        ConnectionOptions options = new ConnectionOptions();
        options.Username = username;
        options.Password = password;
        string path = string.Format(@"\\{0}\root\cimv2", ipAddress);
        ManagementScope scope = new ManagementScope(path, options);
        scope.Connect();

        // Inspiration from here: https://danv74.wordpress.com/2011/01/11/list-network-shares-in-c-using-wmi/
        var query = new ObjectQuery(string.Format("select * from win32_share where Name=\"{0}\"", sharename));
        var finder = new ManagementObjectSearcher(scope, query);
        var shares = finder.Get();

        foreach (ManagementObject share in shares)
        {
            share.Delete();
        }

        mDisplay.appendToResults("Share deleted");
        result = true;
    }
    catch (Exception ex)
    {
        mDisplay.showError("FAILED to remove share: " + ex.Message.ToString());
    }

    return result;
}