Fire progress callbacks also for pushes. It's not very useful to only know that a pre-receive hook has declined a push, you probably want to know why.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161
diff --git a/include/git2/remote.h b/include/git2/remote.h
index d57321f..88040d4 100644
--- a/include/git2/remote.h
+++ b/include/git2/remote.h
@@ -455,7 +455,8 @@ struct git_remote_callbacks {
/**
* Textual progress from the remote. Text send over the
* progress side-band will be passed to this function (this is
- * the 'counting objects' output.
+ * the 'counting objects' output. This callback should return a value less
+ * than zero to cancel the operation.
*/
int (*progress)(const char *str, int len, void *data);
diff --git a/src/transports/smart_protocol.c b/src/transports/smart_protocol.c
index 7e8fcdd..e5b56ea 100644
--- a/src/transports/smart_protocol.c
+++ b/src/transports/smart_protocol.c
@@ -478,7 +478,7 @@ int git_smart__download_pack(
git_transport *transport,
git_repository *repo,
git_transfer_progress *stats,
- git_transfer_progress_callback progress_cb,
+ git_transfer_progress_callback transfer_progress_cb,
void *progress_payload)
{
transport_smart *t = (transport_smart *)transport;
@@ -490,8 +490,8 @@ int git_smart__download_pack(
memset(stats, 0, sizeof(git_transfer_progress));
- if (progress_cb) {
- npp.callback = progress_cb;
+ if (transfer_progress_cb) {
+ npp.callback = transfer_progress_cb;
npp.payload = progress_payload;
npp.stats = stats;
t->packetsize_cb = &network_packetsize;
@@ -504,7 +504,7 @@ int git_smart__download_pack(
}
if ((error = git_repository_odb__weakptr(&odb, repo)) < 0 ||
- ((error = git_odb_write_pack(&writepack, odb, progress_cb, progress_payload)) != 0))
+ ((error = git_odb_write_pack(&writepack, odb, transfer_progress_cb, progress_payload)) != 0))
goto done;
/*
@@ -518,7 +518,7 @@ int git_smart__download_pack(
}
do {
- git_pkt *pkt;
+ git_pkt *pkt = NULL;
/* Check cancellation before network call */
if (t->cancelled.val) {
@@ -527,40 +527,34 @@ int git_smart__download_pack(
goto done;
}
- if ((error = recv_pkt(&pkt, buf)) < 0)
- goto done;
-
- /* Check cancellation after network call */
- if (t->cancelled.val) {
- giterr_clear();
- error = GIT_EUSER;
- goto done;
+ if ((error = recv_pkt(&pkt, buf)) >= 0) {
+ /* Check cancellation after network call */
+ if (t->cancelled.val) {
+ giterr_clear();
+ error = GIT_EUSER;
+ } else if (pkt->type == GIT_PKT_PROGRESS) {
+ if (t->progress_cb) {
+ git_pkt_progress *p = (git_pkt_progress *) pkt;
+ error = t->progress_cb(p->data, p->len, t->message_cb_payload);
+ }
+ } else if (pkt->type == GIT_PKT_DATA) {
+ git_pkt_data *p = (git_pkt_data *) pkt;
+ error = writepack->append(writepack, p->data, p->len, stats);
+ } else if (pkt->type == GIT_PKT_FLUSH) {
+ /* A flush indicates the end of the packfile */
+ git__free(pkt);
+ break;
+ }
}
- if (pkt->type == GIT_PKT_PROGRESS) {
- if (t->progress_cb) {
- git_pkt_progress *p = (git_pkt_progress *) pkt;
- error = t->progress_cb(p->data, p->len, t->message_cb_payload);
- if (error)
- goto done;
- }
- git__free(pkt);
- } else if (pkt->type == GIT_PKT_DATA) {
- git_pkt_data *p = (git_pkt_data *) pkt;
- error = writepack->append(writepack, p->data, p->len, stats);
+ git__free(pkt);
+ if (error < 0)
+ goto done;
- git__free(pkt);
- if (error != 0)
- goto done;
- } else if (pkt->type == GIT_PKT_FLUSH) {
- /* A flush indicates the end of the packfile */
- git__free(pkt);
- break;
- }
} while (1);
/*
- * Trailing execution of progress_cb, if necessary...
+ * Trailing execution of transfer_progress_cb, if necessary...
* Only the callback through the npp datastructure currently
* updates the last_fired_bytes value. It is possible that
* progress has already been reported with the correct
@@ -579,7 +573,7 @@ int git_smart__download_pack(
done:
if (writepack)
writepack->free(writepack);
- if (progress_cb) {
+ if (transfer_progress_cb) {
t->packetsize_cb = NULL;
t->packetsize_payload = NULL;
}
@@ -696,10 +690,11 @@ static int add_push_report_sideband_pkt(git_push *push, git_pkt_data *data_pkt)
return 0;
}
-static int parse_report(gitno_buffer *buf, git_push *push)
+static int parse_report(transport_smart *transport, git_push *push)
{
git_pkt *pkt = NULL;
const char *line_end = NULL;
+ gitno_buffer *buf = &transport->buffer;
int error, recvd;
for (;;) {
@@ -738,6 +733,10 @@ static int parse_report(gitno_buffer *buf, git_push *push)
error = -1;
break;
case GIT_PKT_PROGRESS:
+ if (transport->progress_cb) {
+ git_pkt_progress *p = (git_pkt_progress *) pkt;
+ error = transport->progress_cb(p->data, p->len, transport->message_cb_payload);
+ }
break;
default:
error = add_push_report_pkt(push, pkt);
@@ -953,7 +952,7 @@ int git_smart__push(git_transport *transport, git_push *push)
* we consider the pack to have been unpacked successfully */
if (!push->specs.length || !push->report_status)
push->unpack_ok = 1;
- else if ((error = parse_report(&t->buffer, push)) < 0)
+ else if ((error = parse_report(t, push)) < 0)
goto done;
/* If progress is being reported write the final report */