1
2
3
4
5
6
7
8
9
10
11 package org.eclipse.jgit.transport;
12
13 import static org.junit.Assert.assertEquals;
14 import static org.junit.Assert.assertNotNull;
15 import static org.junit.Assert.assertTrue;
16
17 import java.io.IOException;
18 import java.io.OutputStream;
19 import java.util.HashMap;
20 import java.util.HashSet;
21 import java.util.Map;
22
23 import org.eclipse.jgit.errors.NotSupportedException;
24 import org.eclipse.jgit.errors.TransportException;
25 import org.eclipse.jgit.lib.ObjectId;
26 import org.eclipse.jgit.lib.ObjectIdRef;
27 import org.eclipse.jgit.lib.ProgressMonitor;
28 import org.eclipse.jgit.lib.Ref;
29 import org.eclipse.jgit.lib.RefUpdate.Result;
30 import org.eclipse.jgit.lib.Repository;
31 import org.eclipse.jgit.lib.TextProgressMonitor;
32 import org.eclipse.jgit.test.resources.SampleDataRepositoryTestCase;
33 import org.eclipse.jgit.transport.RemoteRefUpdate.Status;
34 import org.junit.Before;
35 import org.junit.Test;
36
37 public class PushProcessTest extends SampleDataRepositoryTestCase {
38 private PushProcess process;
39
40 private MockTransport transport;
41
42 private HashSet<RemoteRefUpdate> refUpdates;
43
44 private HashSet<Ref> advertisedRefs;
45
46 private Status connectionUpdateStatus;
47
48 @Override
49 @Before
50 public void setUp() throws Exception {
51 super.setUp();
52 transport = new MockTransport(db, new URIish());
53 refUpdates = new HashSet<>();
54 advertisedRefs = new HashSet<>();
55 connectionUpdateStatus = Status.OK;
56 }
57
58
59
60
61
62
63 @Test
64 public void testUpdateFastForward() throws IOException {
65 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
66 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
67 "refs/heads/master", false, null, null);
68 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
69 ObjectId.fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
70 testOneUpdateStatus(rru, ref, Status.OK, Boolean.TRUE);
71 }
72
73
74
75
76
77
78
79 @Test
80 public void testUpdateNonFastForwardUnknownObject() throws IOException {
81 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
82 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
83 "refs/heads/master", false, null, null);
84 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
85 ObjectId.fromString("0000000000000000000000000000000000000001"));
86 testOneUpdateStatus(rru, ref, Status.REJECTED_NONFASTFORWARD, null);
87 }
88
89
90
91
92
93
94
95 @Test
96 public void testUpdateNonFastForward() throws IOException {
97 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
98 "ac7e7e44c1885efb472ad54a78327d66bfc4ecef",
99 "refs/heads/master", false, null, null);
100 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
101 ObjectId.fromString("2c349335b7f797072cf729c4f3bb0914ecb6dec9"));
102 testOneUpdateStatus(rru, ref, Status.REJECTED_NONFASTFORWARD, null);
103 }
104
105
106
107
108
109
110 @Test
111 public void testUpdateNonFastForwardForced() throws IOException {
112 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
113 "ac7e7e44c1885efb472ad54a78327d66bfc4ecef",
114 "refs/heads/master", true, null, null);
115 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
116 ObjectId.fromString("2c349335b7f797072cf729c4f3bb0914ecb6dec9"));
117 testOneUpdateStatus(rru, ref, Status.OK, Boolean.FALSE);
118 }
119
120
121
122
123
124
125 @Test
126 public void testUpdateCreateRef() throws IOException {
127 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
128 "ac7e7e44c1885efb472ad54a78327d66bfc4ecef",
129 "refs/heads/master", false, null, null);
130 testOneUpdateStatus(rru, null, Status.OK, Boolean.TRUE);
131 }
132
133
134
135
136
137
138 @Test
139 public void testUpdateDelete() throws IOException {
140 final RemoteRefUpdate rru = new RemoteRefUpdate(db, (String) null,
141 "refs/heads/master", false, null, null);
142 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
143 ObjectId.fromString("2c349335b7f797072cf729c4f3bb0914ecb6dec9"));
144 testOneUpdateStatus(rru, ref, Status.OK, Boolean.TRUE);
145 }
146
147
148
149
150
151
152
153 @Test
154 public void testUpdateDeleteNonExisting() throws IOException {
155 final RemoteRefUpdate rru = new RemoteRefUpdate(db, (String) null,
156 "refs/heads/master", false, null, null);
157 testOneUpdateStatus(rru, null, Status.NON_EXISTING, null);
158 }
159
160
161
162
163
164
165 @Test
166 public void testUpdateUpToDate() throws IOException {
167 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
168 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
169 "refs/heads/master", false, null, null);
170 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
171 ObjectId.fromString("2c349335b7f797072cf729c4f3bb0914ecb6dec9"));
172 testOneUpdateStatus(rru, ref, Status.UP_TO_DATE, null);
173 }
174
175
176
177
178
179
180 @Test
181 public void testUpdateExpectedRemote() throws IOException {
182 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
183 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
184 "refs/heads/master", false, null, ObjectId
185 .fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
186 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
187 ObjectId.fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
188 testOneUpdateStatus(rru, ref, Status.OK, Boolean.TRUE);
189 }
190
191
192
193
194
195
196
197 @Test
198 public void testUpdateUnexpectedRemote() throws IOException {
199 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
200 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
201 "refs/heads/master", false, null, ObjectId
202 .fromString("0000000000000000000000000000000000000001"));
203 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
204 ObjectId.fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
205 testOneUpdateStatus(rru, ref, Status.REJECTED_REMOTE_CHANGED, null);
206 }
207
208
209
210
211
212
213
214
215 @Test
216 public void testUpdateUnexpectedRemoteVsForce() throws IOException {
217 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
218 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
219 "refs/heads/master", true, null, ObjectId
220 .fromString("0000000000000000000000000000000000000001"));
221 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
222 ObjectId.fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
223 testOneUpdateStatus(rru, ref, Status.REJECTED_REMOTE_CHANGED, null);
224 }
225
226
227
228
229
230
231 @Test
232 public void testUpdateRejectedByConnection() throws IOException {
233 connectionUpdateStatus = Status.REJECTED_OTHER_REASON;
234 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
235 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
236 "refs/heads/master", false, null, null);
237 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
238 ObjectId.fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
239 testOneUpdateStatus(rru, ref, Status.REJECTED_OTHER_REASON, null);
240 }
241
242
243
244
245
246
247
248 @Test
249 public void testUpdateMixedCases() throws IOException {
250 final RemoteRefUpdate rruOk = new RemoteRefUpdate(db, (String) null,
251 "refs/heads/master", false, null, null);
252 final Ref refToChange = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
253 ObjectId.fromString("2c349335b7f797072cf729c4f3bb0914ecb6dec9"));
254 final RemoteRefUpdate rruReject = new RemoteRefUpdate(db,
255 (String) null, "refs/heads/nonexisting", false, null, null);
256 refUpdates.add(rruOk);
257 refUpdates.add(rruReject);
258 advertisedRefs.add(refToChange);
259 executePush();
260 assertEquals(Status.OK, rruOk.getStatus());
261 assertTrue(rruOk.isFastForward());
262 assertEquals(Status.NON_EXISTING, rruReject.getStatus());
263 }
264
265
266
267
268
269
270 @Test
271 public void testTrackingRefUpdateEnabled() throws IOException {
272 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
273 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
274 "refs/heads/master", false, "refs/remotes/test/master", null);
275 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
276 ObjectId.fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
277 refUpdates.add(rru);
278 advertisedRefs.add(ref);
279 final PushResult result = executePush();
280 final TrackingRefUpdate tru = result
281 .getTrackingRefUpdate("refs/remotes/test/master");
282 assertNotNull(tru);
283 assertEquals("refs/remotes/test/master", tru.getLocalName());
284 assertEquals(Result.NEW, tru.getResult());
285 }
286
287
288
289
290
291
292 @Test
293 public void testTrackingRefUpdateDisabled() throws IOException {
294 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
295 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
296 "refs/heads/master", false, null, null);
297 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
298 ObjectId.fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
299 refUpdates.add(rru);
300 advertisedRefs.add(ref);
301 final PushResult result = executePush();
302 assertTrue(result.getTrackingRefUpdates().isEmpty());
303 }
304
305
306
307
308
309
310 @Test
311 public void testTrackingRefUpdateOnReject() throws IOException {
312 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
313 "ac7e7e44c1885efb472ad54a78327d66bfc4ecef",
314 "refs/heads/master", false, null, null);
315 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
316 ObjectId.fromString("2c349335b7f797072cf729c4f3bb0914ecb6dec9"));
317 final PushResult result = testOneUpdateStatus(rru, ref,
318 Status.REJECTED_NONFASTFORWARD, null);
319 assertTrue(result.getTrackingRefUpdates().isEmpty());
320 }
321
322
323
324
325
326
327 @Test
328 public void testPushResult() throws IOException {
329 final RemoteRefUpdate rru = new RemoteRefUpdate(db,
330 "2c349335b7f797072cf729c4f3bb0914ecb6dec9",
331 "refs/heads/master", false, "refs/remotes/test/master", null);
332 final Ref ref = new ObjectIdRef.Unpeeled(Ref.Storage.LOOSE, "refs/heads/master",
333 ObjectId.fromString("ac7e7e44c1885efb472ad54a78327d66bfc4ecef"));
334 refUpdates.add(rru);
335 advertisedRefs.add(ref);
336 final PushResult result = executePush();
337 assertEquals(1, result.getTrackingRefUpdates().size());
338 assertEquals(1, result.getAdvertisedRefs().size());
339 assertEquals(1, result.getRemoteUpdates().size());
340 assertNotNull(result.getTrackingRefUpdate("refs/remotes/test/master"));
341 assertNotNull(result.getAdvertisedRef("refs/heads/master"));
342 assertNotNull(result.getRemoteUpdate("refs/heads/master"));
343 }
344
345 private PushResult testOneUpdateStatus(final RemoteRefUpdate rru,
346 final Ref advertisedRef, final Status expectedStatus,
347 Boolean fastForward) throws NotSupportedException,
348 TransportException {
349 refUpdates.add(rru);
350 if (advertisedRef != null)
351 advertisedRefs.add(advertisedRef);
352 final PushResult result = executePush();
353 assertEquals(expectedStatus, rru.getStatus());
354 if (fastForward != null)
355 assertEquals(fastForward, Boolean.valueOf(rru.isFastForward()));
356 return result;
357 }
358
359 private PushResult executePush() throws NotSupportedException,
360 TransportException {
361 process = new PushProcess(transport, refUpdates);
362 return process.execute(new TextProgressMonitor());
363 }
364
365 private class MockTransport extends Transport {
366 MockTransport(Repository local, URIish uri) {
367 super(local, uri);
368 }
369
370 @Override
371 public FetchConnection openFetch() throws NotSupportedException,
372 TransportException {
373 throw new NotSupportedException("mock");
374 }
375
376 @Override
377 public PushConnection openPush() throws NotSupportedException,
378 TransportException {
379 return new MockPushConnection();
380 }
381
382 @Override
383 public void close() {
384
385 }
386 }
387
388 private class MockPushConnection extends BaseConnection implements
389 PushConnection {
390 MockPushConnection() {
391 final Map<String, Ref> refsMap = new HashMap<>();
392 for (Ref r : advertisedRefs)
393 refsMap.put(r.getName(), r);
394 available(refsMap);
395 }
396
397 @Override
398 public void close() {
399
400 }
401
402 @Override
403 public void push(ProgressMonitor monitor,
404 Map<String, RemoteRefUpdate> refsToUpdate, OutputStream out)
405 throws TransportException {
406 push(monitor, refsToUpdate);
407 }
408
409 @Override
410 public void push(ProgressMonitor monitor,
411 Map<String, RemoteRefUpdate> refsToUpdate)
412 throws TransportException {
413 for (RemoteRefUpdate rru : refsToUpdate.values()) {
414 assertEquals(Status.NOT_ATTEMPTED, rru.getStatus());
415 rru.setStatus(connectionUpdateStatus);
416 }
417 }
418 }
419 }