ref: 72621d62735fefe8bbcbf7308f6f271abe9c8f37
dir: /pull/
#!/bin/rc -ex
rfork en
nl='
'
fn update{
branch=$1
upstream=$2
url=$3
dir=$4
fetch=`{git/fetch -b $branch -u $upstream $url} |[2] tr '\x0d' '\x0a'
st=$status
if(! ~ $st '|'){
echo fetch failed: $st
exit $st
}
echo $fetch | awk '
/^remote/{
if($2=="HEAD")
next
gsub("^refs/heads", "refs/remotes/'$upstream'", $2)
outfile = ".git/"ref
system("mkdir -p `{basename -d "outfile"}");
print hash > outfile;
print ref" => "hash > "/dev/fd/2"
close(outfile);
}
'
}
fn usage{
echo usage: $0 '[-a] [-u upstream] [-b branch]
-u up: pull from upstream "up" (default: origin)
-f: fetch without updating working copy' >[1=2]
exit usage
}
branch=`{awk '$1=="branch"{print $2}' < /mnt/git/ctl}
remote=()
checkout='true'
upstream=origin
if(! cd `{git/conf -r}){
echo 'not in git repository' >[1=2]
exit notgit
}
git/fs
while(~ $1 -*){
switch($1){
case -u
upstream=SOMEONE
remote=$2
shift
case -b
branch=$2
shift
case -f
checkout=()
case *
usage
}
shift
}
if(! ~ $#* 0)
usage
if(~ $#remote 0)
remote=`{git/conf 'remote "'$upstream'".url'}
if(~ $#remote 0){
echo 'no idea from where to pull'
exit upstream
}
update $branch $upstream $remote
if (~ $#checkout 0)
exit
local=`{git/branch}
remote=`{git/branch | sed 's@^(refs/)?heads@remotes/'$upstream'@'}
echo 'remote='$remote
modified=`$nl{git/query -c HEAD $remote | grep '^[+~]' | sed 's/^..//'}
deleted=`$nl{git/query -c HEAD $remote | grep '^-' | sed 's/^..//'}
if(~ foo bar) { #! ~ $#modified 0 || ! ~ $#deleted 0){
if(! git/walk -q $modified $deleted){
echo remote changes would clobber local changes >[1=2]
exit dirty
}
}
cp .git/refs/$remote .git/refs/$local
if(! ~ $#modified 0){
# Modifications can turn a file into
# a directory, so we need to walk to
# check the blobs out correctly.
for(m in `{walk -f $modified}){
gm=/mnt/git/HEAD/tree/$m
d=`{basename -d $m}
mkdir -p $d
mkdir -p .git/index9/tracked/$d
cp $gm $m
walk -eq $m > .git/index9/tracked/$m
}
}
if(! ~ $#deleted 0){
rm -f $deleted
rm -f .git/index9/tracked/$deleted
}