From 99bad8b10f0c2053d5fbdafc9c1a92a8d5de7339 Mon Sep 17 00:00:00 2001 From: Peter Palfrader Date: Fri, 26 Apr 2013 14:27:50 +0200 Subject: [PATCH] Also add the merged files/templates --- .../static-mirroring/staticsync-ssh-wrap | 206 ++++++++++++++++++ .../staticsync-authorized_keys.erb | 46 ++++ 2 files changed, 252 insertions(+) create mode 100755 modules/roles/files/static-mirroring/staticsync-ssh-wrap create mode 100644 modules/roles/templates/static-mirroring/staticsync-authorized_keys.erb diff --git a/modules/roles/files/static-mirroring/staticsync-ssh-wrap b/modules/roles/files/static-mirroring/staticsync-ssh-wrap new file mode 100755 index 00000000..2cb8c317 --- /dev/null +++ b/modules/roles/files/static-mirroring/staticsync-ssh-wrap @@ -0,0 +1,206 @@ +#!/bin/bash + +# Copyright (c) 2009, 2010, 2012 Peter Palfrader +# +# Permission is hereby granted, free of charge, to any person obtaining +# a copy of this software and associated documentation files (the +# "Software"), to deal in the Software without restriction, including +# without limitation the rights to use, copy, modify, merge, publish, +# distribute, sublicense, and/or sell copies of the Software, and to +# permit persons to whom the Software is furnished to do so, subject to +# the following conditions: +# +# The above copyright notice and this permission notice shall be +# included in all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE +# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +set -e +set -u + +MYLOGNAME="`basename "$0"`[$$]" +BASEDIR="/home/staticsync/static-master" +COMPONENTLIST=/etc/static-components.conf + +usage() { + echo "local Usage: $0 " + echo "via ssh orig command:" + echo " mirror " + echo " rsync " + echo " static-master-update-component " +} + +one_more_arg() { + if [ "$#" -lt 1 ]; then + usage >&2 + exit 1 + fi +} + +info() { + logger -p daemon.info -t "$MYLOGNAME" "$1" +} + +croak() { + logger -s -p daemon.warn -t "$MYLOGNAME" "$1" + exit 1 +} + +do_mirror() { + local remote_host="$1"; shift + one_more_arg "$@" + local component="$1"; shift + one_more_arg "$@" + local serial="$1"; shift + + masterhost="$(awk -v component="$component" '$2 == component {print $1; exit}' "$COMPONENTLIST")" + if [ -z "$masterhost" ]; then + croak "Did not find master for component $component." + elif [ "$masterhost" != "$remote_host" ]; then + croak "$remote_host is not master for $component." + else + info "Host $remote_host triggered a mirror run for $component, serial $serial" + exec /usr/local/bin/static-mirror-run "$BASEDIR/mirrors/$component" "$remote_host:$component/-new-" "$serial" + echo >&2 "Exec failed" + croak "exec failed" + fi +} + +do_rsync_on_master() { + local remote_host="$1"; shift + local args="--server --sender -vlHtrze.iLsf --safe-links ." + + for component in $(awk -v this_host="$(hostname -f)" '$1 == this_host {print $2}' $COMPONENTLIST); do + if [ "$*" = "$args $component/-new-/" ] || [ "$*" = "$args ./$component/-new-/" ] ; then + local path="$BASEDIR/master/$component-current-push" + info "serving $remote_host with $path" + exec rsync $args "$path/." + croak "Exec failed" + elif [ "$*" = "$args $component/-live-/" ] || [ "$*" = "$args ./$component/-live-/" ] ; then + local path="$BASEDIR/master/$component-current-live" + info "host $remote_host wants $path, acquiring lock" + exec 200< "$path" + if ! flock -s -w 0 200; then + echo >&2 "Cannot acquire shared lock on $path - this should mean an update is already underway anyway." + exit 1 + fi + exec rsync $args "$path/." + croak "Exec failed" + fi + done +} + +do_rsync_on_source() { + local remote_host="$1" + shift + + local allowed_rsyncs + allowed_rsyncs=() + + if [ -e "$COMPONENTLIST" ]; then + for path in $(awk -v host="$(hostname -f)" '$3 == host {print $4}' $COMPONENTLIST); do + allowed_rsyncs+=("--server --sender -lHtrze.iLsf --safe-links . $path/.") + done + fi + for cmd_idx in ${!allowed_rsyncs[*]}; do + allowed="${allowed_rsyncs[$cmd_idx]}" + if [ "$*" = "$allowed" ]; then + info "Running for host $remote_host: rsync $*" + exec rsync "$@" + croak "Exec failed" + fi + done +} + +do_rsync() { + do_rsync_on_master "$@" + do_rsync_on_source "$@" + + info "NOT allowed for $remote_host: rsync $*" + echo >&2 "This rsync command ($@) not allowed." + exit 1 +} + +do_update_component() { + local remote_host="$1"; shift + + one_more_arg "$@" + component="$1" + shift + + hit="$( + awk -v this_host="$(hostname -f)" -v component="$component" -v host="$remote_host" ' + $1 == this_host && $2 == component { + if ($3 == host) { + print $4 + exit + } + split($5,extra,",") + for (i in extra) { + if (host == extra[i]) { + printf "%s:%s\n", $3, $4 + exit + } + } + exit + }' "$COMPONENTLIST" + )" + if [ -n "$hit" ]; then + exec static-master-update-component "$component" + echo >&2 "Exec failed" + croak "exec failed" + else + info "Not whitelisted: $remote_host update $component" + echo >&2 "Not whitelisted: $remote_host update $component" + exit 1 + fi +} + + +if [ "${1:-}" = "-h" ] || [ "${1:-}" = "--help" ]; then + usage + exit 0 +fi + +one_more_arg "$@" +remote_host="$1" +shift + + +# check/parse remote command line +if [ -z "${SSH_ORIGINAL_COMMAND:-}" ] ; then + croak "Did not find SSH_ORIGINAL_COMMAND" +fi +set "dummy" ${SSH_ORIGINAL_COMMAND} +shift + +info "host $remote_host called with $*" + +one_more_arg "$@" +action="$1" +shift + +case "$action" in + # on a static mirror, update a component from its master + mirror) + do_mirror "$remote_host" "$@" + ;; + # on a static source, allow fetching from the master, + # on a master, allow fetching from a component's mirrors + rsync) + do_rsync "$remote_host" "$@" + ;; + # on a master, initiate an update of a component + static-master-update-component) + do_update_component "$remote_host" "$@" + ;; + *) + croak "Invalid operation '$action'" + ;; +esac diff --git a/modules/roles/templates/static-mirroring/staticsync-authorized_keys.erb b/modules/roles/templates/static-mirroring/staticsync-authorized_keys.erb new file mode 100644 index 00000000..4ed90237 --- /dev/null +++ b/modules/roles/templates/static-mirroring/staticsync-authorized_keys.erb @@ -0,0 +1,46 @@ +## +## THIS FILE IS UNDER PUPPET CONTROL. DON'T EDIT IT HERE. +## + +<%= +def getstaticsynckey(host) + key = nil + begin + facts = YAML.load(File.open("/var/lib/puppet/yaml/facts/#{host}.yaml").read) + return facts.values['staticsync_key'] + rescue Exception => e + end + return key +end + +localinfo = scope.lookupvar('site::localinfo') +allnodeinfo = scope.lookupvar('site::allnodeinfo') + +callers = [] +localinfo.keys.sort.each do |node| + if localinfo[node]['static_mirror'] or localinfo[node]['static_source'] or localinfo[node]['static_master'] + key = getstaticsynckey(node) + callers << { 'node' => node, 'addr' => allnodeinfo[node]['ipHostNumber'], 'key' => key} + end +end + +callers << { 'node' => 'wagner.debian.org', 'addr' => allnodeinfo['wagner.debian.org']['ipHostNumber'], 'key' => 'ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCXHFIkIhOC5iDa0d0IN5w6tUUL2T2iXCYcS2+dandE9f550OpKQ/evUZhw4EERNYDA3G7GV3jJzQR0j/KZWJUtDCichmqS94xJqXURmZVNeLXWY9x/N7CB1iG1Iblu6sgyTUrs7N6Wb0fUab3AXAi9KIXdwNLY622reR9T//bRULPVIl5VFpYtGBPT9n3wR7fLQ4ndEcUmEGcM4jRbpLmye4QGgJotuzeBWUpX+U648Yly6U7NlAJIWPUt7hEzMz2AC81SLhGCwTk6sb19n2dO6WN2ndynp8PLG1emtgd1/DaeaRyPcitoWgSoDNgKNk3zLIDtCdSYvFI8xXrm6cK3 staticsync@wagner'} + +lines = [] +for m in callers: + lines << '# ' + m['node'] + if m['key'].nil? + lines << "# no key for node" + else + lines << "command=\"/usr/local/bin/staticsync-ssh-wrap #{m['node']}\"," + + 'no-port-forwarding,no-X11-forwarding,no-agent-forwarding,no-user-rc,' + + 'from="' + m['addr'].join(',') + '" ' + + m['key'] + end +end + +lines.join("\n") +# vim:set et: +# vim:set sts=4 ts=4: +# vim:set shiftwidth=4: +%> -- 2.39.2