|
|
|
@ -4,7 +4,7 @@ PROGRAM="osync" # Rsync based two way sync engine with fault tolerance
|
|
|
|
|
AUTHOR="(C) 2013-2016 by Orsiris de Jong"
|
|
|
|
|
CONTACT="http://www.netpower.fr/osync - ozy@netpower.fr"
|
|
|
|
|
PROGRAM_VERSION=1.1-dev
|
|
|
|
|
PROGRAM_BUILD=2016040201
|
|
|
|
|
PROGRAM_BUILD=2016040303
|
|
|
|
|
IS_STABLE=yes
|
|
|
|
|
|
|
|
|
|
## FUNC_BUILD=2016040102
|
|
|
|
@ -1186,6 +1186,7 @@ function _CreateStateDirsRemote {
|
|
|
|
|
fi
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#TODO: also create deleted and backup dirs
|
|
|
|
|
function CreateStateDirs {
|
|
|
|
|
__CheckArguments 0 $# ${FUNCNAME[0]} "$@" #__WITH_PARANOIA_DEBUG
|
|
|
|
|
|
|
|
|
@ -1603,7 +1604,9 @@ function _get_file_ctime_mtime_local {
|
|
|
|
|
local file_list="${3}" # Contains list of files to get time attrs
|
|
|
|
|
__CheckArguments 3 $# ${FUNCNAME[0]} "$@" #__WITH_PARANOIA_DEBUG
|
|
|
|
|
|
|
|
|
|
cat "$file_list" | xargs -I {} stat -c '%n;%Z;%Y' "$replica_path{}" | sort > "$RUN_DIR/$PROGRAM.ctime_mtime.$replica_type.$SCRIPT_PID"
|
|
|
|
|
#cat "$file_list" | xargs -I {} stat -c '%n;%Z;%Y' "$replica_path{}" | sort > "$RUN_DIR/$PROGRAM.ctime_mtime.$replica_type.$SCRIPT_PID"
|
|
|
|
|
echo -n "" > "$RUN_DIR/$PROGRAM.ctime_mtime.$replica_type.$SCRIPT_PID"
|
|
|
|
|
while read file; do stat -c '%n;%Z;%Y' "$replica_path$file" | sort > "$RUN_DIR/$PROGRAM.ctime_mtime.$replica_type.$SCRIPT_PID"; done < "$file_list"
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
function _get_file_ctime_mtime_remote {
|
|
|
|
@ -1613,10 +1616,9 @@ function _get_file_ctime_mtime_remote {
|
|
|
|
|
__CheckArguments 3 $# ${FUNCNAME[0]} "$@" #__WITH_PARANOIA_DEBUG
|
|
|
|
|
|
|
|
|
|
local cmd=
|
|
|
|
|
# TODO: test
|
|
|
|
|
cmd='cat "'$file_list'" | '$SSH_CMD' cat | xargs -I "{}" stat -c "%n;%Z;%Y" "'$replica_path'{}" | sort > "'$RUN_DIR/$PROGRAM.ctime_mtime.$replica_type.$SCRIPT_PID'"'
|
|
|
|
|
cmd='cat "'$file_list'" | '$SSH_CMD' "while read file; do stat -c \"%n;%Z;%Y\" \"'$replica_path'\$file\"; done | sort" > "'$RUN_DIR/$PROGRAM.ctime_mtime.$replica_type.$SCRIPT_PID'"'
|
|
|
|
|
Logger "CMD: $cmd" "DEBUG"
|
|
|
|
|
eval "$cmd"
|
|
|
|
|
eval $cmd
|
|
|
|
|
WaitForCompletion $! $SOFT_MAX_EXEC_TIME $HARD_MAX_EXEC_TIME ${FUNCNAME[0]}
|
|
|
|
|
if [ $? != 0 ]; then
|
|
|
|
|
Logger "Getting file attributes failed [$retval] on $replica_type. Stopping execution." "CRITICAL"
|
|
|
|
@ -1682,20 +1684,31 @@ function sync_attrs {
|
|
|
|
|
|
|
|
|
|
# If target gets updated first, then sync_attr must update initiator's attrs first
|
|
|
|
|
# For join, remove leading replica paths
|
|
|
|
|
|
|
|
|
|
sed -i "s;^${INITIATOR[1]};;g" "$RUN_DIR/$PROGRAM.ctime_mtime.${INITIATOR[0]}.$SCRIPT_PID"
|
|
|
|
|
sed -i "s;^${TARGET[1]};;g" "$RUN_DIR/$PROGRAM.ctime_mtime.${TARGET[0]}.$SCRIPT_PID"
|
|
|
|
|
|
|
|
|
|
if [ "$CONFLICT_PREVALANCE" == "${TARGET[0]}" ]; then
|
|
|
|
|
local source_dir="${INITIATOR[1]}"
|
|
|
|
|
local esc_source_dir=$(EscapeSpaces "${INITIATOR[1]}")
|
|
|
|
|
local dest_dir="${TARGET[1]}"
|
|
|
|
|
local esc_dest_dir=$(EscapeSpaces "${TARGET[1]}")
|
|
|
|
|
local dest_replica="${TARGET[0]}"
|
|
|
|
|
sed -i "s;^${TARGET[1]};;g" "$RUN_DIR/$PROGRAM.ctime_mtime.${TARGET[0]}.$SCRIPT_PID"
|
|
|
|
|
join -j 1 -t ';' -o 1.1,1.2,2.2 "$RUN_DIR/$PROGRAM.ctime_mtime.${INITIATOR[0]}.$SCRIPT_PID" "$RUN_DIR/$PROGRAM.ctime_mtime.${TARGET[0]}.$SCRIPT_PID" | awk -F';' '{if ($2 > $3) print $1}' > "$RUN_DIR/$PROGRAM.${FUNCNAME[0]}-ctime_files.$SCRIPT_PID"
|
|
|
|
|
else
|
|
|
|
|
local source_dir="${TARGET[1]}"
|
|
|
|
|
local esc_source_dir=$(EscapeSpaces "${TARGET[1]}")
|
|
|
|
|
local dest_dir="${INITIATOR[1]}"
|
|
|
|
|
local esc_dest_dir=$(EscapeSpaces "${INITIATOR[1]}")
|
|
|
|
|
local dest_replica="${INITIATOR[0]}"
|
|
|
|
|
sed -i "s;^${INITIATOR[1]};;g" "$RUN_DIR/$PROGRAM.ctime_mtime.${INITIATOR[0]}.$SCRIPT_PID"
|
|
|
|
|
join -j 1 -t ';' -o 1.1,1.2,2.2 "$RUN_DIR/$PROGRAM.ctime_mtime.${TARGET[0]}.$SCRIPT_PID" "$RUN_DIR/$PROGRAM.ctime_mtime.${INITIATOR[0]}.$SCRIPT_PID" | awk -F';' '{if ($2 > $3) print $1}' > "$RUN_DIR/$PROGRAM.${FUNCNAME[0]}-ctime_files.$SCRIPT_PID"
|
|
|
|
|
fi
|
|
|
|
|
|
|
|
|
|
if [ $(wc -l < "$RUN_DIR/$PROGRAM.${FUNCNAME[0]}-ctime_files.$SCRIPT_PID") -eq 0 ]; then
|
|
|
|
|
Logger "Updating file attributes on $dest_replica not required" "NOTICE"
|
|
|
|
|
return 0
|
|
|
|
|
fi
|
|
|
|
|
|
|
|
|
|
Logger "Updating file attributes on $dest_replica." "NOTICE"
|
|
|
|
|
|
|
|
|
|
if [ "$REMOTE_OPERATION" == "yes" ]; then
|
|
|
|
@ -1703,8 +1716,8 @@ function sync_attrs {
|
|
|
|
|
CheckConnectivityRemoteHost
|
|
|
|
|
|
|
|
|
|
# No rsync args (hence no -r) because files are selected with --from-file
|
|
|
|
|
if [ "$dest" == "${INITIATOR[0]}" ]; then
|
|
|
|
|
rsync_cmd="$(type -p $RSYNC_EXECUTABLE) --rsync-path=\"$RSYNC_PATH\" $RSYNC_DRY_ARG $RSYNC_ATTR_ARGS $SYNC_OPTS -e \"$RSYNC_SSH_CMD\" --exclude \"$OSYNC_DIR\" $RSYNC_PATTERNS $RSYNC_PARTIAL_EXCLUDE --exclude-from=\"${INITIATOR[1]}${INITIATOR[3]}/${INITIATOR[0]}$delete_list_filename\" --exclude-from=\"${INITIATOR[1]}${INITIATOR[3]}/${TARGET[0]}$delete_list_filename\" --files-from=\"$RUN_DIR/$PROGRAM.${FUNCNAME[0]}-ctime_files.$SCRIPT_PID\" $REMOTE_USER@REMOTE_HOST:\"$esc_source_dir\" \"$dest_dir\" > $RUN_DIR/$PROGRAM.attr-update.$dest_replica.$SCRIPT_PID 2>&1 &"
|
|
|
|
|
if [ "$dest_replica" == "${INITIATOR[0]}" ]; then
|
|
|
|
|
rsync_cmd="$(type -p $RSYNC_EXECUTABLE) --rsync-path=\"$RSYNC_PATH\" $RSYNC_DRY_ARG $RSYNC_ATTR_ARGS $SYNC_OPTS -e \"$RSYNC_SSH_CMD\" --exclude \"$OSYNC_DIR\" $RSYNC_PATTERNS $RSYNC_PARTIAL_EXCLUDE --exclude-from=\"${INITIATOR[1]}${INITIATOR[3]}/${INITIATOR[0]}$delete_list_filename\" --exclude-from=\"${INITIATOR[1]}${INITIATOR[3]}/${TARGET[0]}$delete_list_filename\" --files-from=\"$RUN_DIR/$PROGRAM.${FUNCNAME[0]}-ctime_files.$SCRIPT_PID\" $REMOTE_USER@$REMOTE_HOST:\"$esc_source_dir\" \"$dest_dir\" > $RUN_DIR/$PROGRAM.attr-update.$dest_replica.$SCRIPT_PID 2>&1 &"
|
|
|
|
|
else
|
|
|
|
|
rsync_cmd="$(type -p $RSYNC_EXECUTABLE) --rsync-path=\"$RSYNC_PATH\" $RSYNC_DRY_ARG $RSYNC_ATTR_ARGS $SYNC_OPTS -e \"$RSYNC_SSH_CMD\" --exclude \"$OSYNC_DIR\" $RSYNC_PATTERNS $RSYNC_PARTIAL_EXCLUDE --exclude-from=\"${INITIATOR[1]}${INITIATOR[3]}/${INITIATOR[0]}$delete_list_filename\" --exclude-from=\"${INITIATOR[1]}${INITIATOR[3]}/${TARGET[0]}$delete_list_filename\" --files-from=\"$RUN_DIR/$PROGRAM.${FUNCNAME[0]}-ctime_files.$SCRIPT_PID\" \"$source_dir\" $REMOTE_USER@$REMOTE_HOST:\"$esc_dest_dir\" > $RUN_DIR/$PROGRAM.attr-update.$dest_replica.$SCRIPT_PID 2>&1 &"
|
|
|
|
|
fi
|
|
|
|
@ -1717,14 +1730,14 @@ function sync_attrs {
|
|
|
|
|
eval "$rsync_cmd"
|
|
|
|
|
WaitForCompletion $! $SOFT_MAX_EXEC_TIME $HARD_MAX_EXEC_TIME ${FUNCNAME[0]}
|
|
|
|
|
retval=$?
|
|
|
|
|
if [ $_VERBOSE -eq 1 ] && [ -f "$RUN_DIR/$PROGRAM.${FUNCNAME[0]}-attrfiles.$SCRIPT_PID" ]; then
|
|
|
|
|
Logger "List:\n$(cat $RUN_DIR/$PROGRAM.$FUNCNAM-attrfiles.$SCRIPT_PID)" "NOTICE"
|
|
|
|
|
if [ $_VERBOSE -eq 1 ] && [ -f "$RUN_DIR/$PROGRAM.attr-update.$dest_replica.$SCRIPT_PID" ]; then
|
|
|
|
|
Logger "List:\n$(cat $RUN_DIR/$PROGRAM.attr-update.$dest_replica.$SCRIPT_PID)" "NOTICE"
|
|
|
|
|
fi
|
|
|
|
|
|
|
|
|
|
if [ $retval != 0 ] && [ $retval != 24 ]; then
|
|
|
|
|
Logger "Updating file attributes on $source [$retval]. Stopping execution." "CRITICAL"
|
|
|
|
|
if [ $_VERBOSE -eq 0 ] && [ -f "$RUN_DIR/$PROGRAM.${FUNCNAME[0]}-attrfiles.$SCRIPT_PID" ]; then
|
|
|
|
|
Logger "Rsync output:\n$(cat $RUN_DIR/$PROGRAM.${FUNCNAME[0]}-attrfiles.$SCRIPT_PID)" "NOTICE"
|
|
|
|
|
if [ $_VERBOSE -eq 0 ] && [ -f "$RUN_DIR/$PROGRAM.attr-update.$dest_replica.$SCRIPT_PID" ]; then
|
|
|
|
|
Logger "Rsync output:\n$(cat $RUN_DIR/$PROGRAM.attr-update.$dest_replica.$SCRIPT_PID)" "NOTICE"
|
|
|
|
|
fi
|
|
|
|
|
exit $retval
|
|
|
|
|
else
|
|
|
|
|