Skip to content

Commit

Permalink
transport-helper: factor out push_update_refs_status
Browse files Browse the repository at this point in the history
The update ref status part of push is useful for the export command
as well, factor it out into it's own function.

Also factor out push_update_ref_status to avoid a long loop without
an explicit condition with a non-trivial body.

Signed-off-by: Sverre Rabbelier <srabbelier@gmail.com>
Acked-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
  • Loading branch information
Sverre Rabbelier authored and Junio C Hamano committed Jul 19, 2011
1 parent 82670a5 commit d2e73c6
Showing 1 changed file with 84 additions and 69 deletions.
153 changes: 84 additions & 69 deletions transport-helper.c
Original file line number Diff line number Diff line change
Expand Up @@ -559,6 +559,88 @@ static int fetch(struct transport *transport,
return -1;
}

static void push_update_ref_status(struct strbuf *buf,
struct ref **ref,
struct ref *remote_refs)
{
char *refname, *msg;
int status;

if (!prefixcmp(buf->buf, "ok ")) {
status = REF_STATUS_OK;
refname = buf->buf + 3;
} else if (!prefixcmp(buf->buf, "error ")) {
status = REF_STATUS_REMOTE_REJECT;
refname = buf->buf + 6;
} else
die("expected ok/error, helper said '%s'\n", buf->buf);

msg = strchr(refname, ' ');
if (msg) {
struct strbuf msg_buf = STRBUF_INIT;
const char *end;

*msg++ = '\0';
if (!unquote_c_style(&msg_buf, msg, &end))
msg = strbuf_detach(&msg_buf, NULL);
else
msg = xstrdup(msg);
strbuf_release(&msg_buf);

if (!strcmp(msg, "no match")) {
status = REF_STATUS_NONE;
free(msg);
msg = NULL;
}
else if (!strcmp(msg, "up to date")) {
status = REF_STATUS_UPTODATE;
free(msg);
msg = NULL;
}
else if (!strcmp(msg, "non-fast forward")) {
status = REF_STATUS_REJECT_NONFASTFORWARD;
free(msg);
msg = NULL;
}
}

if (*ref)
*ref = find_ref_by_name(*ref, refname);
if (!*ref)
*ref = find_ref_by_name(remote_refs, refname);
if (!*ref) {
warning("helper reported unexpected status of %s", refname);
return;
}

if ((*ref)->status != REF_STATUS_NONE) {
/*
* Earlier, the ref was marked not to be pushed, so ignore the ref
* status reported by the remote helper if the latter is 'no match'.
*/
if (status == REF_STATUS_NONE)
return;
}

(*ref)->status = status;
(*ref)->remote_status = msg;
}

static void push_update_refs_status(struct helper_data *data,
struct ref *remote_refs)
{
struct strbuf buf = STRBUF_INIT;
struct ref *ref = remote_refs;
for (;;) {
recvline(data, &buf);
if (!buf.len)
break;

push_update_ref_status(&buf, &ref, remote_refs);
}
strbuf_release(&buf);
}

static int push_refs_with_push(struct transport *transport,
struct ref *remote_refs, int flags)
{
Expand Down Expand Up @@ -613,76 +695,9 @@ static int push_refs_with_push(struct transport *transport,

strbuf_addch(&buf, '\n');
sendline(data, &buf);

ref = remote_refs;
while (1) {
char *refname, *msg;
int status;

recvline(data, &buf);
if (!buf.len)
break;

if (!prefixcmp(buf.buf, "ok ")) {
status = REF_STATUS_OK;
refname = buf.buf + 3;
} else if (!prefixcmp(buf.buf, "error ")) {
status = REF_STATUS_REMOTE_REJECT;
refname = buf.buf + 6;
} else
die("expected ok/error, helper said '%s'\n", buf.buf);

msg = strchr(refname, ' ');
if (msg) {
struct strbuf msg_buf = STRBUF_INIT;
const char *end;

*msg++ = '\0';
if (!unquote_c_style(&msg_buf, msg, &end))
msg = strbuf_detach(&msg_buf, NULL);
else
msg = xstrdup(msg);
strbuf_release(&msg_buf);

if (!strcmp(msg, "no match")) {
status = REF_STATUS_NONE;
free(msg);
msg = NULL;
}
else if (!strcmp(msg, "up to date")) {
status = REF_STATUS_UPTODATE;
free(msg);
msg = NULL;
}
else if (!strcmp(msg, "non-fast forward")) {
status = REF_STATUS_REJECT_NONFASTFORWARD;
free(msg);
msg = NULL;
}
}

if (ref)
ref = find_ref_by_name(ref, refname);
if (!ref)
ref = find_ref_by_name(remote_refs, refname);
if (!ref) {
warning("helper reported unexpected status of %s", refname);
continue;
}

if (ref->status != REF_STATUS_NONE) {
/*
* Earlier, the ref was marked not to be pushed, so ignore the ref
* status reported by the remote helper if the latter is 'no match'.
*/
if (status == REF_STATUS_NONE)
continue;
}

ref->status = status;
ref->remote_status = msg;
}
strbuf_release(&buf);

push_update_refs_status(data, remote_refs);
return 0;
}

Expand Down

0 comments on commit d2e73c6

Please sign in to comment.