--- libs.git/apichanges.xml
+++ libs.git/apichanges.xml
@@ -112,6 +112,24 @@
The log command returns also branches containing the commits from the result.
+
+
+
+
+
+
+ - Adding new methods to GitClient allowing users to check a submodule's status, initialize them
+ after a clone and update them to a commit relevant to the state in the parent repository.
+ - Adding a new class GitSubmoduleStatus wrapping information about a submodule.
+
+
+
+
+
+
+
+
+ The log command returns also branches containing the commits from the result.
--- libs.git/manifest.mf
+++ libs.git/manifest.mf
@@ -1,4 +1,4 @@
Manifest-Version: 1.0
OpenIDE-Module: org.netbeans.libs.git/1
OpenIDE-Module-Localizing-Bundle: org/netbeans/libs/git/Bundle.properties
-OpenIDE-Module-Specification-Version: 1.15
+OpenIDE-Module-Specification-Version: 1.16
--- libs.git/src/org/netbeans/libs/git/GitClassFactoryImpl.java
+++ libs.git/src/org/netbeans/libs/git/GitClassFactoryImpl.java
@@ -54,6 +54,7 @@
import org.eclipse.jgit.revwalk.RevCommit;
import org.eclipse.jgit.revwalk.RevObject;
import org.eclipse.jgit.revwalk.RevTag;
+import org.eclipse.jgit.submodule.SubmoduleStatus;
import org.eclipse.jgit.transport.RemoteConfig;
import org.eclipse.jgit.transport.RemoteRefUpdate;
import org.eclipse.jgit.transport.TrackingRefUpdate;
@@ -185,4 +186,9 @@
branch.setTrackedBranch(trackedBranch);
}
+ @Override
+ public GitSubmoduleStatus createSubmoduleStatus (SubmoduleStatus status, File folder) {
+ return new GitSubmoduleStatus(status, folder);
+ }
+
}
--- libs.git/src/org/netbeans/libs/git/GitClient.java
+++ libs.git/src/org/netbeans/libs/git/GitClient.java
@@ -98,6 +98,9 @@
import org.netbeans.libs.git.jgit.commands.StatusCommand;
import org.netbeans.libs.git.jgit.commands.UnignoreCommand;
import org.netbeans.libs.git.jgit.commands.SetUpstreamBranchCommand;
+import org.netbeans.libs.git.jgit.commands.SubmoduleInitializeCommand;
+import org.netbeans.libs.git.jgit.commands.SubmoduleStatusCommand;
+import org.netbeans.libs.git.jgit.commands.SubmoduleUpdateCommand;
import org.netbeans.libs.git.progress.FileListener;
import org.netbeans.libs.git.progress.NotificationListener;
import org.netbeans.libs.git.progress.ProgressMonitor;
@@ -655,6 +658,24 @@
cmd.execute();
return cmd.getFileDifferences();
}
+
+ /**
+ * Scans for any submodules under given roots or in the whole repository and
+ * returns their status.
+ *
+ * @param roots files to search for submodules. If empty all submodules will
+ * be returned
+ * @param monitor command progress monitor
+ * @return status map of repository's submodules
+ * @throws GitException an unexpected error occurs
+ * @since 1.16
+ */
+ public Map getSubmoduleStatus (File[] roots, ProgressMonitor monitor) throws GitException {
+ Repository repository = gitRepository.getRepository();
+ SubmoduleStatusCommand cmd = new SubmoduleStatusCommand(repository, getClassFactory(), roots, monitor);
+ cmd.execute();
+ return cmd.getStatuses();
+ }
/**
* Returns remote configuration set up for this repository identified by a given remoteName
@@ -730,6 +751,23 @@
}
/**
+ * Initializes submodules and registers them in .git/config file.
+ *
+ * @param roots modules to initialize
+ * @param monitor progress monitor
+ * @return initialized submodule statuses
+ * @throws GitException an unexpected error occurs
+ * @since 1.16
+ */
+ public Map initializeSubmodules (File[] roots, ProgressMonitor monitor) throws GitException {
+ Repository repository = gitRepository.getRepository();
+ SubmoduleInitializeCommand cmd = new SubmoduleInitializeCommand(repository, getClassFactory(),
+ roots, monitor);
+ cmd.execute();
+ return cmd.getStatuses();
+ }
+
+ /**
* Returns files that are marked as modified between the HEAD and Index.
* @param roots files or folders to search for modified files.
* @param monitor progress monitor
@@ -1065,6 +1103,23 @@
return cmd.getModifiedIgnoreFiles();
}
+ /**
+ * Updates submodules. An equivalent to submodule update command.
+ *
+ * @param roots modules to update
+ * @param monitor progress monitor
+ * @return submodule statuses
+ * @throws GitException an unexpected error occurs
+ * @since 1.16
+ */
+ public Map updateSubmodules (File[] roots, ProgressMonitor monitor) throws GitException {
+ Repository repository = gitRepository.getRepository();
+ SubmoduleUpdateCommand cmd = new SubmoduleUpdateCommand(repository, getClassFactory(),
+ roots, monitor);
+ cmd.execute();
+ return cmd.getStatuses();
+ }
+
private GitClassFactory getClassFactory () {
if (gitFactory == null) {
gitFactory = GitClassFactoryImpl.getInstance();
--- libs.git/src/org/netbeans/libs/git/GitSubmoduleStatus.java
+++ libs.git/src/org/netbeans/libs/git/GitSubmoduleStatus.java
@@ -0,0 +1,125 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
+ *
+ * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
+ * Other names may be trademarks of their respective owners.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common
+ * Development and Distribution License("CDDL") (collectively, the
+ * "License"). You may not use this file except in compliance with the
+ * License. You can obtain a copy of the License at
+ * http://www.netbeans.org/cddl-gplv2.html
+ * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
+ * specific language governing permissions and limitations under the
+ * License. When distributing the software, include this License Header
+ * Notice in each file and include the License file at
+ * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the GPL Version 2 section of the License file that
+ * accompanied this code. If applicable, add the following below the
+ * License Header, with the fields enclosed by brackets [] replaced by
+ * your own identifying information:
+ * "Portions Copyrighted [year] [name of copyright owner]"
+ *
+ * If you wish your version of this file to be governed by only the CDDL
+ * or only the GPL Version 2, indicate your decision by adding
+ * "[Contributor] elects to include this software in this distribution
+ * under the [CDDL or GPL Version 2] license." If you do not indicate a
+ * single choice of license, a recipient has the option to distribute
+ * your version of this file under either the CDDL, the GPL Version 2 or
+ * to extend the choice of license to its licensees as provided above.
+ * However, if you add GPL Version 2 code and therefore, elected the GPL
+ * Version 2 license, then the option applies only if the new code is
+ * made subject to such option by the copyright holder.
+ *
+ * Contributor(s):
+ *
+ * Portions Copyrighted 2013 Sun Microsystems, Inc.
+ */
+package org.netbeans.libs.git;
+
+import java.io.File;
+import org.eclipse.jgit.submodule.SubmoduleStatus;
+import org.eclipse.jgit.submodule.SubmoduleStatusType;
+
+/**
+ * Describes current status of a repository's submodule
+ *
+ * @author Ondrej Vrabec
+ * @since 1.16
+ */
+public final class GitSubmoduleStatus {
+
+ private final SubmoduleStatus delegate;
+ private final StatusType statusType;
+ private final File folder;
+
+ /**
+ * Submodule's status
+ */
+ public enum StatusType {
+
+ /**
+ * Submodule's configuration is missing
+ */
+ MISSING,
+ /**
+ * Submodule's Git repository is not initialized
+ */
+ UNINITIALIZED,
+ /**
+ * Submodule's Git repository is initialized
+ */
+ INITIALIZED,
+ /**
+ * Submodule checked out commit is different than the commit referenced
+ * in the index tree
+ */
+ REV_CHECKED_OUT;
+ }
+
+ GitSubmoduleStatus (SubmoduleStatus delegate, File folder) {
+ this.delegate = delegate;
+ this.folder = folder;
+ this.statusType = parseStatus(delegate.getType());
+ }
+
+ /**
+ * Returns status of the submodule
+ * @return submodule's status
+ */
+ public StatusType getStatus () {
+ return statusType;
+ }
+
+ /**
+ * Returns the submodule's root folder.
+ * @return submodule's root folder.
+ */
+ public File getSubmoduleFolder () {
+ return folder;
+ }
+
+ /**
+ * Returns the commit id of the currently checked-out commit.
+ * @return submodule's commit id.
+ */
+ public String getHeadId () {
+ return delegate.getHeadId().getName();
+ }
+
+ /**
+ * Returns the state of the index in the submodule.
+ * @return submodule's index tree id.
+ */
+ public String getIndexId () {
+ return delegate.getIndexId().getName();
+ }
+
+ static StatusType parseStatus (SubmoduleStatusType status) {
+ return StatusType.valueOf(status.name());
+ }
+}
--- libs.git/src/org/netbeans/libs/git/jgit/GitClassFactory.java
+++ libs.git/src/org/netbeans/libs/git/jgit/GitClassFactory.java
@@ -55,6 +55,7 @@
import org.eclipse.jgit.revwalk.RevCommit;
import org.eclipse.jgit.revwalk.RevObject;
import org.eclipse.jgit.revwalk.RevTag;
+import org.eclipse.jgit.submodule.SubmoduleStatus;
import org.eclipse.jgit.transport.RemoteConfig;
import org.eclipse.jgit.transport.RemoteRefUpdate;
import org.eclipse.jgit.transport.TrackingRefUpdate;
@@ -73,6 +74,7 @@
import org.netbeans.libs.git.GitRevisionInfo.GitFileInfo;
import org.netbeans.libs.git.GitStatus;
import org.netbeans.libs.git.GitStatus.Status;
+import org.netbeans.libs.git.GitSubmoduleStatus;
import org.netbeans.libs.git.GitTag;
import org.netbeans.libs.git.GitTransportUpdate;
import org.netbeans.libs.git.GitUser;
@@ -113,6 +115,8 @@
public abstract GitStatus createStatus (boolean tracked, String path, String workTreePath, File file,
Status statusHeadIndex, Status statusIndexWC, Status statusHeadWC,
GitConflictDescriptor conflictDescriptor, boolean folder, DiffEntry diffEntry);
+
+ public abstract GitSubmoduleStatus createSubmoduleStatus (SubmoduleStatus status, File folder);
public abstract GitTag createTag (RevTag revTag);
--- libs.git/src/org/netbeans/libs/git/jgit/commands/SubmoduleInitializeCommand.java
+++ libs.git/src/org/netbeans/libs/git/jgit/commands/SubmoduleInitializeCommand.java
@@ -0,0 +1,104 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
+ *
+ * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
+ * Other names may be trademarks of their respective owners.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common
+ * Development and Distribution License("CDDL") (collectively, the
+ * "License"). You may not use this file except in compliance with the
+ * License. You can obtain a copy of the License at
+ * http://www.netbeans.org/cddl-gplv2.html
+ * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
+ * specific language governing permissions and limitations under the
+ * License. When distributing the software, include this License Header
+ * Notice in each file and include the License file at
+ * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the GPL Version 2 section of the License file that
+ * accompanied this code. If applicable, add the following below the
+ * License Header, with the fields enclosed by brackets [] replaced by
+ * your own identifying information:
+ * "Portions Copyrighted [year] [name of copyright owner]"
+ *
+ * If you wish your version of this file to be governed by only the CDDL
+ * or only the GPL Version 2, indicate your decision by adding
+ * "[Contributor] elects to include this software in this distribution
+ * under the [CDDL or GPL Version 2] license." If you do not indicate a
+ * single choice of license, a recipient has the option to distribute
+ * your version of this file under either the CDDL, the GPL Version 2 or
+ * to extend the choice of license to its licensees as provided above.
+ * However, if you add GPL Version 2 code and therefore, elected the GPL
+ * Version 2 license, then the option applies only if the new code is
+ * made subject to such option by the copyright holder.
+ *
+ * Contributor(s):
+ *
+ * Portions Copyrighted 2013 Sun Microsystems, Inc.
+ */
+
+package org.netbeans.libs.git.jgit.commands;
+
+import java.io.File;
+import java.util.Map;
+import org.eclipse.jgit.api.Git;
+import org.eclipse.jgit.api.errors.GitAPIException;
+import org.eclipse.jgit.api.errors.JGitInternalException;
+import org.eclipse.jgit.lib.Repository;
+import org.netbeans.libs.git.GitException;
+import org.netbeans.libs.git.GitSubmoduleStatus;
+import org.netbeans.libs.git.jgit.DelegatingGitProgressMonitor;
+import org.netbeans.libs.git.jgit.GitClassFactory;
+import org.netbeans.libs.git.jgit.Utils;
+import org.netbeans.libs.git.progress.ProgressMonitor;
+
+/**
+ *
+ * @author Ondrej Vrabec
+ */
+public class SubmoduleInitializeCommand extends GitCommand {
+
+ private final File[] roots;
+ private final SubmoduleStatusCommand statusCmd;
+
+ public SubmoduleInitializeCommand (Repository repository, GitClassFactory classFactory,
+ File[] roots, ProgressMonitor monitor) {
+ super(repository, classFactory, monitor);
+ this.roots = roots;
+ this.statusCmd = new SubmoduleStatusCommand(repository,
+ getClassFactory(), roots, new DelegatingGitProgressMonitor(monitor));
+ }
+
+ @Override
+ protected void run () throws GitException {
+ Repository repository = getRepository();
+ File workTree = repository.getWorkTree();
+ org.eclipse.jgit.api.SubmoduleInitCommand cmd = new Git(repository).submoduleInit();
+ for (String path : Utils.getRelativePaths(workTree, roots)) {
+ cmd.addPath(path);
+ }
+ try {
+ cmd.call();
+ statusCmd.run();
+ } catch (GitAPIException | JGitInternalException ex) {
+ throw new GitException(ex);
+ }
+ }
+
+ @Override
+ protected String getCommandDescription () {
+ StringBuilder sb = new StringBuilder("git submodule initialize"); //NOI18N
+ for (File root : roots) {
+ sb.append(" ").append(root.getAbsolutePath());
+ }
+ return sb.toString();
+ }
+
+ public Map getStatuses () {
+ return statusCmd.getStatuses();
+ }
+
+}
--- libs.git/src/org/netbeans/libs/git/jgit/commands/SubmoduleStatusCommand.java
+++ libs.git/src/org/netbeans/libs/git/jgit/commands/SubmoduleStatusCommand.java
@@ -0,0 +1,108 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
+ *
+ * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
+ * Other names may be trademarks of their respective owners.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common
+ * Development and Distribution License("CDDL") (collectively, the
+ * "License"). You may not use this file except in compliance with the
+ * License. You can obtain a copy of the License at
+ * http://www.netbeans.org/cddl-gplv2.html
+ * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
+ * specific language governing permissions and limitations under the
+ * License. When distributing the software, include this License Header
+ * Notice in each file and include the License file at
+ * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the GPL Version 2 section of the License file that
+ * accompanied this code. If applicable, add the following below the
+ * License Header, with the fields enclosed by brackets [] replaced by
+ * your own identifying information:
+ * "Portions Copyrighted [year] [name of copyright owner]"
+ *
+ * If you wish your version of this file to be governed by only the CDDL
+ * or only the GPL Version 2, indicate your decision by adding
+ * "[Contributor] elects to include this software in this distribution
+ * under the [CDDL or GPL Version 2] license." If you do not indicate a
+ * single choice of license, a recipient has the option to distribute
+ * your version of this file under either the CDDL, the GPL Version 2 or
+ * to extend the choice of license to its licensees as provided above.
+ * However, if you add GPL Version 2 code and therefore, elected the GPL
+ * Version 2 license, then the option applies only if the new code is
+ * made subject to such option by the copyright holder.
+ *
+ * Contributor(s):
+ *
+ * Portions Copyrighted 2013 Sun Microsystems, Inc.
+ */
+
+package org.netbeans.libs.git.jgit.commands;
+
+import java.io.File;
+import java.util.LinkedHashMap;
+import java.util.Map;
+import org.eclipse.jgit.api.Git;
+import org.eclipse.jgit.api.errors.GitAPIException;
+import org.eclipse.jgit.api.errors.JGitInternalException;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.submodule.SubmoduleStatus;
+import org.netbeans.libs.git.GitException;
+import org.netbeans.libs.git.GitSubmoduleStatus;
+import org.netbeans.libs.git.jgit.GitClassFactory;
+import org.netbeans.libs.git.jgit.Utils;
+import org.netbeans.libs.git.progress.ProgressMonitor;
+
+/**
+ *
+ * @author Ondrej Vrabec
+ */
+public class SubmoduleStatusCommand extends GitCommand {
+
+ private final File[] roots;
+ private final LinkedHashMap statuses;
+
+ public SubmoduleStatusCommand (Repository repository, GitClassFactory classFactory,
+ File[] roots, ProgressMonitor monitor) {
+ super(repository, classFactory, monitor);
+ this.roots = roots;
+ statuses = new LinkedHashMap<>();
+ }
+
+ @Override
+ protected void run () throws GitException {
+ Repository repository = getRepository();
+ File workTree = repository.getWorkTree();
+ org.eclipse.jgit.api.SubmoduleStatusCommand cmd = new Git(repository).submoduleStatus();
+ for (String path : Utils.getRelativePaths(workTree, roots)) {
+ cmd.addPath(path);
+ }
+ try {
+ Map result = cmd.call();
+ GitClassFactory fac = getClassFactory();
+ for (Map.Entry e : result.entrySet()) {
+ File root = new File(workTree, e.getKey());
+ statuses.put(root, fac.createSubmoduleStatus(e.getValue(), root));
+ }
+ } catch (GitAPIException | JGitInternalException ex) {
+ throw new GitException(ex);
+ }
+ }
+
+ @Override
+ protected String getCommandDescription () {
+ StringBuilder sb = new StringBuilder("git submodule status"); //NOI18N
+ for (File root : roots) {
+ sb.append(" ").append(root.getAbsolutePath());
+ }
+ return sb.toString();
+ }
+
+ public Map getStatuses () {
+ return statuses;
+ }
+
+}
--- libs.git/src/org/netbeans/libs/git/jgit/commands/SubmoduleUpdateCommand.java
+++ libs.git/src/org/netbeans/libs/git/jgit/commands/SubmoduleUpdateCommand.java
@@ -0,0 +1,108 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
+ *
+ * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
+ * Other names may be trademarks of their respective owners.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common
+ * Development and Distribution License("CDDL") (collectively, the
+ * "License"). You may not use this file except in compliance with the
+ * License. You can obtain a copy of the License at
+ * http://www.netbeans.org/cddl-gplv2.html
+ * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
+ * specific language governing permissions and limitations under the
+ * License. When distributing the software, include this License Header
+ * Notice in each file and include the License file at
+ * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the GPL Version 2 section of the License file that
+ * accompanied this code. If applicable, add the following below the
+ * License Header, with the fields enclosed by brackets [] replaced by
+ * your own identifying information:
+ * "Portions Copyrighted [year] [name of copyright owner]"
+ *
+ * If you wish your version of this file to be governed by only the CDDL
+ * or only the GPL Version 2, indicate your decision by adding
+ * "[Contributor] elects to include this software in this distribution
+ * under the [CDDL or GPL Version 2] license." If you do not indicate a
+ * single choice of license, a recipient has the option to distribute
+ * your version of this file under either the CDDL, the GPL Version 2 or
+ * to extend the choice of license to its licensees as provided above.
+ * However, if you add GPL Version 2 code and therefore, elected the GPL
+ * Version 2 license, then the option applies only if the new code is
+ * made subject to such option by the copyright holder.
+ *
+ * Contributor(s):
+ *
+ * Portions Copyrighted 2013 Sun Microsystems, Inc.
+ */
+
+package org.netbeans.libs.git.jgit.commands;
+
+import java.io.File;
+import java.util.Map;
+import org.eclipse.jgit.api.Git;
+import org.eclipse.jgit.api.errors.GitAPIException;
+import org.eclipse.jgit.api.errors.JGitInternalException;
+import org.eclipse.jgit.lib.Repository;
+import org.netbeans.libs.git.GitException;
+import org.netbeans.libs.git.GitSubmoduleStatus;
+import org.netbeans.libs.git.jgit.DelegatingGitProgressMonitor;
+import org.netbeans.libs.git.jgit.DelegatingProgressMonitor;
+import org.netbeans.libs.git.jgit.GitClassFactory;
+import org.netbeans.libs.git.jgit.Utils;
+import org.netbeans.libs.git.progress.ProgressMonitor;
+
+/**
+ *
+ * @author Ondrej Vrabec
+ */
+public class SubmoduleUpdateCommand extends GitCommand {
+
+ private final File[] roots;
+ private final SubmoduleStatusCommand statusCmd;
+ private final ProgressMonitor monitor;
+
+ public SubmoduleUpdateCommand (Repository repository, GitClassFactory classFactory,
+ File[] roots, ProgressMonitor monitor) {
+ super(repository, classFactory, monitor);
+ this.monitor = monitor;
+ this.roots = roots;
+ this.statusCmd = new SubmoduleStatusCommand(repository,
+ getClassFactory(), roots, new DelegatingGitProgressMonitor(monitor));
+ }
+
+ @Override
+ protected void run () throws GitException {
+ Repository repository = getRepository();
+ File workTree = repository.getWorkTree();
+ org.eclipse.jgit.api.SubmoduleUpdateCommand cmd = new Git(repository).submoduleUpdate();
+ for (String path : Utils.getRelativePaths(workTree, roots)) {
+ cmd.addPath(path);
+ }
+ try {
+ cmd.setProgressMonitor(new DelegatingProgressMonitor(monitor));
+ cmd.call();
+ statusCmd.run();
+ } catch (GitAPIException | JGitInternalException ex) {
+ throw new GitException(ex);
+ }
+ }
+
+ @Override
+ protected String getCommandDescription () {
+ StringBuilder sb = new StringBuilder("git submodule initialize"); //NOI18N
+ for (File root : roots) {
+ sb.append(" ").append(root.getAbsolutePath());
+ }
+ return sb.toString();
+ }
+
+ public Map getStatuses () {
+ return statusCmd.getStatuses();
+ }
+
+}
--- libs.git/test/unit/src/org/netbeans/libs/git/GitEnumsStateTest.java
+++ libs.git/test/unit/src/org/netbeans/libs/git/GitEnumsStateTest.java
@@ -47,6 +47,7 @@
import org.eclipse.jgit.api.RebaseResult;
import org.eclipse.jgit.lib.RefUpdate;
import org.eclipse.jgit.lib.RepositoryState;
+import org.eclipse.jgit.submodule.SubmoduleStatusType;
import org.eclipse.jgit.transport.RemoteRefUpdate;
import org.netbeans.libs.git.jgit.AbstractGitTestCase;
@@ -89,4 +90,10 @@
assertNotNull(GitRebaseResult.parseRebaseStatus(status));
}
}
+
+ public void testSubmoduleStatus () {
+ for (SubmoduleStatusType status : SubmoduleStatusType.values()) {
+ assertNotNull(GitSubmoduleStatus.parseStatus(status));
+ }
+ }
}
--- libs.git/test/unit/src/org/netbeans/libs/git/jgit/CommandsTestSuite.java
+++ libs.git/test/unit/src/org/netbeans/libs/git/jgit/CommandsTestSuite.java
@@ -76,6 +76,7 @@
import org.netbeans.libs.git.jgit.commands.RevertTest;
import org.netbeans.libs.git.jgit.commands.SetUpstreamBranchTest;
import org.netbeans.libs.git.jgit.commands.StatusTest;
+import org.netbeans.libs.git.jgit.commands.SubmoduleTest;
import org.netbeans.libs.git.jgit.commands.TagTest;
import org.netbeans.libs.git.jgit.commands.UnignoreTest;
@@ -122,6 +123,7 @@
suite.addTestSuite(ResetTest.class);
suite.addTestSuite(SetUpstreamBranchTest.class);
suite.addTestSuite(StatusTest.class);
+ suite.addTestSuite(SubmoduleTest.class);
suite.addTestSuite(TagTest.class);
suite.addTestSuite(UnignoreTest.class);
return suite;
--- libs.git/test/unit/src/org/netbeans/libs/git/jgit/commands/SubmoduleTest.java
+++ libs.git/test/unit/src/org/netbeans/libs/git/jgit/commands/SubmoduleTest.java
@@ -0,0 +1,230 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
+ *
+ * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
+ * Other names may be trademarks of their respective owners.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common
+ * Development and Distribution License("CDDL") (collectively, the
+ * "License"). You may not use this file except in compliance with the
+ * License. You can obtain a copy of the License at
+ * http://www.netbeans.org/cddl-gplv2.html
+ * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
+ * specific language governing permissions and limitations under the
+ * License. When distributing the software, include this License Header
+ * Notice in each file and include the License file at
+ * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the GPL Version 2 section of the License file that
+ * accompanied this code. If applicable, add the following below the
+ * License Header, with the fields enclosed by brackets [] replaced by
+ * your own identifying information:
+ * "Portions Copyrighted [year] [name of copyright owner]"
+ *
+ * If you wish your version of this file to be governed by only the CDDL
+ * or only the GPL Version 2, indicate your decision by adding
+ * "[Contributor] elects to include this software in this distribution
+ * under the [CDDL or GPL Version 2] license." If you do not indicate a
+ * single choice of license, a recipient has the option to distribute
+ * your version of this file under either the CDDL, the GPL Version 2 or
+ * to extend the choice of license to its licensees as provided above.
+ * However, if you add GPL Version 2 code and therefore, elected the GPL
+ * Version 2 license, then the option applies only if the new code is
+ * made subject to such option by the copyright holder.
+ *
+ * Contributor(s):
+ *
+ * Portions Copyrighted 2013 Sun Microsystems, Inc.
+ */
+
+package org.netbeans.libs.git.jgit.commands;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.Arrays;
+import java.util.Map;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.transport.RemoteConfig;
+import org.eclipse.jgit.transport.URIish;
+import org.netbeans.libs.git.GitClient;
+import org.netbeans.libs.git.GitSubmoduleStatus;
+import org.netbeans.libs.git.jgit.AbstractGitTestCase;
+import org.netbeans.libs.git.jgit.Utils;
+
+/**
+ *
+ * @author Ondrej Vrabec
+ */
+public class SubmoduleTest extends AbstractGitTestCase {
+
+ private Repository repository;
+ private Repository repositorySM1;
+ private Repository repositorySM2;
+ private File workDir;
+ private File moduleRepo;
+ private File submoduleRepo1;
+ private File submoduleRepo2;
+ private File submoduleFolder1;
+ private File submoduleFolder2;
+ private File f1;
+ private File f2;
+ private File f;
+
+ public SubmoduleTest (String testName) throws IOException {
+ super(testName);
+ }
+
+ @Override
+ protected void setUp() throws Exception {
+ super.setUp();
+ workDir = getWorkingDirectory();
+ repository = getRepository(getLocalGitRepository());
+
+ moduleRepo = new File(workDir.getParentFile(), "module");
+ GitClient client = getClient(moduleRepo);
+ client.init(NULL_PROGRESS_MONITOR);
+ submoduleRepo1 = new File(workDir.getParentFile(), "submodule1");
+ client = getClient(submoduleRepo1);
+ client.init(NULL_PROGRESS_MONITOR);
+ submoduleRepo2 = new File(workDir.getParentFile(), "submodule2");
+ client = getClient(submoduleRepo2);
+ client.init(NULL_PROGRESS_MONITOR);
+
+ client = getClient(workDir);
+ f = new File(workDir, "f");
+ write(f, "init");
+ client.add(new File[] { f }, NULL_PROGRESS_MONITOR);
+ client.commit(new File[] { f }, "init commit", null, null, NULL_PROGRESS_MONITOR);
+ RemoteConfig cfg = new RemoteConfig(repository.getConfig(), "origin");
+ cfg.addURI(new URIish(moduleRepo.toURI().toURL().toString()));
+ cfg.update(repository.getConfig());
+ repository.getConfig().save();
+ client.push("origin", Arrays.asList("refs/heads/master:refs/heads/master"),
+ Arrays.asList("+refs/heads/master:refs/remotes/origin/master"), NULL_PROGRESS_MONITOR);
+
+ File submodules = new File(workDir, "submodules");
+
+ submoduleFolder1 = new File(submodules, "submodule1");
+ submoduleFolder1.mkdirs();
+ getClient(submoduleFolder1).init(NULL_PROGRESS_MONITOR);
+ f1 = new File(submoduleFolder1, "file");
+ write(f1, "init");
+ getClient(submoduleFolder1).add(new File[] { f1 }, NULL_PROGRESS_MONITOR);
+ getClient(submoduleFolder1).commit(new File[] { f1 }, "init SM1 commit", null, null, NULL_PROGRESS_MONITOR);
+ repositorySM1 = getRepository(getClient(submoduleFolder1));
+ cfg = new RemoteConfig(repositorySM1.getConfig(), "origin");
+ cfg.addURI(new URIish(submoduleRepo1.toURI().toURL().toString()));
+ cfg.update(repositorySM1.getConfig());
+ repositorySM1.getConfig().save();
+ getClient(submoduleFolder1).push("origin", Arrays.asList("refs/heads/master:refs/heads/master"),
+ Arrays.asList("+refs/heads/master:refs/remotes/origin/master"), NULL_PROGRESS_MONITOR);
+
+
+ submoduleFolder2 = new File(submodules, "submodule2");
+ submoduleFolder2.mkdirs();
+ getClient(submoduleFolder2).init(NULL_PROGRESS_MONITOR);
+ f2 = new File(submoduleFolder2, "file");
+ write(f2, "init");
+ getClient(submoduleFolder2).add(new File[] { f2 }, NULL_PROGRESS_MONITOR);
+ getClient(submoduleFolder2).commit(new File[] { f2 }, "init SM1 commit", null, null, NULL_PROGRESS_MONITOR);
+ repositorySM2 = getRepository(getClient(submoduleFolder2));
+ cfg = new RemoteConfig(repositorySM2.getConfig(), "origin");
+ cfg.addURI(new URIish(submoduleRepo2.toURI().toURL().toString()));
+ cfg.update(repositorySM2.getConfig());
+ repositorySM2.getConfig().save();
+ getClient(submoduleFolder2).push("origin", Arrays.asList("refs/heads/master:refs/heads/master"),
+ Arrays.asList("+refs/heads/master:refs/remotes/origin/master"), NULL_PROGRESS_MONITOR);
+ }
+
+ public void testStatusEmpty () throws Exception {
+ GitClient client = getClient(workDir);
+ assertEquals(0, client.getSubmoduleStatus(new File[0], NULL_PROGRESS_MONITOR).size());
+ }
+
+ public void testStatusUninitialized () throws Exception {
+ prepareUninitializedWorkdir();
+
+ GitClient client = getClient(workDir);
+ Map status = client.getSubmoduleStatus(new File[] { f } , NULL_PROGRESS_MONITOR);
+ assertEquals(0, status.size());
+
+ status = client.getSubmoduleStatus(new File[] { submoduleFolder1 } , NULL_PROGRESS_MONITOR);
+ assertStatus(status.get(submoduleFolder1), GitSubmoduleStatus.StatusType.UNINITIALIZED,
+ submoduleFolder1);
+
+ status = client.getSubmoduleStatus(new File[] { submoduleFolder2 } , NULL_PROGRESS_MONITOR);
+ assertStatus(status.get(submoduleFolder2), GitSubmoduleStatus.StatusType.UNINITIALIZED,
+ submoduleFolder2);
+
+ status = client.getSubmoduleStatus(new File[0], NULL_PROGRESS_MONITOR);
+ assertStatus(status.get(submoduleFolder1), GitSubmoduleStatus.StatusType.UNINITIALIZED,
+ submoduleFolder1);
+ assertStatus(status.get(submoduleFolder2), GitSubmoduleStatus.StatusType.UNINITIALIZED,
+ submoduleFolder2);
+ }
+
+ public void testInitialize () throws Exception {
+ prepareUninitializedWorkdir();
+
+ GitClient client = getClient(workDir);
+ Map status = client.getSubmoduleStatus(new File[] { f } , NULL_PROGRESS_MONITOR);
+ assertEquals(0, status.size());
+
+ status = client.getSubmoduleStatus(new File[] { submoduleFolder1 }, NULL_PROGRESS_MONITOR);
+ assertStatus(status.get(submoduleFolder1), GitSubmoduleStatus.StatusType.UNINITIALIZED,
+ submoduleFolder1);
+
+ status = client.initializeSubmodules(new File[] { submoduleFolder1 }, NULL_PROGRESS_MONITOR);
+ assertStatus(status.get(submoduleFolder1), GitSubmoduleStatus.StatusType.UNINITIALIZED,
+ submoduleFolder1);
+ }
+
+ public void testUpdate () throws Exception {
+ prepareUninitializedWorkdir();
+
+ GitClient client = getClient(workDir);
+ Map status = client.getSubmoduleStatus(new File[] { f } , NULL_PROGRESS_MONITOR);
+ assertEquals(0, status.size());
+
+ status = client.initializeSubmodules(new File[] { submoduleFolder1 }, NULL_PROGRESS_MONITOR);
+ assertStatus(status.get(submoduleFolder1), GitSubmoduleStatus.StatusType.UNINITIALIZED,
+ submoduleFolder1);
+ status = client.updateSubmodules(new File[] { submoduleFolder1 }, NULL_PROGRESS_MONITOR);
+ assertStatus(status.get(submoduleFolder1), GitSubmoduleStatus.StatusType.INITIALIZED,
+ submoduleFolder1);
+ }
+
+ private void prepareUninitializedWorkdir () throws Exception {
+ File gmFile = new File(workDir, ".gitmodules");
+ gmFile.createNewFile();
+ write(gmFile, "[submodule \"submodules/submodule1\"]\n" +
+" path = submodules/submodule1\n" +
+" url = " + submoduleRepo1.toURI().toURL().toString() + "\n" +
+"[submodule \"submodules/submodule2\"]\n" +
+" path = submodules/submodule2\n" +
+" url = " + submoduleRepo2.toURI().toURL().toString() + "\n");
+
+ GitClient client = getClient(workDir);
+ client.add(new File[] { gmFile, submoduleFolder1, submoduleFolder2 }, NULL_PROGRESS_MONITOR);
+ client.commit(new File[0], "adding modules", null, null, NULL_PROGRESS_MONITOR);
+ client.push("origin", Arrays.asList("refs/heads/master:refs/heads/master"),
+ Arrays.asList("+refs/heads/master:refs/remotes/origin/master"), NULL_PROGRESS_MONITOR);
+
+ Utils.deleteRecursively(submoduleFolder1);
+ Utils.deleteRecursively(submoduleFolder2);
+ assertFalse(submoduleFolder1.exists());
+ assertFalse(submoduleFolder2.exists());
+ client.reset("master", GitClient.ResetType.HARD, NULL_PROGRESS_MONITOR);
+ assertTrue(submoduleFolder1.exists());
+ assertTrue(submoduleFolder2.exists());
+ }
+
+ private void assertStatus (GitSubmoduleStatus status, GitSubmoduleStatus.StatusType statusKind,
+ File submoduleRoot) {
+ assertEquals(statusKind, status.getStatus());
+ assertEquals(submoduleRoot, status.getSubmoduleFolder());
+ }
+}