From d27c15d2aeec7458afc7563049c3a931bf75f352 Mon Sep 17 00:00:00 2001
From: Yuanle Song <sylecn@gmail.com>
Date: Thu, 14 Nov 2019 01:30:56 +0800
Subject: [PATCH] rsync over ssh works.

---
 Program.fs                          | 33 +++++++++++++++--------------
 mbackup-config/mbackup-default.list |  6 +++---
 operational                         | 12 ++++++++++-
 3 files changed, 31 insertions(+), 20 deletions(-)

diff --git a/Program.fs b/Program.fs
index 28ee008..d1f7442 100644
--- a/Program.fs
+++ b/Program.fs
@@ -29,6 +29,7 @@ type CLIArguments =
     | Remote_User of remoteUser: string
     | [<AltCommandLine("-i")>] Itemize_Changes
     | Node_Name of nodeName: string
+    | Ssh_Key of sshKeyFilename: string
 with
     interface IArgParserTemplate with
         member s.Usage =
@@ -38,6 +39,7 @@ with
             | Remote_User _ -> "remote linux user to own the backup files"
             | Itemize_Changes _ -> "add -i option to rsync"
             | Node_Name _ -> "local node's name, used in remote logging"
+            | Ssh_Key _ -> "ssh private key, used when backup to remote ssh node"
 
 type Logger() =
   let mutable level = Logger.DEBUG
@@ -105,12 +107,18 @@ let EnsureWinDir (path: string) = if path.EndsWith "\\" then path else path + "\
 let appDataRoamingDir = Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData) |> ToMingwPath |> EnsureDir
 let programDataDirWin = GetEnv "PROGRAMDATA" |> EnsureWinDir
 let programDataDir = ToMingwPath programDataDirWin
-let appDataLocalDirWin =  Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) |> EnsureDir
-let appDataLocalDir =  appDataLocalDirWin|> ToMingwPath
+let appDataLocalDirWin =  Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) |> EnsureWinDir
+let appDataLocalDir =  appDataLocalDirWin |> ToMingwPath
 
 let mbackupInstallDirWin = Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles) |> EnsureDir |> fun s -> s + "mbackup"
 let mbackupInstallDir = mbackupInstallDirWin |> ToMingwPath
 
+let userHomeWin =
+  GetEnvDefault "HOME" (Environment.GetFolderPath(Environment.SpecialFolder.UserProfile))
+  |> EnsureWinDir
+
+let userHome = userHomeWin |> ToMingwPath
+
 //let userConfigDir = appDataRoamingDir + "mbackup/"
 let userConfigDirWin = programDataDirWin + "mbackup\\"
 let userConfigDir = programDataDir + "mbackup/"
@@ -142,7 +150,6 @@ let expandUserFile (fn: string) =
   if fn.StartsWith("/") then
     fn
   else
-    let userHome = Environment.GetFolderPath(Environment.SpecialFolder.UserProfile) |> ToMingwPath |> EnsureDir
     userHome + fn
 
 // generate mbackup.list file
@@ -159,10 +166,10 @@ let generateMbackupList (logger: Logger) =
     let readMbackupListFile fn = File.ReadAllLines(fn) |> dropEmptyLinesAndComments
 
     try
-      let defaultListLines = readMbackupListFile mbackupDefaultList
+      let defaultListLines = readMbackupListFile mbackupDefaultList |> Seq.map ToMingwPath
       let localListLinesMaybe =
         try
-          let lines = readMbackupListFile mbackupLocalList
+          let lines = readMbackupListFile mbackupLocalList |> Seq.map ToMingwPath
           (true, lines)
         with
           | :? System.IO.FileNotFoundException ->
@@ -199,8 +206,8 @@ let main argv =
 
     let logger = Logger()
 
-    logger.Info "userConfigDir=%s" userConfigDir
-    logger.Info "runtimeDir=%s" runtimeDir
+    logger.Info "using user config dir: %s" userConfigDirWin
+    logger.Info "using runtime dir: %s" runtimeDirWin
 
     let rsyncCmd: string list = []
     let rsyncCmd = appendWhen dryRun rsyncCmd "--dry-run"
