Created
June 15, 2015 20:01
-
-
Save mattly/34e14ca0480ff9efb1d5 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| #!/usr/bin/env bash | |
| getDir () { | |
| fname=$1 | |
| [ -h $fname ] && fname=$(readlink $fname) | |
| echo "$(cd "$(dirname $fname)" && pwd)" | |
| } | |
| # used by loader to find core/ and stdlib/ | |
| BORK_SOURCE_DIR="$(getDir $(getDir ${BASH_SOURCE[0]}))" | |
| BORK_SCRIPT_DIR=$PWD | |
| BORK_WORKING_DIR=$PWD | |
| operation="satisfy" | |
| case "$1" in | |
| status) operation="$1" | |
| esac | |
| is_compiled () { return 0; } | |
| arguments () { | |
| op=$1 | |
| shift | |
| case $op in | |
| get) | |
| key=$1 | |
| shift | |
| value= | |
| while [ -n "$1" ] && [ -z "$value" ]; do | |
| this=$1 | |
| shift | |
| if [ ${this:0:2} = '--' ]; then | |
| tmp=${this:2} # strip off leading -- | |
| param=${tmp%%=*} # everything before = | |
| val=${tmp##*=} # everything after = | |
| if [ "$param" = $key ]; then value=$val; fi | |
| fi | |
| done | |
| [ -n $value ] && echo "$value" | |
| ;; | |
| *) return 1 ;; | |
| esac | |
| } | |
| bag () { | |
| action=$1 | |
| varname=$2 | |
| shift 2 | |
| if [ "$action" != "init" ]; then | |
| length=$(eval "echo \${#$varname[*]}") | |
| last=$(( length - 1 )) | |
| fi | |
| case "$action" in | |
| init) eval "$varname=( )" ;; | |
| push) eval "$varname[$length]=\"$1\"" ;; | |
| pop) eval "unset $varname[$last]=" ;; | |
| read) | |
| [ "$length" -gt 0 ] && echo $(eval "echo \${$varname[$last]}") ;; | |
| size) echo $length ;; | |
| filter) | |
| index=0 | |
| (( limit=$2 )) | |
| [ "$limit" -eq 0 ] && limit=-1 | |
| while [ "$index" -lt $length ]; do | |
| line=$(eval "echo \${$varname[$index]}") | |
| if str_matches "$line" "$1"; then | |
| [ -n "$3" ] && echo $index || echo $line | |
| [ "$limit" -ge $index ] && return | |
| fi | |
| (( index++ )) | |
| done ;; | |
| find) echo $(bag filter $varname $1 1) ;; | |
| index) echo $(bag filter $varname $1 1 1) ;; | |
| set) | |
| idx=$(bag index $varname "^$1=") | |
| [ -z "$idx" ] && idx=$length | |
| eval "$varname[$idx]=\"$1=$2\"" | |
| ;; | |
| get) | |
| line=$(bag filter $varname "^$1=" 1) | |
| echo "${line##*=}" ;; | |
| *) return 1 ;; | |
| esac | |
| } | |
| bake () { eval "$*"; } | |
| md5cmd () { | |
| case $1 in | |
| Darwin) | |
| [ -z "$2" ] && echo "md5" || echo "md5 -q $2" | |
| ;; | |
| Linux) | |
| [ -z "$2" ] && arg="" || arg="$2 " | |
| echo "md5sum $arg| awk '{print \$1}'" | |
| ;; | |
| *) return 1 ;; | |
| esac | |
| } | |
| satisfying () { [ "$operation" == "satisfy" ]; } | |
| permission_cmd () { | |
| case $1 in | |
| Linux) echo "stat --printf '%a'" ;; | |
| Darwin) echo "stat -f '%Lp'" ;; | |
| *) return 1 ;; | |
| esac | |
| } | |
| STATUS_OK=0 | |
| STATUS_FAILED=1 | |
| STATUS_MISSING=10 | |
| STATUS_OUTDATED=11 | |
| STATUS_PARTIAL=12 | |
| STATUS_MISMATCH_UPGRADE=13 | |
| STATUS_MISMATCH_CLOBBER=14 | |
| STATUS_CONFLICT_UPGRADE=20 | |
| STATUS_CONFLICT_CLOBBER=21 | |
| STATUS_CONFLICT_HALT=25 | |
| STATUS_BAD_ARGUMENTS=30 | |
| STATUS_FAILED_ARGUMENTS=31 | |
| STATUS_FAILED_ARGUMENT_PRECONDITION=32 | |
| STATUS_FAILED_PRECONDITION=33 | |
| STATUS_UNSUPPORTED_PLATFORM=34 | |
| _status_for () { | |
| case "$1" in | |
| $STATUS_OK) echo "ok" ;; | |
| $STATUS_FAILED) echo "failed" ;; | |
| $STATUS_MISSING) echo "missing" ;; | |
| $STATUS_OUTDATED) echo "outdated" ;; | |
| $STATUS_PARTIAL) echo "partial" ;; | |
| $STATUS_MISMATCH_UPGRADE) echo "mismatch (upgradable)" ;; | |
| $STATUS_MISMATCH_CLOBBER) echo "mismatch (clobber required)" ;; | |
| $STATUS_CONFLICT_UPGRADE) echo "conflict (upgradable)" ;; | |
| $STATUS_CONFLICT_CLOBBER) echo "conflict (clobber required)" ;; | |
| $STATUS_CONFLICT_HALT) echo "conflict (unresolvable)" ;; | |
| $STATUS_BAD_ARGUMENT) echo "error (bad arguments)" ;; | |
| $STATUS_FAILED_ARGUMENTS) echo "error (failed arguments)" ;; | |
| $STATUS_FAILED_ARGUMENT_PRECONDITION) echo "error (failed argument precondition)" ;; | |
| $STATUS_FAILED_PRECONDITION) echo "error (failed precondition)" ;; | |
| $STATUS_UNSUPPORTED_PLATFORM) echo "error (unsupported platform)" ;; | |
| *) echo "unknown status: $1" ;; | |
| esac | |
| } | |
| needs_exec () { | |
| [ -z "$1" ] && return 1 | |
| [ -z "$2" ] && running_status=0 || running_status=$2 | |
| path=$(bake "which $1") | |
| if [ "$?" -gt 0 ]; then | |
| echo "missing required exec: $1" | |
| retval=$((running_status+1)) | |
| return $retval | |
| else return $running_status | |
| fi | |
| } | |
| platform=$(uname -s) | |
| is_platform () { | |
| [ "$platform" = $1 ] | |
| return $? | |
| } | |
| platform_is () { | |
| [ "$platform" = $1 ] | |
| return $? | |
| } | |
| baking_platform= | |
| baking_platform_is () { | |
| [ -z "$baking_platform" ] && baking_platform=$(bake uname -s) | |
| [ "$baking_platform" = $1 ] | |
| return $? | |
| } | |
| str_contains () { | |
| str_matches "$1" "^$2\$" | |
| } | |
| str_get_field () { | |
| echo $(echo "$1" | awk '{print $'"$2"'}') | |
| } | |
| str_item_count () { | |
| accum=0 | |
| for item in $1; do | |
| ((accum++)) | |
| done | |
| echo $accum | |
| } | |
| str_matches () { | |
| $(echo "$1" | grep -E "$2" > /dev/null) | |
| return $? | |
| } | |
| str_replace () { | |
| echo $(echo "$1" | sed -E 's|'"$2"'|'"$3"'|g') | |
| } | |
| bork_performed_install=0 | |
| bork_performed_upgrade=0 | |
| bork_performed_error=0 | |
| bork_any_updated=0 | |
| did_install () { [ "$bork_performed_install" -eq 1 ] && return 0 || return 1; } | |
| did_upgrade () { [ "$bork_performed_upgrade" -eq 1 ] && return 0 || return 1; } | |
| did_update () { | |
| if did_install; then return 0 | |
| elif did_upgrade; then return 0 | |
| else return 1 | |
| fi | |
| } | |
| did_error () { [ "$bork_performed_error" -gt 0 ] && return 0 || return 1; } | |
| any_updated () { [ "$bork_any_updated" -gt 0 ] && return 0 || return 1; } | |
| _changes_reset () { | |
| bork_performed_install=0 | |
| bork_performed_upgrade=0 | |
| bork_performed_error=0 | |
| last_change_type= | |
| } | |
| _changes_complete () { | |
| status=$1 | |
| action=$2 | |
| if [ "$status" -gt 0 ]; then bork_performed_error=1 | |
| elif [ "$action" = "install" ]; then bork_performed_install=1 | |
| elif [ "$action" = "upgrade" ]; then bork_performed_upgrade=1 | |
| fi | |
| if did_update; then bork_any_updated=1 ;fi | |
| [ "$status" -gt 0 ] && echo "* failure" | |
| } | |
| BORK_DESTINATION=$BORK_WORKING_DIR | |
| destination () { | |
| BORK_DESTINATION=$1 | |
| if [ ! -d "$1" ]; then | |
| echo "missing destination: $1" | |
| return 1 | |
| fi | |
| } | |
| include () { | |
| if [ -e "$BORK_SCRIPT_DIR/$1" ]; then | |
| . "$BORK_SCRIPT_DIR/$1" | |
| else | |
| echo "include: $BORK_SCRIPT_DIR/$1: No such file or directory" | |
| exit 1 | |
| fi | |
| } | |
| _ok_run () { | |
| fn=$1 | |
| shift | |
| if is_compiled; then (cd $BORK_DESTINATION; $fn $*) | |
| else (cd $BORK_DESTINATION; . $fn $*) | |
| fi | |
| } | |
| _source_runner () { | |
| if is_compiled; then echo "cd $BORK_DESTINATION; $1" | |
| else echo "cd $BORK_DESTINATION; . $1" | |
| fi | |
| } | |
| _bork_check_failed=0 | |
| check_failed () { [ "$_bork_check_failed" -gt 0 ] && return 0 || return 1; } | |
| _checked_len=0 | |
| _checking () { | |
| type=$1 | |
| shift | |
| check_str="$type: $*" | |
| _checked_len=${#check_str} | |
| echo -n "$check_str"$'\r' | |
| } | |
| _checked () { | |
| report="$*" | |
| (( pad=$_checked_len - ${#report} )) | |
| i=1 | |
| while [ "$i" -le $pad ]; do | |
| report+=" " | |
| (( i++ )) | |
| done | |
| echo "$report" | |
| } | |
| _conflict_approve () { | |
| if [ -n "$BORK_CONFLICT_RESOLVE" ]; then | |
| return $BORK_CONFLICT_RESOLVE | |
| fi | |
| echo | |
| echo "== Warning! Assertion: $*" | |
| echo "Attempting to satisfy has resulted in a conflict. Satisfying this may overwrite data." | |
| _yesno "Do you want to continue?" | |
| return $? | |
| } | |
| _yesno () { | |
| answered=0 | |
| answer= | |
| while [ "$answered" -eq 0 ]; do | |
| read -p "$* (yes/no) " answer | |
| if [[ "$answer" == 'y' || "$answer" == "yes" || "$answer" == "n" || "$answer" == "no" ]]; then | |
| answered=1 | |
| else | |
| echo "Valid answers are: yes y no n" >&2 | |
| fi | |
| done | |
| [[ "$answer" == 'y' || "$answer" == 'yes' ]] | |
| } | |
| ok () { | |
| assertion=$1 | |
| shift | |
| _bork_check_failed=0 | |
| _changes_reset | |
| fn=$(_lookup_type $assertion) | |
| if [ -z "$fn" ]; then | |
| echo "not found: $assertion" 1>&2 | |
| return 1 | |
| fi | |
| argstr=$* | |
| quoted_argstr= | |
| while [ -n "$1" ]; do | |
| quoted_argstr=$(echo "$quoted_argstr \"$1\"") | |
| shift | |
| done | |
| case $operation in | |
| echo) echo "$fn $argstr" ;; | |
| status) | |
| _checking "checking" $assertion $argstr | |
| output=$(eval "$(_source_runner $fn) status $quoted_argstr") | |
| status=$? | |
| _checked "$(_status_for $status): $assertion $argstr" | |
| [ "$status" -eq 1 ] && _bork_check_failed=1 | |
| [ "$status" -ne 0 ] && [ -n "$output" ] && echo "$output" | |
| return $status ;; | |
| satisfy) | |
| _checking "checking" $assertion $argstr | |
| status_output=$(eval "$(_source_runner $fn) status $quoted_argstr") | |
| status=$? | |
| _checked "$(_status_for $status): $assertion $argstr" | |
| case $status in | |
| 0) : ;; | |
| 1) | |
| _bork_check_failed=1 | |
| echo "$status_output" | |
| ;; | |
| 10) | |
| eval "$(_source_runner $fn) install $quoted_argstr" | |
| _changes_complete $? 'install' | |
| ;; | |
| 11|12|13) | |
| echo "$status_output" | |
| eval "$(_source_runner $fn) upgrade $quoted_argstr" | |
| _changes_complete $? 'upgrade' | |
| ;; | |
| 20) | |
| echo "$status_output" | |
| _conflict_approve $assertion $argstr | |
| if [ "$?" -eq 0 ]; then | |
| echo "Resolving conflict..." | |
| eval "$(_source_runner $fn) upgrade $quoted_argstr" | |
| _changes_complete $? 'upgrade' | |
| else | |
| echo "Conflict unresolved." | |
| fi | |
| ;; | |
| *) | |
| echo "-- sorry, bork doesn't handle this response yet" | |
| echo "$status_output" | |
| ;; | |
| esac | |
| if did_update; then | |
| echo "verifying $last_change_type: $assertion $argstr" | |
| output=$(eval "_ok_run $fn status $quoted_argstr") | |
| status=$? | |
| if [ "$status" -gt 0 ]; then | |
| echo "* $last_change_type failed" | |
| _checked "$(_status_for $status)" | |
| echo "$output" | |
| else | |
| echo "* success" | |
| fi | |
| return 1 | |
| fi | |
| ;; | |
| esac | |
| } | |
| bag init bork_assertion_types | |
| register () { | |
| file=$1 | |
| type=$(basename $file '.sh') | |
| if [ -e "$BORK_SCRIPT_DIR/$file" ]; then | |
| file="$BORK_SCRIPT_DIR/$file" | |
| else | |
| exit 1 | |
| fi | |
| bag set bork_assertion_types $type $file | |
| } | |
| _lookup_type () { | |
| assertion=$1 | |
| if is_compiled; then | |
| echo "type_$assertion" | |
| return | |
| fi | |
| fn=$(bag get bork_assertion_types $assertion) | |
| if [ -n "$fn" ]; then | |
| echo "$fn" | |
| return | |
| fi | |
| bork_official="$BORK_SOURCE_DIR/types/$(echo $assertion).sh" | |
| if [ -e "$bork_official" ]; then | |
| echo "$bork_official" | |
| return | |
| fi | |
| local_script="$BORK_SCRIPT_DIR/$assertion" | |
| if [ -e "$local_script" ]; then | |
| echo "$local_script" | |
| return | |
| fi | |
| return 1 | |
| } | |
| # include osx.sh | |
| # auto-expand save, print dialogs | |
| type_defaults () { | |
| action=$1 | |
| domain=$2 | |
| key=$3 | |
| desired_type=$4 | |
| desired_val=$5 | |
| case $action in | |
| desc) | |
| echo "asserts settings for OS X's 'defaults' system" | |
| echo "* defaults domain key type value" | |
| echo "> defaults com.apple.dock autohide bool true" | |
| ;; | |
| status) | |
| needs_exec "defaults" || return $STATUS_FAILED_PRECONDITION | |
| current_val=$(bake defaults read $domain $key) | |
| [ "$?" -eq 1 ] && return $STATUS_MISSING | |
| current_type=$(str_get_field "$(bake defaults read-type $domain $key)" 3) | |
| conflict= | |
| if [ "$current_type" = "boolean" ]; then | |
| current_type="bool" | |
| case "$current_val" in | |
| 0) current_val="false" ;; | |
| 1|YES) current_val="true" ;; | |
| esac | |
| fi | |
| if [ "$desired_type" != $current_type ]; then | |
| conflict=1 | |
| echo "expected type: $desired_type" | |
| echo "received type: $current_type" | |
| fi | |
| if [ "$current_val" != $desired_val ]; then | |
| conflict=1 | |
| echo "expected value: $desired_val" | |
| echo "received value: $current_val" | |
| fi | |
| [ -n "$conflict" ] && return $STATUS_MISMATCH_UPGRADE | |
| return 0 ;; | |
| install|upgrade) | |
| bake defaults write $domain $key "-$desired_type" $desired_val | |
| ;; | |
| *) return 1 ;; | |
| esac | |
| } | |
| ok defaults NSGlobalDomain NSNavPanelExpandedStateForSaveMode bool true | |
| ok defaults NSGlobalDomain NSNavPanelExpandedStateForSaveMode2 bool true | |
| ok defaults NSGlobalDomain PMPrintingExpandedStateForPrint bool true | |
| ok defaults NSGlobalDomain PMPrintingExpandedStateForPrint2 bool true | |
| # default to save to disk, not iCloud | |
| ok defaults NSGlobalDomain NSDocumentSaveNewDocumentsToCloud bool false | |
| # disable gatekeeper | |
| # ok defaults com.apple.LaunchServices LSQuarantine bool false | |
| # speed up the UI | |
| ok defaults NSGlobalDomain NSAutomaticWindowAnimationsEnabled bool false | |
| ok defaults NSGlobalDomain NSWindowResizeTime string .001 | |
| # fix the UI | |
| ok defaults NSGlobalDomain AppleEnableMenuBarTransparency bool false | |
| ok defaults NSGlobalDomain NSTableViewDefaultSizeMode int 2 | |
| # show all extensions | |
| ok defaults NSGlobalDomain AppleShowAllExtensions bool true | |
| # help viewer to regular window | |
| ok defaults com.apple.helpviewer DevMode bool true | |
| # disable auto spelling correction | |
| ok defaults NSGlobalDomain NSAutomaticSpellingCorrectionEnabled bool false | |
| ok defaults com.apple.desktopservices DSDontWriteNetworkStores bool true | |
| ok defaults com.apple.frameworks.diskimages skip-verify bool true | |
| ok defaults com.apple.frameworks.diskimages skip-verify-remote bool true | |
| ok defaults com.apple.frameworks.diskimages skip-verify-locked bool true | |
| # don't prompt time machine on new disks | |
| ok defaults com.apple.TimeMachine DoNotOfferNewDisksForBackup bool true | |
| # --- dock | |
| ok defaults com.apple.dock autohide bool true | |
| ok defaults com.apple.dock static-only bool true | |
| ok defaults com.apple.dock workspaces-swoosh-animation-off bool true | |
| ok defaults com.apple.dashboard mcx-disabled bool true | |
| ok defaults com.apple.dock tilesize integer 36 | |
| # dock show/hide | |
| ok defaults com.apple.dock autohide-delay float 0 | |
| ok defaults com.apple.dock autohide-time-modifier float 0 | |
| # don't re-order spaces in mission control | |
| ok defaults com.apple.dock mru-spaces bool false | |
| # top-left corner: start screen saver | |
| ok defaults com.apple.dock wvous-tl-corner integer 5 | |
| ok defaults com.apple.dock wvous-tl-modifier integer 0 | |
| # Put it on the left | |
| ok defaults com.apple.dock orientation string bottom | |
| # clear the dock | |
| # ok rm ~/Library/Application Support/Dock/*.db | |
| # DIE DASHBOARD DIE | |
| ok defaults com.apple.dashboard mcx-disabled bool true | |
| # TODO: if changed... | |
| # killall Dock | |
| ok defaults com.apple.Finder FXPreferredViewStyle string clmv | |
| ok defaults com.apple.finder FXEnableExtensionChangeWarning bool false | |
| # ok defaults com.apple.finder EmptyTrashSecurely bool true | |
| # show ~/Library | |
| # chflags nohidden ~/Library | |
| # TODO: if changed... | |
| # killall Finder | |
| # require password immediately on sleep or screensaver | |
| ok defaults com.apple.screensaver askForPassword bool true | |
| ok defaults com.apple.screensaver askForPasswordDelay integer 0 | |
| # show ascii-control characters using caret notation in text views | |
| ok defaults NSGlobalDomain NSTextShowsControlCharacters bool true | |
| type_brew () { | |
| action=$1 | |
| name=$2 | |
| shift 2 | |
| from=$(arguments get from $*) | |
| if [ -z "$name" ]; then | |
| case $action in | |
| desc) | |
| echo "asserts presence of packages installed via homebrew on mac os x" | |
| echo "* brew (installs homebrew)" | |
| echo "* brew package-name (instals package)" | |
| echo "--from=caskroom/cask (source repository)" | |
| ;; | |
| status) | |
| baking_platform_is "Darwin" || return $STATUS_UNSUPPORTED_PLATFORM | |
| needs_exec "ruby" || return $STATUS_FAILED_PRECONDITION | |
| path=$(bake which brew) | |
| [ "$?" -gt 0 ] && return $STATUS_MISSING | |
| changes=$(cd /usr/local; git fetch --quiet; git log master..origin/master) | |
| [ "$(echo $changes | sed '/^\s*$/d' | wc -l | awk '{print $1}')" -gt 0 ] && return $STATUS_OUTDATED | |
| return $STATUS_OK | |
| ;; | |
| install) | |
| bake 'ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"' | |
| ;; | |
| upgrade) | |
| bake brew update | |
| ;; | |
| *) return 1 ;; | |
| esac | |
| else | |
| case $action in | |
| status) | |
| baking_platform_is "Darwin" || return $STATUS_UNSUPPORTED_PLATFORM | |
| needs_exec "brew" || return $STATUS_FAILED_PRECONDITION | |
| bake brew list | grep -E "^$name$" > /dev/null | |
| [ "$?" -gt 0 ] && return $STATUS_MISSING | |
| bake brew outdated | awk '{print $1}' | grep -E "^$name$" > /dev/null | |
| [ "$?" -eq 0 ] && return $STATUS_OUTDATED | |
| return 0 ;; | |
| install) | |
| if [ -z "$from" ]; then | |
| bake brew install $name | |
| else | |
| bake brew install $from/$name | |
| fi | |
| ;; | |
| upgrade) bake brew upgrade $name ;; | |
| *) return 1 ;; | |
| esac | |
| fi | |
| } | |
| ok brew | |
| ok brew git | |
| # include dotfiles.sh | |
| type_directory () { | |
| action=$1 | |
| dir=$2 | |
| shift 2 | |
| case "$action" in | |
| desc) | |
| echo "asserts presence of a directory" | |
| echo "* directories ~/.ssh" | |
| ;; | |
| status) | |
| [ ! -e "$dir" ] && return $STATUS_MISSING | |
| [ -d "$dir" ] && return $STATUS_OK | |
| echo "target exists as non-directory" | |
| return $STATUS_CONFLICT_CLOBBER | |
| ;; | |
| install) bake mkdir -p $dir ;; | |
| *) return 1 ;; | |
| esac | |
| } | |
| ok directory $HOME/code/mattly | |
| destination $HOME/code/mattly | |
| type_github () { | |
| action=$1 | |
| repo=$2 | |
| shift 2 | |
| case $action in | |
| desc) | |
| echo "front-end for git type, uses github urls" | |
| echo "> ok github mattly/bork" | |
| echo "--branch=gh-pages (specify branch or tag)" | |
| ;; | |
| compile) | |
| include_assertion git $BORK_SOURCE_DIR/types/git.sh | |
| ;; | |
| *) | |
| . $BORK_SOURCE_DIR/types/git.sh $action "https://github.com/$(echo $repo).git" $* | |
| ;; | |
| esac | |
| } | |
| type_git () { | |
| action=$1 | |
| git_url=$2 | |
| shift 2 | |
| branch=$(arguments get branch $*) | |
| git_name=$(basename $git_url .git) | |
| git_dir="$git_name" | |
| if [[ ! -z $branch ]]; then | |
| git_branch=$branch | |
| else | |
| git_branch="master" | |
| fi | |
| case $action in | |
| desc) | |
| echo "asserts presence and state of a git repository" | |
| echo "> git [email protected]:mattly/bork" | |
| echo "--branch=gh-pages (specify branch or tag)" | |
| ;; | |
| status) | |
| needs_exec "git" || return $STATUS_FAILED_PRECONDITION | |
| bake [ ! -d $git_dir ] && return $STATUS_MISSING | |
| git_dir_contents=$(str_item_count "$(bake ls -A $git_dir)") | |
| [ "$git_dir_contents" -eq 0 ] && return $STATUS_MISSING | |
| bake cd $git_dir | |
| git_fetch="$(bake git fetch 2>&1)" | |
| git_fetch_status=$? | |
| if [ $git_fetch_status -gt 0 ]; then | |
| echo "destination directory $git_dir exists, not a git repository (exit status $git_fetch_status)" | |
| return $STATUS_CONFLICT_CLOBBER | |
| elif str_matches "$git_fetch" '"^fatal"'; then | |
| echo "destination directory exists, not a git repository" | |
| echo "$git_fetch" | |
| return $STATUS_CONFLICT_CLOBBER | |
| fi | |
| git_stat=$(bake git status -uno -b --porcelain) | |
| git_first_line=$(echo "$git_stat" | head -n 1) | |
| git_divergence=$(str_get_field "$git_first_line" 3) | |
| if str_matches "$git_divergence" 'ahead'; then | |
| echo "local git repository is ahead of remote" | |
| return $STATUS_CONFLICT_UPGRADE | |
| fi | |
| if str_matches "$git_stat" "^\\s?\\w"; then | |
| echo "local git repository has uncommitted changes" | |
| return $STATUS_CONFLICT_UPGRADE | |
| fi | |
| str_matches "$(str_get_field "$git_first_line" 2)" "$git_branch" | |
| if [ "$?" -ne 0 ]; then | |
| echo "local git repository is on incorrect branch" | |
| return $STATUS_MISMATCH_UPGRADE | |
| fi | |
| if str_matches "$git_divergence" 'behind'; then return $STATUS_OUTDATED; fi | |
| return $STATUS_OK ;; | |
| install) | |
| bake mkdir -p $git_dir | |
| bake git clone -b $git_branch $git_url $git_dir | |
| ;; | |
| upgrade) | |
| bake cd $git_dir | |
| bake git reset --hard | |
| bake git pull | |
| bake git checkout $git_branch | |
| bake git log HEAD@{2}.. | |
| printf "\n" | |
| ;; | |
| *) return 1 ;; | |
| esac | |
| } | |
| ok github mattly/dotfiles | |
| destination $HOME | |
| for config in $HOME/code/mattly/dotfiles/configs/*; do | |
| type_symlink () { | |
| action=$1 | |
| target=$2 | |
| source=$3 | |
| case "$action" in | |
| desc) | |
| echo "assert presence and target of a symlink" | |
| echo "> symlink .vimrc ~/code/dotfiles/configs/vimrc" | |
| ;; | |
| status) | |
| if bake [ -h "\"$target\"" ]; then | |
| existing_source=$(bake readlink \"$target\") | |
| if [ "$existing_source" != "$source" ]; then | |
| echo "received source for existing symlink: $existing_source" | |
| echo "expected source for symlink: $source" | |
| return $STATUS_MISMATCH_UPGRADE | |
| else | |
| return $STATUS_OK | |
| fi | |
| elif bake [ -e "\"$target\"" ]; then | |
| echo "not a symlink: $target" | |
| return $STATUS_CONFLICT_CLOBBER | |
| else | |
| return $STATUS_MISSING | |
| fi ;; | |
| install|upgrade) | |
| bake ln -sf "$source" "$target" ;; | |
| *) return 1;; | |
| esac | |
| } | |
| ok symlink "$HOME/.$(basename $config)" $config | |
| done | |
| ok brew tig | |
| ok brew fish | |
| if did_install; then | |
| echo "changing shell to fish, you will need to enter your password" | |
| sudo echo /usr/local/bin/fish >> /etc/shells | |
| cshs -s /usr/local/bin/fish | |
| fi | |
| ok brew the_silver_searcher | |
| ok brew curl | |
| ok brew emacs-mac | |
| ok directory $HOME/code | |
| destination $HOME/code | |
| ok github syl20bnr/spacemacs | |
| destination $HOME | |
| ok symlink "$HOME/.emacs.d" $HOME/code/spacemacs | |
| ok brew brew-cask --from=caskroom/cask | |
| type_cask () { | |
| action=$1 | |
| name=$2 | |
| shift 2 | |
| appdir=$(arguments get appdir $*) | |
| case $action in | |
| desc) | |
| echo "asserts presenece of apps installed via caskroom.io on Mac OS X" | |
| echo "* cask app-name (installs cask)" | |
| echo "--appdir=/Applications (changes symlink path)" | |
| ;; | |
| status) | |
| baking_platform_is "Darwin" || return $STATUS_UNSUPPORTED_PLATFORM | |
| needs_exec "brew" || return $STATUS_FAILED_PRECONDITION | |
| bake brew cask 2&>/dev/null | |
| [ "$?" -gt 0 ] && return $STATUS_FAILED_PRECONDITION | |
| list=$(bake brew cask list) | |
| echo "$list" | grep -E "^$name$" > /dev/null | |
| [ "$?" -gt 0 ] && return $STATUS_MISSING | |
| return 0 ;; | |
| install) | |
| if [ -n "$appdir" ]; then | |
| bake brew cask install $name --appdir=$appdir | |
| else | |
| bake brew cask install $name | |
| fi | |
| ;; | |
| *) return 1 ;; | |
| esac | |
| } | |
| ok cask the-unarchiver | |
| ok cask iterm2 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment