#!/bin/bash . "${0%/*}/common" if [ -z "$(git -C "${git_dir}" diff)" ]; then exit fi find_vcfs \ | while read -r file; do if [ ! -f "${file}" ]; then >&2 printf 'File "%s" is in git, but not in the worktree.\n' "${file##*/}" exit 1 fi if ! git -C "${git_dir}" archive HEAD -- "${file##*/}" >/dev/null; then >&2 printf 'File "%s" is in the worktree but not in git.\n' "${file##*/}" exit 1 fi if ! git -C "${git_dir}" archive HEAD -- "${file##*/}" \ | tar -Ox \ | diff -q - "${file}"; then >&2 printf 'File "%s" was changed relative to git.\n' "${file##*/}" exit 1 fi done print_cnt() { printf 'BEGIN:VCARD\n' printf 'VERSION:3.0\n' for key in "${keys[@]}"; do eval 'value="${'"$1${key}"'}"' if [ -n "${value}" ]; then printf '%s:%s\n' "${key}" "${value}" fi done printf 'END:VCARD\n' } read_line() { local line IFS='' read -r line for key in "${alpine_keys[@]}"; do eval "${1}${key}"'="${line%%'"$(printf '\t')"'*}"' eval 'line="${line#${'"${1}${key}"'}}"' line="${line#$(printf '\t')}" done } sed -i ' /^#/d ' "${git_dir}"'/addressbook' last_uids=() git -C "${git_dir}" diff -U0 -- addressbook \ | sed ' 1,/^+++/d $ s#$#\n@@ # ' \ | while IFS='' read -r line; do case "${line}" in '@@ '*) for last_uid in "${last_uids[@]}"; do sed -i '/^'"${last_uid}"'\s/d' "${git_dir}/uids" rm "${git_dir}/${last_uid}.vcf" done last_uids=() removals=false ;; '+'*) newUID="${last_uids[${#last_uids[@]}]}" mapfile -t last_uids < <( printf '%s\n' "${last_uids[@]}" \ | sed '$d' ) read_line 'new' < <( printf '%s\n' "${line#+}" ) newREV=$( date -u -Iseconds \ | sed 's@+00:00$@Z@' ) if [ -z "${newUID}" ]; then if ${removals}; then >&2 printf 'There were more addresses added than removed.\n' exit 1 fi newUID=$(uuidgen) printf '%s\t%s\n' "${newUID}" "${line#+}" \ >> "${git_dir}/uids" print_cnt 'new' > "${git_dir}/${newUID}.vcf" else read_line 'old' < <( sed ' s/^'"${newUID}"'\t// t d ' "${git_dir}/uids" ) sed -i ' /^'"${newUID}"'\t/ { i '"${newUID}$(printf '\t')${line#+}"' d } ' "${git_dir}/uids" for key in "${alpine_keys[@]}"; do if eval '[ "${old'"${key}"'}" != "${new'"${key}"'}" ]'; then for insert in "${key}:" 'VERSION:' 'BEGIN:VCARD$' ''; do if [ -z "${insert}" ]; then >&2 printf 'Cannot find any place to insert into "%s".\n' "${uid}.vcf" exit 1 fi if ! grep -q '^'"${insert}" "${git_dir}/${uid}.vcf"; then continue fi if [ "${insert}" = "${key}:" ]; then delete_command='d' else delete_command='' fi eval 'value="${new'"${key}"'}"' if [ -z "${value}" ]; then insert_command='' else insert_command='a '"${key}"':'"${value}" fi sed -i ' /^'"${key}"'/ { '"${insert_command}"' '"${delete_command}"' } ' "${git_dir}/${uid}.vcf" break done fi done fi ;; '-'*) removals=true if num=$( sed 's@^\S\+ @@' "${git_dir}/uids" \ | grep -nxF "${line#-}" ); then last_uid=$( sed -n ' '"${num}"' { s@\s.*$@@ p }' ) else >&2 printf 'cannot find line "%s" for removal\n' "${line#-}" exit 1 fi last_uids=( "${last_uids[@]}" "${last_uid}" ) ;; esac done