@@ -224,8 +231,8 @@ let main argv =
     let mbackupInstallDirWinTest = "D:\\downloads\\apps\\mbackupTest\\"
     let mbackupInstallDirTest = mbackupInstallDirWinTest |> ToMingwPath |> EnsureDir
     let sshExeFile = mbackupInstallDirTest + "rsync-w64/usr/bin/ssh.exe"
-    let sshConfigFile = userConfigDir + "ssh_config"
-    let sshPrivateKeyFile = userConfigDir + "ssh_id_rsa"
+    let sshConfigFile = userHome + ".ssh/config"
+    let sshPrivateKeyFile = results.GetResult(Ssh_Key, defaultValue = userHome + ".ssh/id_rsa") |> ToMingwPath
     let rsyncCmd = List.append rsyncCmd [sprintf "-e \"%s -F %s -i %s -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null\"" sshExeFile sshConfigFile sshPrivateKeyFile]
 
     let backupTarget = results.GetResult (Target, defaultValue = Environment.GetEnvironmentVariable "TARGET")
@@ -238,13 +245,7 @@ let main argv =
           let rsyncCmd =
             if not (isLocalTarget backupTarget)
               then
-                let nodeName =
-                  match results.GetResult Node_Name with
-                    | null ->
-                      match GetEnv "NODE_NAME" with
-                        | null -> Net.Dns.GetHostName()
-                        | X -> X
-                    | X -> X
+                let nodeName = results.GetResult(Node_Name, defaultValue = Net.Dns.GetHostName())
                 let remoteLogFile = sprintf "/var/log/mbackup/%s.log" nodeName
                 let remoteUser = results.GetResult (Remote_User, defaultValue = Environment.UserName)
                 let rsyncCmd = List.append rsyncCmd [sprintf "--remote-option=--log-file=%s" remoteLogFile]
diff --git a/mbackup-config/mbackup-default.list b/mbackup-config/mbackup-default.list
index 7a9fbb3..ce01a57 100644
--- a/mbackup-config/mbackup-default.list
+++ b/mbackup-config/mbackup-default.list
@@ -1,4 +1,4 @@
 # dirs to backup
-/cygdrive/c/ProgramData/mbackup
-/cygdrive/c/path/to/dir
-/cygdrive/d/path/to/dir
+C:\ProgramData\mbackup
+C:\path\to\dir
+D:\path\to\dir
diff --git a/operational b/operational
index 8cfaefa..758ab17 100644
--- a/operational
+++ b/operational
@@ -8,6 +8,15 @@ dotnet run -- --dry-run --itemize-changes --target d:\backup
 dotnet run -- -n -i --target d:\backup
 dotnet run -- -n --target d:\backup
 
+try an ssh run:
+
+dotnet run -- -n --target root@sylecn01.emacsos.com:/data/backup/PC-backup/B75I3/
+it works.
+
+file list works.
+ssh transfer works.
+remote logging works.
+
 ** 2019-11-12 docs
 - rsync
   https://www.samba.org/ftp/rsync/rsync.html
@@ -50,9 +59,9 @@ dotnet run -- -n --target d:\backup
   http://fsprojects.github.io/FSharpLint/index.html
 
 * later                                                               :entry:
+** 2019-11-14 supports expand Downloads dir in user-default.list
 * current                                                             :entry:
 ** 
-** 2019-11-13 build mbackup.list file from file list and exclude lists.
 ** 2019-11-13 extra user default list.
 Documents is replaced by real path.
 Downloads
@@ -213,4 +222,5 @@ C:\ProgramData\mbackup\user-default.list
     it contains hostname.
   - 
 * done                                                                :entry:
+** 2019-11-13 build mbackup.list file from file list and exclude lists.
 * wontfix                                                             :entry:
-- 
GitLab