Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 22 additions & 0 deletions jgit/src/main/java/org/openrewrite/jgit/api/CloneCommand.java
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,8 @@ public class CloneCommand extends TransportCommand<CloneCommand, Git> {

private TagOpt tagOption;

private Integer depth;

private enum FETCH_TYPE {
MULTIPLE_BRANCHES, ALL_BRANCHES, MIRROR
}
Expand Down Expand Up @@ -306,6 +308,9 @@ private FetchResult fetch(Repository clonedRepo, URIish u)
fetchAll ? TagOpt.FETCH_TAGS : TagOpt.AUTO_FOLLOW);
}
command.setInitialBranch(branch);
if (depth != null) {
command.setDepth(depth.intValue());
}
configure(command);

return command.call();
Expand Down Expand Up @@ -737,6 +742,23 @@ public CloneCommand setCallback(Callback callback) {
return this;
}

/**
* Creates a shallow clone with a history truncated to the specified number
* of commits.
*
* @param depth
* the depth of the shallow clone
* @return {@code this}
* @since 5.13
*/
public CloneCommand setDepth(int depth) {
if (depth < 1) {
throw new IllegalArgumentException("depth must be >= 1");
}
this.depth = Integer.valueOf(depth);
return this;
}

private static void validateDirs(File directory, File gitDir, boolean bare)
throws IllegalStateException {
if (directory != null) {
Expand Down
23 changes: 23 additions & 0 deletions jgit/src/main/java/org/openrewrite/jgit/api/FetchCommand.java
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,8 @@ public class FetchCommand extends TransportCommand<FetchCommand, FetchResult> {

private String initialBranch;

private Integer depth;

/**
* Callback for status of fetch operation.
*
Expand Down Expand Up @@ -209,6 +211,9 @@ public FetchResult call() throws GitAPIException, InvalidRemoteException,
if (tagOption != null)
transport.setTagOpt(tagOption);
transport.setFetchThin(thin);
if (depth != null) {
transport.setDepth(depth.intValue());
}
configure(transport);
FetchResult result = transport.fetch(monitor,
applyOptions(refSpecs), initialBranch);
Expand Down Expand Up @@ -542,4 +547,22 @@ public FetchCommand setForceUpdate(boolean force) {
this.isForceUpdate = force;
return this;
}

/**
* Limits fetching to the specified number of commits from the tip of each
* remote branch history.
*
* @param depth
* the depth
* @return {@code this}
* @since 5.13
*/
public FetchCommand setDepth(int depth) {
checkCallable();
if (depth < 1) {
throw new IllegalArgumentException("depth must be >= 1");
}
this.depth = Integer.valueOf(depth);
return this;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,16 +12,22 @@

package org.openrewrite.jgit.transport;

import java.io.BufferedWriter;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.Date;
import java.util.HashSet;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Set;

import org.openrewrite.jgit.errors.PackProtocolException;
Expand All @@ -31,6 +37,7 @@
import org.openrewrite.jgit.internal.storage.file.PackLock;
import org.openrewrite.jgit.lib.AnyObjectId;
import org.openrewrite.jgit.lib.Config;
import org.openrewrite.jgit.lib.Constants;
import org.openrewrite.jgit.lib.MutableObjectId;
import org.openrewrite.jgit.lib.NullProgressMonitor;
import org.openrewrite.jgit.lib.ObjectId;
Expand Down Expand Up @@ -226,6 +233,8 @@ public abstract class BasePackFetchConnection extends BasePackConnection
*/
private final FilterSpec filterSpec;

private final Integer depth;

/**
* Create a new connection to fetch using the native git transport.
*
Expand All @@ -247,6 +256,7 @@ public BasePackFetchConnection(PackTransport packTransport) {
includeTags = transport.getTagOpt() != TagOpt.NO_TAGS;
thinPack = transport.isFetchThin();
filterSpec = transport.getFilterSpec();
depth = transport.getDepth();

if (local != null) {
walk = new RevWalk(local);
Expand Down Expand Up @@ -459,8 +469,12 @@ private void doFetchV2(ProgressMonitor monitor, Collection<Ref> want,
if (sentDone && line.startsWith("ERR ")) { //$NON-NLS-1$
throw new RemoteRepositoryException(uri, line.substring(4));
}
// "shallow-info", "wanted-refs", and "packfile-uris" would have to be
// handled here in that order.
// Handle shallow-info section for shallow clones
if (GitProtocolConstants.SECTION_SHALLOW_INFO.equals(line)) {
readShallowInfo();
line = pckIn.readString();
}
// "wanted-refs" and "packfile-uris" would have to be handled here
if (!GitProtocolConstants.SECTION_PACKFILE.equals(line)) {
throw new PackProtocolException(
MessageFormat.format(JGitText.get().expectedGot,
Expand Down Expand Up @@ -702,9 +716,48 @@ private boolean sendWants(Collection<Ref> want, PacketLineOut p)
if (!filterSpec.isNoOp()) {
p.writeString(filterSpec.filterLine());
}
sendShallow(p);
return true;
}

private void sendShallow(PacketLineOut p) throws IOException {
if (depth != null) {
p.writeString("deepen " + depth); //$NON-NLS-1$
}
}

private void readShallowInfo() throws IOException {
// Read shallow-info section and write to .git/shallow file
// The server sends "shallow <oid>" lines for commits that are shallow boundaries
List<ObjectId> shallowCommits = new ArrayList<>();
String line;
while ((line = pckIn.readString()) != PacketLineIn.END) {
if (PacketLineIn.isDelimiter(line)) {
break;
}
if (line.startsWith("shallow ")) { //$NON-NLS-1$
ObjectId id = ObjectId.fromString(line.substring(8));
shallowCommits.add(id);
}
// "unshallow" lines are ignored for now (used when deepening)
}

// Write shallow commits to .git/shallow file
if (!shallowCommits.isEmpty() && local != null) {
File gitDir = local.getDirectory();
if (gitDir != null) {
File shallowFile = new File(gitDir, Constants.SHALLOW);
try (BufferedWriter writer = Files.newBufferedWriter(
shallowFile.toPath(), StandardCharsets.UTF_8)) {
for (ObjectId id : shallowCommits) {
writer.write(id.name());
writer.newLine();
}
}
}
}
}

private Set<String> getCapabilitiesV2(Set<String> advertisedCapabilities)
throws TransportException {
Set<String> capabilities = new LinkedHashSet<>();
Expand All @@ -727,6 +780,7 @@ private Set<String> getCapabilitiesV2(Set<String> advertisedCapabilities)
JGitText.get().filterRequiresCapability);
}
// The FilterSpec will be added later in sendWants().
// Shallow capabilities are handled implicitly in protocol v2
return capabilities;
}

Expand Down Expand Up @@ -765,6 +819,10 @@ else if (wantCapability(line, OPTION_SIDE_BAND))
OPTION_MULTI_ACK_DETAILED));
}

if (depth != null) {
wantCapability(line, OPTION_SHALLOW);
}

if (!filterSpec.isNoOp() && !wantCapability(line, OPTION_FILTER)) {
throw new PackProtocolException(uri,
JGitText.get().filterRequiresCapability);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -371,6 +371,10 @@ private void updateFETCH_HEAD(FetchResult result) throws IOException {
}

private boolean askForIsComplete() throws TransportException {
// Shallow clones cannot assume completeness
if (transport.getDepth() != null) {
return false;
}
try {
try (ObjectWalk ow = new ObjectWalk(transport.local)) {
for (ObjectId want : askFor.keySet())
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -307,6 +307,13 @@ public final class GitProtocolConstants {
*/
public static final String SECTION_PACKFILE = "packfile"; //$NON-NLS-1$

/**
* Protocol V2 shallow-info section header.
*
* @since 5.13
*/
public static final String SECTION_SHALLOW_INFO = "shallow-info"; //$NON-NLS-1$

/**
* Protocol announcement for protocol version 1. This is the same as V0,
* except for this initial line.
Expand Down
27 changes: 27 additions & 0 deletions jgit/src/main/java/org/openrewrite/jgit/transport/Transport.java
Original file line number Diff line number Diff line change
Expand Up @@ -778,6 +778,8 @@ private static String findTrackingRefName(final String remoteName,
@Nullable
TransferConfig.ProtocolVersion protocol;

private Integer depth;

/**
* Create a new transport instance.
*
Expand Down Expand Up @@ -1204,6 +1206,31 @@ public void setPushOptions(List<String> pushOptions) {
this.pushOptions = pushOptions;
}

/**
* Get the depth of the shallow clone.
*
* @return the depth of the shallow clone, or null if not set
* @since 5.13
*/
public Integer getDepth() {
return depth;
}

/**
* Limit fetching to the specified number of commits from the tip of each
* remote branch history.
*
* @param depth
* the depth
* @since 5.13
*/
public void setDepth(int depth) {
if (depth < 1) {
throw new IllegalArgumentException("depth must be >= 1");
}
this.depth = Integer.valueOf(depth);
}

/**
* Fetch objects and refs from the remote repository to the local one.
* <p>
Expand Down
Loading