Change-Id: I01821d6a9fbed7a5fe4619884e42937fbd6909cetags/v4.8.0.201705170830-rc1
package org.eclipse.jgit.transport; | package org.eclipse.jgit.transport; | ||||
import static java.nio.charset.StandardCharsets.UTF_8; | |||||
import static org.eclipse.jgit.lib.Constants.OBJ_BLOB; | |||||
import static org.junit.Assert.assertEquals; | import static org.junit.Assert.assertEquals; | ||||
import static org.junit.Assert.assertNotNull; | |||||
import static org.junit.Assert.assertNull; | import static org.junit.Assert.assertNull; | ||||
import static org.junit.Assert.assertTrue; | import static org.junit.Assert.assertTrue; | ||||
import static org.junit.Assert.fail; | import static org.junit.Assert.fail; | ||||
import java.util.Set; | import java.util.Set; | ||||
import org.eclipse.jgit.errors.MissingBundlePrerequisiteException; | import org.eclipse.jgit.errors.MissingBundlePrerequisiteException; | ||||
import org.eclipse.jgit.errors.MissingObjectException; | |||||
import org.eclipse.jgit.errors.NotSupportedException; | import org.eclipse.jgit.errors.NotSupportedException; | ||||
import org.eclipse.jgit.errors.TransportException; | import org.eclipse.jgit.errors.TransportException; | ||||
import org.eclipse.jgit.internal.storage.dfs.DfsRepositoryDescription; | |||||
import org.eclipse.jgit.internal.storage.dfs.InMemoryRepository; | |||||
import org.eclipse.jgit.lib.Constants; | |||||
import org.eclipse.jgit.lib.NullProgressMonitor; | import org.eclipse.jgit.lib.NullProgressMonitor; | ||||
import org.eclipse.jgit.lib.ObjectId; | import org.eclipse.jgit.lib.ObjectId; | ||||
import org.eclipse.jgit.lib.ObjectInserter; | |||||
import org.eclipse.jgit.lib.ObjectReader; | |||||
import org.eclipse.jgit.lib.Ref; | import org.eclipse.jgit.lib.Ref; | ||||
import org.eclipse.jgit.lib.Repository; | import org.eclipse.jgit.lib.Repository; | ||||
import org.eclipse.jgit.revwalk.RevCommit; | import org.eclipse.jgit.revwalk.RevCommit; | ||||
assertTrue(caught); | assertTrue(caught); | ||||
} | } | ||||
@Test | |||||
public void testCustomObjectReader() throws Exception { | |||||
String refName = "refs/heads/blob"; | |||||
String data = "unflushed data"; | |||||
ObjectId id; | |||||
ByteArrayOutputStream out = new ByteArrayOutputStream(); | |||||
try (Repository repo = new InMemoryRepository( | |||||
new DfsRepositoryDescription("repo")); | |||||
ObjectInserter ins = repo.newObjectInserter(); | |||||
ObjectReader or = ins.newReader()) { | |||||
id = ins.insert(OBJ_BLOB, Constants.encode(data)); | |||||
BundleWriter bw = new BundleWriter(or); | |||||
bw.include(refName, id); | |||||
bw.writeBundle(NullProgressMonitor.INSTANCE, out); | |||||
assertNull(repo.exactRef(refName)); | |||||
try { | |||||
repo.open(id, OBJ_BLOB); | |||||
fail("We should not be able to open the unflushed blob"); | |||||
} catch (MissingObjectException e) { | |||||
// Expected. | |||||
} | |||||
} | |||||
try (Repository repo = new InMemoryRepository( | |||||
new DfsRepositoryDescription("copy"))) { | |||||
fetchFromBundle(repo, out.toByteArray()); | |||||
Ref ref = repo.exactRef(refName); | |||||
assertNotNull(ref); | |||||
assertEquals(id, ref.getObjectId()); | |||||
assertEquals(data, new String(repo.open(id, OBJ_BLOB).getBytes(), UTF_8)); | |||||
} | |||||
} | |||||
private static FetchResult fetchFromBundle(final Repository newRepo, | private static FetchResult fetchFromBundle(final Repository newRepo, | ||||
final byte[] bundle) throws URISyntaxException, | final byte[] bundle) throws URISyntaxException, | ||||
NotSupportedException, TransportException { | NotSupportedException, TransportException { |
import org.eclipse.jgit.lib.AnyObjectId; | import org.eclipse.jgit.lib.AnyObjectId; | ||||
import org.eclipse.jgit.lib.Constants; | import org.eclipse.jgit.lib.Constants; | ||||
import org.eclipse.jgit.lib.ObjectId; | import org.eclipse.jgit.lib.ObjectId; | ||||
import org.eclipse.jgit.lib.ObjectReader; | |||||
import org.eclipse.jgit.lib.ProgressMonitor; | import org.eclipse.jgit.lib.ProgressMonitor; | ||||
import org.eclipse.jgit.lib.Ref; | import org.eclipse.jgit.lib.Ref; | ||||
import org.eclipse.jgit.lib.Repository; | import org.eclipse.jgit.lib.Repository; | ||||
public class BundleWriter { | public class BundleWriter { | ||||
private final Repository db; | private final Repository db; | ||||
private final ObjectReader reader; | |||||
private final Map<String, ObjectId> include; | private final Map<String, ObjectId> include; | ||||
private final Set<RevCommit> assume; | private final Set<RevCommit> assume; | ||||
* @param repo | * @param repo | ||||
* repository where objects are stored. | * repository where objects are stored. | ||||
*/ | */ | ||||
public BundleWriter(final Repository repo) { | |||||
public BundleWriter(Repository repo) { | |||||
db = repo; | db = repo; | ||||
reader = null; | |||||
include = new TreeMap<>(); | |||||
assume = new HashSet<>(); | |||||
tagTargets = new HashSet<>(); | |||||
} | |||||
/** | |||||
* Create a writer for a bundle. | |||||
* | |||||
* @param or | |||||
* reader for reading objects. Will be closed at the end of {@link | |||||
* #writeBundle(ProgressMonitor, OutputStream)}, but readers may be | |||||
* reused after closing. | |||||
* @since 4.8 | |||||
*/ | |||||
public BundleWriter(ObjectReader or) { | |||||
db = null; | |||||
reader = or; | |||||
include = new TreeMap<>(); | include = new TreeMap<>(); | ||||
assume = new HashSet<>(); | assume = new HashSet<>(); | ||||
tagTargets = new HashSet<>(); | tagTargets = new HashSet<>(); | ||||
* | * | ||||
* @param pc | * @param pc | ||||
* configuration controlling packing parameters. If null the | * configuration controlling packing parameters. If null the | ||||
* source repository's settings will be used. | |||||
* source repository's settings will be used, or the default | |||||
* settings if constructed without a repo. | |||||
*/ | */ | ||||
public void setPackConfig(PackConfig pc) { | public void setPackConfig(PackConfig pc) { | ||||
this.packConfig = pc; | this.packConfig = pc; | ||||
*/ | */ | ||||
public void writeBundle(ProgressMonitor monitor, OutputStream os) | public void writeBundle(ProgressMonitor monitor, OutputStream os) | ||||
throws IOException { | throws IOException { | ||||
PackConfig pc = packConfig; | |||||
if (pc == null) | |||||
pc = new PackConfig(db); | |||||
try (PackWriter packWriter = new PackWriter(pc, db.newObjectReader())) { | |||||
try (PackWriter packWriter = newPackWriter()) { | |||||
packWriter.setObjectCountCallback(callback); | packWriter.setObjectCountCallback(callback); | ||||
final HashSet<ObjectId> inc = new HashSet<>(); | final HashSet<ObjectId> inc = new HashSet<>(); | ||||
} | } | ||||
} | } | ||||
private PackWriter newPackWriter() { | |||||
PackConfig pc = packConfig; | |||||
if (pc == null) { | |||||
pc = db != null ? new PackConfig(db) : new PackConfig(); | |||||
} | |||||
return new PackWriter(pc, reader != null ? reader : db.newObjectReader()); | |||||
} | |||||
/** | /** | ||||
* Set the {@link ObjectCountCallback}. | * Set the {@link ObjectCountCallback}. | ||||
* <p> | * <p> |