Reputation: 404
I have searched high and low, but cannot seem to find a solution to this problem (maybe it doesn't exist?). Here is my problem:
I have a file on my local machine called myFile.txt. There is a file on a remote machine with the same name (myFile.txt). Both file structures look like this:
<tag1>November 22, 2012<tag1>
<tag2>version5.8<tag2>
<tag3>ASDFA23RASDF29ASDJ29DJ2<tag3>
Both files have this exact same layout. I need to write a script keeps the string in between <tag3>
in sync for the two files (local and remote). I need to get the string from <tag3>
on the remote server and compare it to the same string on my local machine. If there is a difference I need to change my local string to reflect the remote one.
What I've tried thus far: I've grabbed the local string using awk, and assigned it to a variable. Easy enough. I ssh'ed into the remote server and attempted to use the same method to assign the remote string to a variable. As far as I can tell, this seems to be working. The issue is the variable doesn't come back to my local machine with a value (if that makes sense). This is how I'm attempting to do this:
#!/bin/bash
fileName="myFile.txt"
logon="[email protected]"
localString=$(awk -F "<tag3>" '{print $2}' $fileName)
x=$(ssh $logon "remoteString=$(awk -F "<tag3>" '{print $2}' $fileName); echo $remoteString")
echo "remote string = $x"
if [ $localString == $x ]; then
echo "The 2 auth keys are EQUAL!!!"
else
echo "The 2 auth keys are NOT equal!!!"
fi
I can see the variable being assigned when I echo out $remoteString. From my understanding this is happening on the remote server though as I'm getting the correct string printed to console followed by "command not found". The next line echo's "remote string = ". So $x is either losing it's value or is never properly assigned. I've tried varying this line where $x is assigned many many time, but have not had any luck.
Other ideas: If this isn't possible I'm beginning to think maybe I need to do a scp of the file, bring it over to my server, make the comparison, and then delete the copied filed. I would need to change the name of the copy before moving it to my local machine, or else I will overwrite my file. Also, it would seem more efficient not to have to make a secure copy because this script will have to run on many machines, and the file will potentially be a lot bigger than 3 lines. I've looked into diff, but can't find a way to get it to compare just one line.
I am fairly new to bash scripting so please forgive me if I am missing something obvious. Thank you for any help as it is greatly appreciated.
Upvotes: 3
Views: 1121
Reputation: 46823
You can use something along these lines:
#!/bin/bash
fileName="myFile.txt"
logon="[email protected]"
sedcommand='/^<tag3>.*<tag3>$/{s/<tag3>\(.*\)<tag3>/\1/p;q}'
localString=$( sed -n $sedcommand "$fileName" )
remoteString=$( ssh "$logon" "sed -n '$sedcommand' \"$fileName\"" )
if [[ $localString == $remoteString ]]; then
echo "The 2 auth keys are EQUAL!!!"
else
echo "The 2 auth keys are NOT equal!!!"
fi
(which seems simpler than your method). The sed
command finds the first occurence of a line starting by <tag3>
and ending by <tag3>
and removes the tags so as to transfer only the "auth key". There's no guard against files that don't exist, or against the tag not being find. This detail is left to the reader. But the script is safe regarding spaces in file names and doesn't use two nested subshells!
Upvotes: 1
Reputation: 15560
There's a escaping issue with the ssh
commands - you should escape the $
inside the ssh
parameters.
Then, I just replaced the remoteString=$(awk ....); echo $remoteString
with just awk ....
. If not, there was some issue with a leading blank line that made the strings to not match - and it seems pretty useless to store a command's output just to echo
ing it.
#!/bin/bash
fileName="myFile.txt"
logon="[email protected]"
localString=$(awk -F "<tag3>" '{print $2}' $fileName)
x=$(ssh $logon "awk -F '<tag3>' '{print \$2}' $fileName")
echo "remote string = $x"
if [ "$localString" == "$x" ]; then
echo "The 2 auth keys are EQUAL!!!"
else
echo "The 2 auth keys are NOT equal!!!"
fi
Upvotes: 1
Reputation: 47267
Try changing this line:
x=$(ssh $logon "remoteString=$(awk -F "<tag3>" '{print $2}' $fileName); echo $remoteString")
to
x=$(ssh $logon "remoteString=$(awk -F '<tag3>' '{print $2}' $fileName); echo $remoteString")
i.e.: change "<tag3>"
to '<tag3>'
I have a feeling that your current use of the double quotes is actually breaking the intended use of your ssh command.
As a side note: always wrap your variables in double quotes when you single [
's for condition tests:
if [ $localString == $x ]; then
would be safer as:
if [ "$localString" == "$x" ]; then
or
# this also works, but less portable
if [[ $localString == $x ]]; then
The reason is that if either variable evaluates to the null string (suppose in this case x
is empty), bash would see something like this instead: if [ ASDFA23RASDF29ASDJ29DJ2 == ]; then
Upvotes: 0