Thanks to visit codestin.com
Credit goes to github.com

Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 6 additions & 1 deletion bin/ghe-restore
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,12 @@ bm_end "ghe-import-redis"

if $cluster; then
echo "Restoring Git repositories into cluster ..."
ghe-restore-repositories-dgit "$GHE_HOSTNAME" 1>&3
if ghe-ssh "$GHE_HOSTNAME" test -f /data/github/current/script/dgit-cluster-restore-routes; then
ghe_verbose "* Using ghe-restore-repositories-dgit-ng to restore"
ghe-restore-repositories-dgit-ng "$GHE_HOSTNAME" 1>&3
else
ghe-restore-repositories-dgit "$GHE_HOSTNAME" 1>&3
fi

echo "Restoring Gists into cluster ..."
if ghe-ssh "$GHE_HOSTNAME" test -f /data/github/current/script/gist-cluster-restore-routes; then
Expand Down
146 changes: 146 additions & 0 deletions share/github-backup-utils/ghe-restore-repositories-dgit-ng
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
#!/usr/bin/env bash
#/ Usage: ghe-restore-repositories-dgit-ng <host>
#/ Restore repositories fron an rsync snapshot of all Git repository data to a GitHub cluster.
#/
#/ Note: This script typically isn't called directly. It's invoked by the
#/ ghe-restore command when restoring into a cluster.
set -e

# Bring in the backup configuration
. $( dirname "${BASH_SOURCE[0]}" )/ghe-backup-config

# Show usage and bail with no arguments
[ -z "$*" ] && print_usage

bm_start "$(basename $0)"

# Grab host arg
GHE_HOSTNAME="$1"

# The snapshot to restore should be set by the ghe-restore command but this lets
# us run this script directly.
: ${GHE_RESTORE_SNAPSHOT:=current}

network_paths=$(cd $GHE_DATA_DIR/$GHE_RESTORE_SNAPSHOT/ && find repositories -mindepth 6 -maxdepth 7 -name \*.git -exec dirname {} \; | uniq | grep nw | cut -d / -f2-)

if [ -z "$network_paths" ]; then
echo "Warning: Repositories backup missing. Skipping ..."
exit 0
fi

# Perform a host-check and establish GHE_REMOTE_XXX variables.
ghe_remote_version_required "$GHE_HOSTNAME"

# Generate SSH config for forwarding
# Split host:port into parts
port=$(ssh_port_part "$GHE_HOSTNAME")
host=$(ssh_host_part "$GHE_HOSTNAME")

# Add user / -l option
user="${host%@*}"
[ "$user" = "$host" ] && user="admin"

tempdir=$(mktemp -d)
ssh_config_file=$tempdir/ssh_config
opts="$GHE_EXTRA_SSH_OPTS -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no -o PasswordAuthentication=no"
tmp_list=$tempdir/tmp_list
to_restore=$tempdir/to_restore

hostnames=$(ghe-ssh "$GHE_HOSTNAME" ghe-config --get-regexp cluster.*.hostname | cut -d ' ' -f 2)
for hostname in $hostnames; do
echo "
Host $hostname
ServerAliveInterval 60
ProxyCommand ssh -q $GHE_EXTRA_SSH_OPTS -p $port $user@$host nc.openbsd %h %p
StrictHostKeyChecking=no" >> $ssh_config_file
done

cleanup() {
for hostname in $hostnames; do
ghe-gc-enable -F $ssh_config_file $hostname:$port
done
rm -rf $tempdir
}
trap cleanup EXIT

# Disable remote GC operations
for hostname in $hostnames; do
ghe-gc-disable -F $ssh_config_file $hostname:$port
done

# Build a list of network paths to send to the server to calculate
# the restore routes, something like:
#
# a/nw/a8/3f/02/100000855
# a/nw/a8/bc/8d/100000880
# a/nw/a5/06/81/100000659
# a/nw/a5/84/6f/100000708
# a/nw/a5/e0/01/146
# ...
#
# One network path per line.
OLDIFS=$IFS; IFS=$'\n'
for path in $network_paths; do
# Get the network ID
# The nework id from a repository is the last component of the path
# i.e. /data/repositories/a/nw/a5/bf/c9/37 network ID would be 37
ghe_verbose "Adding network_path $path to the list of networks to send"
echo $path
done > $tmp_list
IFS=$OLDIFS

# The server returns a list of routes:
#
# a/nw/a8/3f/02/100000855 dgit-node1 dgit-node2 dgit-node3
# a/nw/a8/bc/8d/100000880 dgit-node1 dgit-node2 dgit-node4
# a/nw/a5/06/81/100000659 dgit-node3 dgit-node2 dgit-node4
# ...
#
# One route per line.
cat $tmp_list | ghe-ssh "$GHE_HOSTNAME" github-env ./bin/dgit-cluster-restore-routes \
| while read route; do
ghe_verbose "Received route $route"
servers=$(echo $route | cut -d ' ' -f2-)
for server in $servers; do
network_path=$(echo $route | cut -d ' ' -f1)
ghe_verbose "Adding $network_path to $tempdir/$server.rsync"
echo "$network_path" >> $tempdir/$server.rsync
done

network_id=$(echo $network_path | awk -F/ '{print $(NF)}')
ghe_verbose "Route: $network_id /data/repositories/$network_path $servers"
echo "$network_id /data/repositories/$network_path $servers" >> $to_restore
done

# rsync all the repositories
for file_list in $tempdir/*.rsync; do
server=$(basename $file_list .rsync)
ghe_verbose "* Transferring repositories to $server"
ghe-rsync -avrHR --delete \
-e "ssh -q $opts -p $port -F $ssh_config_file -l $user" \
--rsync-path="sudo -u git rsync" \
--files-from=$file_list \
"$GHE_DATA_DIR/$GHE_RESTORE_SNAPSHOT/repositories/./" \
"$server:$GHE_REMOTE_DATA_USER_DIR/repositories/" 1>&3
done

# Tell dgit about the repositories restored
cat $to_restore | ghe-ssh "$GHE_HOSTNAME" github-env ./bin/dgit-cluster-restore-finalize >&3

if [ -d $GHE_DATA_DIR/$GHE_RESTORE_SNAPSHOT/repositories/info ]; then
ghe_verbose "* Transferring repository info data"
for route in `ghe-ssh "$GHE_HOSTNAME" ghe-cluster-each -r git -p`; do
if ! ghe-rsync -av --delete \
-e "ssh -q $opts -p $port -F $ssh_config_file -l $user" \
--rsync-path="sudo -u git rsync" \
"$GHE_DATA_DIR/$GHE_RESTORE_SNAPSHOT/repositories/info/" \
"$route:$GHE_REMOTE_DATA_USER_DIR/repositories/info" 1>&3; then
echo "Error restoring /data/repositories/info to $route"
fi
done
else
ghe_verbose "* Removing repository info data"
ghe-ssh "$GHE_HOSTNAME" ghe-cluster-each -r git -- rm -f /data/repositories/info/*
fi

bm_end "$(basename $0)"