Browse Source

Fix differnt SCP Upload issue.
Remove not SCP feature of creating directory structure for uploaded files or directories

olegkap_cp 12 năm trước cách đây
mục cha
commit
b04d660cd6
1 tập tin đã thay đổi với 59 bổ sung57 xóa
  1. 59 57
      Renci.SshClient/Renci.SshNet/ScpClient.NET.cs

+ 59 - 57
Renci.SshClient/Renci.SshNet/ScpClient.NET.cs

@@ -18,15 +18,19 @@ namespace Renci.SshNet
     public partial class ScpClient
     {
         private static Regex _rootPath = new Regex(@"^(/|[A-Z][:])", RegexOptions.Compiled | RegexOptions.IgnoreCase);
+
         /// <summary>
-        /// Uploads the specified file or directory to the remote host.
+        /// Uploads the specified file to the remote host.
         /// </summary>
-        /// <param name="fileInfo">Local file to upload.</param>
-        /// <param name="filename">Remote host file name.</param>
-        /// <exception cref="ArgumentNullException"><paramref name="fileInfo"/> or <paramref name="filename"/> is null.</exception>
-        public void Upload(FileSystemInfo fileSystemInfo, string path)
+        /// <param name="fileInfo">The file system info.</param>
+        /// <param name="path">The path.</param>
+        /// <exception cref="System.ArgumentNullException">fileSystemInfo</exception>
+        /// <exception cref="System.ArgumentException">path</exception>
+        /// <exception cref="System.NotSupportedException"></exception>
+        /// <exception cref="ArgumentNullException"><paramref name="fileInfo" /> or <paramref name="filename" /> is null.</exception>
+        public void Upload(FileInfo fileInfo, string path)
         {
-            if (fileSystemInfo == null)
+            if (fileInfo == null)
                 throw new ArgumentNullException("fileSystemInfo");
 
             if (string.IsNullOrEmpty(path))
@@ -43,56 +47,54 @@ namespace Renci.SshNet
 
                 channel.Open();
 
-                var isRootPath = _rootPath.Match(path);
+                //  Send channel command request
+                channel.SendExecRequest(string.Format("scp -t \"{0}\"", path));
+                this.CheckReturnCode(input);
 
-                var pathParts = path.Split('\\', '/');
-                var targetPath = path;
+                this.InternalUpload(channel, input, fileInfo, fileInfo.Name);
 
-                if (isRootPath.Success)
-                {
-                    //  Send channel command request
-                    channel.SendExecRequest(string.Format("scp -rt \"{0}\"", path));
-                    this.CheckReturnCode(input);
-                }
-                else
-                {
-                    targetPath = pathParts.Last();
+                channel.Close();
+            }
+        }
 
-                    //  Send channel command request
-                    channel.SendExecRequest(string.Format("scp -rt \"{0}\"", pathParts[0]));
-                    this.CheckReturnCode(input);
+        /// <summary>
+        /// Uploads the specified directory to the remote host.
+        /// </summary>
+        /// <param name="directoryInfo">The directory info.</param>
+        /// <param name="path">The path.</param>
+        /// <exception cref="System.ArgumentNullException">fileSystemInfo</exception>
+        /// <exception cref="System.ArgumentException">path</exception>
+        public void Upload(DirectoryInfo directoryInfo, string path)
+        {
+            if (directoryInfo == null)
+                throw new ArgumentNullException("fileSystemInfo");
 
-                    //  Prepare directory structure
-                    for (int i = 0; i < pathParts.Length - 1; i++)
-                    {
-                        this.InternalSetTimestamp(channel, input, fileSystemInfo.LastWriteTimeUtc, fileSystemInfo.LastAccessTimeUtc);
-                        this.SendData(channel, string.Format("D0755 0 {0}\n", pathParts[i]));
-                        this.CheckReturnCode(input);
-                    }
-                }
+            if (string.IsNullOrEmpty(path))
+                throw new ArgumentException("path");
 
-                if (fileSystemInfo is FileInfo)
-                {
-                    this.InternalUpload(channel, input, fileSystemInfo as FileInfo, targetPath);
-                }
-                else if (fileSystemInfo is DirectoryInfo)
-                {
-                    this.InternalUpload(channel, input, fileSystemInfo as DirectoryInfo, targetPath);
-                }
-                else
+            using (var input = new PipeStream())
+            using (var channel = this.Session.CreateChannel<ChannelSession>())
+            {
+                channel.DataReceived += delegate(object sender, Common.ChannelDataEventArgs e)
                 {
-                    throw new NotSupportedException(string.Format("Type '{0}' is not supported.", fileSystemInfo.GetType().FullName));
-                }
+                    input.Write(e.Data, 0, e.Data.Length);
+                    input.Flush();
+                };
 
-                if (!isRootPath.Success)
-                {
-                    //  Finish directory structure
-                    for (int i = 0; i < pathParts.Length - 1; i++)
-                    {
-                        this.SendData(channel, "E\n");
-                        this.CheckReturnCode(input);
-                    }
-                }
+                channel.Open();
+
+                //  Send channel command request
+                channel.SendExecRequest(string.Format("scp -rt \"{0}\"", path));
+                this.CheckReturnCode(input);
+
+                this.InternalSetTimestamp(channel, input, directoryInfo.LastWriteTimeUtc, directoryInfo.LastAccessTimeUtc);
+                this.SendData(channel, string.Format("D0755 0 {0}\n", Path.GetFileName(path)));
+                this.CheckReturnCode(input);
+
+                this.InternalUpload(channel, input, directoryInfo as DirectoryInfo, directoryInfo.Name);
+
+                this.SendData(channel, "E\n");
+                this.CheckReturnCode(input);
 
                 channel.Close();
             }
@@ -177,12 +179,8 @@ namespace Renci.SshNet
             }
         }
 
-        private void InternalUpload(ChannelSession channel, PipeStream input, DirectoryInfo directoryInfo, string directoryName)
+        private void InternalUpload(ChannelSession channel, Stream input, DirectoryInfo directoryInfo, string directoryName)
         {
-            this.InternalSetTimestamp(channel, input, directoryInfo.LastWriteTimeUtc, directoryInfo.LastAccessTimeUtc);
-            this.SendData(channel, string.Format("D0755 0 {0}\n", directoryName));
-            this.CheckReturnCode(input);
-
             //  Upload files
             var files = directoryInfo.GetFiles();
             foreach (var file in files)
@@ -194,11 +192,15 @@ namespace Renci.SshNet
             var directories = directoryInfo.GetDirectories();
             foreach (var directory in directories)
             {
+                this.InternalSetTimestamp(channel, input, directoryInfo.LastWriteTimeUtc, directoryInfo.LastAccessTimeUtc);
+                this.SendData(channel, string.Format("D0755 0 {0}\n", directory.Name));
+                this.CheckReturnCode(input);
+
                 this.InternalUpload(channel, input, directory, directory.Name);
-            }
 
-            this.SendData(channel, "E\n");
-            this.CheckReturnCode(input);
+                this.SendData(channel, "E\n");
+                this.CheckReturnCode(input);
+            }
         }
 
         private void InternalDownload(ChannelSession channel, Stream input, FileSystemInfo fileSystemInfo)