git/git-push.sh

88 строки
1.7 KiB
Bash
Исходник Обычный вид История

#!/bin/sh
USAGE='[--all] [--tags] [--force] <repository> [<refspec>...]'
. git-sh-setup
# Parse out parameters and then stop at remote, so that we can
# translate it using .git/branches information
has_all=
has_force=
has_exec=
has_thin=--thin
remote=
git-push: avoid falling back on pushing "matching" refs. The underlying "git send-pack remote.host:path" pushes all the matching refs that both local and remote have, and "git push" blindly inherits this property. Which probably was a mistake. A typical cloned repository (e.g. a subsystem repository cloned from Linus repository) has at least two branches, "master" to keep the subsystem and "origin" that records tip of Linus "master" when the repository was cloned. If this is the public repository for the subsystem, then subsystem developers would clone it, and then cloned ones have "master" and "origin". When developers use this public subsystem repository as a shared repository, pushing into it via "git push subsys:/path/name" would try to push the matching refs, "master" and "origin", from the developers' repositories. The "origin" in the public shared repository does not have much relevance, yet pushing into "origin" would cause "not a fast forward" checks to be triggered. Arguably "git push subsys:/path/name master" would work it around, but having them to say it explicitly to avoid pushing into "origin" as well is bad. This commit requires you to give at least one refspec to git-push. You could "give" by either: (1) Listing the refspec(s) explicitly on the command line. E.g. "git push subsys:/path/name master". (2) Using --all or --tags on the command line. E.g. "git push --tags subsys:/path/name". (3) Using a $GIT_DIR/remotes shorthand with 'Push: refspec' line in it. Unlike pull that can happen pretty much promiscuously, people will push into the same set of a limited number of remote repositories repeatedly over the life of the project, so it is reasonable to assume they would want to keep a $GIT_DIR/remotes/ entry for those repositories even only to save typing the URL, so keeping the default 'Push: refspec' line in such is a sensible thing to do. It was suggested to further fall back on pushing the current branch, but this commit does not implement it. If developers adopt topic branch workflow, pushing to public while on a topic branch by mistake would expose the topic branch to the public repository. Not falling back to the current branch prevents that mistake from happening. Signed-off-by: Junio C Hamano <junkio@cox.net>
2006-01-13 02:29:12 +03:00
do_tags=
while case "$#" in 0) break ;; esac
do
case "$1" in
--all)
has_all=--all ;;
git-push: avoid falling back on pushing "matching" refs. The underlying "git send-pack remote.host:path" pushes all the matching refs that both local and remote have, and "git push" blindly inherits this property. Which probably was a mistake. A typical cloned repository (e.g. a subsystem repository cloned from Linus repository) has at least two branches, "master" to keep the subsystem and "origin" that records tip of Linus "master" when the repository was cloned. If this is the public repository for the subsystem, then subsystem developers would clone it, and then cloned ones have "master" and "origin". When developers use this public subsystem repository as a shared repository, pushing into it via "git push subsys:/path/name" would try to push the matching refs, "master" and "origin", from the developers' repositories. The "origin" in the public shared repository does not have much relevance, yet pushing into "origin" would cause "not a fast forward" checks to be triggered. Arguably "git push subsys:/path/name master" would work it around, but having them to say it explicitly to avoid pushing into "origin" as well is bad. This commit requires you to give at least one refspec to git-push. You could "give" by either: (1) Listing the refspec(s) explicitly on the command line. E.g. "git push subsys:/path/name master". (2) Using --all or --tags on the command line. E.g. "git push --tags subsys:/path/name". (3) Using a $GIT_DIR/remotes shorthand with 'Push: refspec' line in it. Unlike pull that can happen pretty much promiscuously, people will push into the same set of a limited number of remote repositories repeatedly over the life of the project, so it is reasonable to assume they would want to keep a $GIT_DIR/remotes/ entry for those repositories even only to save typing the URL, so keeping the default 'Push: refspec' line in such is a sensible thing to do. It was suggested to further fall back on pushing the current branch, but this commit does not implement it. If developers adopt topic branch workflow, pushing to public while on a topic branch by mistake would expose the topic branch to the public repository. Not falling back to the current branch prevents that mistake from happening. Signed-off-by: Junio C Hamano <junkio@cox.net>
2006-01-13 02:29:12 +03:00
--tags)
do_tags=yes ;;
--force)
has_force=--force ;;
--exec=*)
has_exec="$1" ;;
--thin)
;; # noop
--no-thin)
has_thin= ;;
-*)
usage ;;
*)
set x "$@"
shift
break ;;
esac
shift
done
case "$#" in
0)
echo "Where would you want to push today?"
usage ;;
esac
. git-parse-remote
remote=$(get_remote_url "$@")
case "$has_all" in
--all)
set x ;;
'')
case "$do_tags,$#" in
yes,1)
set x $(cd "$GIT_DIR/refs" && find tags -type f -print) ;;
yes,*)
set x $(cd "$GIT_DIR/refs" && find tags -type f -print) \
$(get_remote_refs_for_push "$@") ;;
,*)
set x $(get_remote_refs_for_push "$@") ;;
esac
esac
shift ;# away the initial 'x'
git-push: avoid falling back on pushing "matching" refs. The underlying "git send-pack remote.host:path" pushes all the matching refs that both local and remote have, and "git push" blindly inherits this property. Which probably was a mistake. A typical cloned repository (e.g. a subsystem repository cloned from Linus repository) has at least two branches, "master" to keep the subsystem and "origin" that records tip of Linus "master" when the repository was cloned. If this is the public repository for the subsystem, then subsystem developers would clone it, and then cloned ones have "master" and "origin". When developers use this public subsystem repository as a shared repository, pushing into it via "git push subsys:/path/name" would try to push the matching refs, "master" and "origin", from the developers' repositories. The "origin" in the public shared repository does not have much relevance, yet pushing into "origin" would cause "not a fast forward" checks to be triggered. Arguably "git push subsys:/path/name master" would work it around, but having them to say it explicitly to avoid pushing into "origin" as well is bad. This commit requires you to give at least one refspec to git-push. You could "give" by either: (1) Listing the refspec(s) explicitly on the command line. E.g. "git push subsys:/path/name master". (2) Using --all or --tags on the command line. E.g. "git push --tags subsys:/path/name". (3) Using a $GIT_DIR/remotes shorthand with 'Push: refspec' line in it. Unlike pull that can happen pretty much promiscuously, people will push into the same set of a limited number of remote repositories repeatedly over the life of the project, so it is reasonable to assume they would want to keep a $GIT_DIR/remotes/ entry for those repositories even only to save typing the URL, so keeping the default 'Push: refspec' line in such is a sensible thing to do. It was suggested to further fall back on pushing the current branch, but this commit does not implement it. If developers adopt topic branch workflow, pushing to public while on a topic branch by mistake would expose the topic branch to the public repository. Not falling back to the current branch prevents that mistake from happening. Signed-off-by: Junio C Hamano <junkio@cox.net>
2006-01-13 02:29:12 +03:00
# $# is now 0 if there was no explicit refspec on the command line
# and there was no defalt refspec to push from remotes/ file.
# we will let git-send-pack to do its "matching refs" thing.
git-push: avoid falling back on pushing "matching" refs. The underlying "git send-pack remote.host:path" pushes all the matching refs that both local and remote have, and "git push" blindly inherits this property. Which probably was a mistake. A typical cloned repository (e.g. a subsystem repository cloned from Linus repository) has at least two branches, "master" to keep the subsystem and "origin" that records tip of Linus "master" when the repository was cloned. If this is the public repository for the subsystem, then subsystem developers would clone it, and then cloned ones have "master" and "origin". When developers use this public subsystem repository as a shared repository, pushing into it via "git push subsys:/path/name" would try to push the matching refs, "master" and "origin", from the developers' repositories. The "origin" in the public shared repository does not have much relevance, yet pushing into "origin" would cause "not a fast forward" checks to be triggered. Arguably "git push subsys:/path/name master" would work it around, but having them to say it explicitly to avoid pushing into "origin" as well is bad. This commit requires you to give at least one refspec to git-push. You could "give" by either: (1) Listing the refspec(s) explicitly on the command line. E.g. "git push subsys:/path/name master". (2) Using --all or --tags on the command line. E.g. "git push --tags subsys:/path/name". (3) Using a $GIT_DIR/remotes shorthand with 'Push: refspec' line in it. Unlike pull that can happen pretty much promiscuously, people will push into the same set of a limited number of remote repositories repeatedly over the life of the project, so it is reasonable to assume they would want to keep a $GIT_DIR/remotes/ entry for those repositories even only to save typing the URL, so keeping the default 'Push: refspec' line in such is a sensible thing to do. It was suggested to further fall back on pushing the current branch, but this commit does not implement it. If developers adopt topic branch workflow, pushing to public while on a topic branch by mistake would expose the topic branch to the public repository. Not falling back to the current branch prevents that mistake from happening. Signed-off-by: Junio C Hamano <junkio@cox.net>
2006-01-13 02:29:12 +03:00
case "$remote" in
git://*)
die "Cannot use READ-ONLY transport to push to $remote" ;;
rsync://*)
die "Pushing with rsync transport is deprecated" ;;
esac
set x "$remote" "$@"; shift
test "$has_all" && set x "$has_all" "$@" && shift
test "$has_force" && set x "$has_force" "$@" && shift
test "$has_exec" && set x "$has_exec" "$@" && shift
test "$has_thin" && set x "$has_thin" "$@" && shift
case "$remote" in
http://* | https://*)
exec git-http-push "$@";;
*)
exec git-send-pack "$@";;
esac