Skip to content

Commit f39a9c6

Browse files
Denton-Lgitster
authored andcommitted
remote: add --save-to-push option to git remote set-url
This adds the --save-to-push option to `git remote set-url` such that when executed, we move the remote.*.url to remote.*.pushurl and set remote.*.url to the given url argument. For example, if we have the following config: [remote "origin"] url = [email protected]:git/git.git `git remote set-url --save-to-push origin https://github.com/git/git.git` would change the config to the following: [remote "origin"] url = https://github.com/git/git.git pushurl = [email protected]:git/git.git Helped-by: Junio C Hamano <[email protected]> Signed-off-by: Denton Liu <[email protected]> Signed-off-by: Junio C Hamano <[email protected]>
1 parent 8858448 commit f39a9c6

File tree

3 files changed

+44
-5
lines changed

3 files changed

+44
-5
lines changed

Documentation/git-remote.txt

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ SYNOPSIS
1919
'git remote set-url' [--push] <name> <newurl> [<oldurl>]
2020
'git remote set-url --add' [--push] <name> <newurl>
2121
'git remote set-url --delete' [--push] <name> <url>
22+
'git remote set-url --save-to-push' <name> <url>
2223
'git remote' [-v | --verbose] 'show' [-n] <name>...
2324
'git remote prune' [-n | --dry-run] <name>...
2425
'git remote' [-v | --verbose] 'update' [-p | --prune] [(<group> | <remote>)...]
@@ -155,6 +156,17 @@ With `--delete`, instead of changing existing URLs, all URLs matching
155156
regex <url> are deleted for remote <name>. Trying to delete all
156157
non-push URLs is an error.
157158
+
159+
With `--save-to-push`, the current URL is saved into the push URL before
160+
setting the URL to <url>. Note that this command will not work if more than one
161+
URL is defined because the behavior would be ambiguous. A use-case for this
162+
feature is that you may have started your interaction with the repository with
163+
a single authenticated URL that can be used for both fetching and pushing, but
164+
over time you may have become sick of having to authenticate only to fetch. In
165+
such a case, you can feed an unauthenticated/anonymous fetch URL to set-url
166+
with this option, so that the authenticated URL that you have been using for
167+
pushing becomes the pushURL, and the new, unauthenticated/anonymous URL will be
168+
used for fetching.
169+
+
158170
Note that the push URL and the fetch URL, even though they can
159171
be set differently, must still refer to the same place. What you
160172
pushed to the push URL should be what you would see if you

builtin/remote.c

Lines changed: 21 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,9 @@ static const char * const builtin_remote_usage[] = {
2424
N_("git remote set-branches [--add] <name> <branch>..."),
2525
N_("git remote get-url [--push] [--all] <name>"),
2626
N_("git remote set-url [--push] <name> <newurl> [<oldurl>]"),
27-
N_("git remote set-url --add <name> <newurl>"),
28-
N_("git remote set-url --delete <name> <url>"),
27+
N_("git remote set-url --add [--push] <name> <newurl>"),
28+
N_("git remote set-url --delete [--push] <name> <url>"),
29+
N_("git remote set-url --save-to-push <name> <url>"),
2930
NULL
3031
};
3132

@@ -77,8 +78,9 @@ static const char * const builtin_remote_geturl_usage[] = {
7778

7879
static const char * const builtin_remote_seturl_usage[] = {
7980
N_("git remote set-url [--push] <name> <newurl> [<oldurl>]"),
80-
N_("git remote set-url --add <name> <newurl>"),
81-
N_("git remote set-url --delete <name> <url>"),
81+
N_("git remote set-url --add [--push] <name> <newurl>"),
82+
N_("git remote set-url --delete [--push] <name> <url>"),
83+
N_("git remote set-url --save-to-push <name> <url>"),
8284
NULL
8385
};
8486

@@ -1519,7 +1521,7 @@ static int get_url(int argc, const char **argv)
15191521

15201522
static int set_url(int argc, const char **argv)
15211523
{
1522-
int i, push_mode = 0, add_mode = 0, delete_mode = 0;
1524+
int i, push_mode = 0, save_to_push = 0, add_mode = 0, delete_mode = 0;
15231525
int matches = 0, negative_matches = 0;
15241526
const char *remotename = NULL;
15251527
const char *newurl = NULL;
@@ -1532,6 +1534,8 @@ static int set_url(int argc, const char **argv)
15321534
struct option options[] = {
15331535
OPT_BOOL('\0', "push", &push_mode,
15341536
N_("manipulate push URLs")),
1537+
OPT_BOOL('\0', "save-to-push", &save_to_push,
1538+
N_("change fetching URL behavior")),
15351539
OPT_BOOL('\0', "add", &add_mode,
15361540
N_("add URL")),
15371541
OPT_BOOL('\0', "delete", &delete_mode,
@@ -1543,6 +1547,8 @@ static int set_url(int argc, const char **argv)
15431547

15441548
if (add_mode && delete_mode)
15451549
die(_("--add --delete doesn't make sense"));
1550+
if (save_to_push && (push_mode || add_mode || delete_mode))
1551+
die(_("--save-to-push cannot be used with other options"));
15461552

15471553
if (argc < 3 || argc > 4 || ((add_mode || delete_mode) && argc != 3))
15481554
usage_with_options(builtin_remote_seturl_usage, options);
@@ -1564,6 +1570,16 @@ static int set_url(int argc, const char **argv)
15641570
urlset = remote->pushurl;
15651571
urlset_nr = remote->pushurl_nr;
15661572
} else {
1573+
if (save_to_push) {
1574+
if (remote->url_nr != 1)
1575+
die(_("--save-to-push can only be used when only one url is defined"));
1576+
1577+
strbuf_addf(&name_buf, "remote.%s.pushurl", remotename);
1578+
git_config_set_multivar(name_buf.buf,
1579+
remote->url[0], "^$", 0);
1580+
strbuf_reset(&name_buf);
1581+
}
1582+
15671583
strbuf_addf(&name_buf, "remote.%s.url", remotename);
15681584
urlset = remote->url;
15691585
urlset_nr = remote->url_nr;

t/t5505-remote.sh

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1194,6 +1194,17 @@ test_expect_success 'remote set-url --delete baz' '
11941194
cmp expect actual
11951195
'
11961196

1197+
test_expect_success 'remote set-url --save-to-push bbb' '
1198+
git remote set-url --save-to-push someremote bbb &&
1199+
echo bbb >expect &&
1200+
echo "YYY" >>expect &&
1201+
echo ccc >>expect &&
1202+
git config --get-all remote.someremote.url >actual &&
1203+
echo "YYY" >>actual &&
1204+
git config --get-all remote.someremote.pushurl >>actual &&
1205+
cmp expect actual
1206+
'
1207+
11971208
test_expect_success 'extra args: setup' '
11981209
# add a dummy origin so that this does not trigger failure
11991210
git remote add origin .

0 commit comments

Comments
 (0)