Author: brane
Date: Thu Aug 1 00:24:07 2013
New Revision: 1509055
URL: http://svn.apache.org/r1509055
Log:
Implement svn_ra_get_location_segments and svn_ra_stat in JavaHL.
[in subversion/bindings/javahl/src/org/apache/subversion/javahl]
* ISVNRemote.java (ISVNRemote.stat, ISVNRemote.LocationSegment,
ISVNRemote.getLocationSegments): New.
* remote/RemoteSession.java (ISVNRemote.stat, ISVNRemote.LocationSegment): New.
[in subversion/bindings/javahl/native]
* RemoteSession.h
(RemoteSession::stat, RemoteSession::getLocationSegments): New methods.
* RemoteSession.cpp
(RemoteSession::stat, RemoteSession::getLocationSegments): Implement.
(LocationSegmentHandler): New helper for RemoteSession::getLocationSegments.
* org_apache_subversion_javahl_remote_RemoteSession.cpp
(Java_org_apache_subversion_javahl_remote_RemoteSession_stat,
Java_org_apache_subversion_javahl_remote_RemoteSession_getLocationSegments):
New native wrappers.
[in subversion/bindings/javahl/tests/org/apache/subversion/javahl]
* SVNRemoteTests.java
(SVNRemoteTests.testStat, SVNRemoteTests.testGetLocationSegments): New.
Modified:
subversion/trunk/subversion/bindings/javahl/native/RemoteSession.cpp
subversion/trunk/subversion/bindings/javahl/native/RemoteSession.h
subversion/trunk/subversion/bindings/javahl/native/org_apache_subversion_javahl_remote_RemoteSession.cpp
subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/ISVNRemote.java
subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/remote/RemoteSession.java
subversion/trunk/subversion/bindings/javahl/tests/org/apache/subversion/javahl/SVNRemoteTests.java
Modified: subversion/trunk/subversion/bindings/javahl/native/RemoteSession.cpp
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/bindings/javahl/native/RemoteSession.cpp?rev=1509055&r1=1509054&r2=1509055&view=diff
==============================================================================
--- subversion/trunk/subversion/bindings/javahl/native/RemoteSession.cpp
(original)
+++ subversion/trunk/subversion/bindings/javahl/native/RemoteSession.cpp Thu
Aug 1 00:24:07 2013
@@ -924,7 +924,25 @@ RemoteSession::checkPath(jstring jpath,
return EnumMapper::mapNodeKind(kind);
}
-// TODO: stat
+jobject
+RemoteSession::stat(jstring jpath, jlong jrevision)
+{
+ SVN::Pool subPool(pool);
+ Relpath path(jpath, subPool);
+ if (JNIUtil::isExceptionThrown())
+ return NULL;
+ SVN_JNI_ERR(path.error_occurred(), NULL);
+
+ svn_dirent_t* dirent;
+ SVN_JNI_ERR(svn_ra_stat(m_session, path.c_str(),
+ svn_revnum_t(jrevision),
+ &dirent, subPool.getPool()),
+ NULL);
+
+ if (dirent)
+ return CreateJ::DirEntry(path.c_str(), path.c_str(), dirent);
+ return NULL;
+}
namespace {
apr_array_header_t*
@@ -1057,7 +1075,114 @@ RemoteSession::getLocations(jstring jpat
return location_hash_to_map(locations, subPool.getPool());
}
-// TODO: getLocationSegments
+namespace {
+class LocationSegmentHandler
+{
+public:
+ static svn_error_t* callback(svn_location_segment_t* segment,
+ void* baton, apr_pool_t*)
+ {
+ LocationSegmentHandler* const self =
+ static_cast<LocationSegmentHandler*>(baton);
+ SVN_ERR_ASSERT(self->m_jresult_list != NULL);
+ self->add(segment);
+ SVN_ERR(JNIUtil::checkJavaException(SVN_ERR_BASE));
+ return SVN_NO_ERROR;
+ }
+
+ LocationSegmentHandler()
+ : m_jresult_list(NULL)
+ {
+ JNIEnv* env = JNIUtil::getEnv();
+ jclass cls = env->FindClass("java/util/ArrayList");
+ if (JNIUtil::isJavaExceptionThrown())
+ return;
+
+ static jmethodID mid = 0;
+ if (mid == 0)
+ {
+ mid = env->GetMethodID(cls, "<init>", "()V");
+ if (JNIUtil::isJavaExceptionThrown())
+ return;
+ }
+
+ jobject jresult_list = env->NewObject(cls, mid);
+ if (!JNIUtil::isJavaExceptionThrown() && jresult_list)
+ m_jresult_list = jresult_list;
+ }
+
+ jobject get() const { return m_jresult_list; }
+
+private:
+ void add(svn_location_segment_t* segment)
+ {
+ JNIEnv* env = JNIUtil::getEnv();
+ jclass cls = env->FindClass(JAVA_PACKAGE"/ISVNRemote$LocationSegment");
+ if (JNIUtil::isJavaExceptionThrown())
+ return;
+
+ static jmethodID mid = 0;
+ if (mid == 0)
+ {
+ mid = env->GetMethodID(cls, "<init>",
+ "(Ljava/lang/String;JJ)V");
+ if (JNIUtil::isJavaExceptionThrown())
+ return;
+ }
+
+ static jmethodID mid_add = 0;
+ if (mid_add == 0)
+ {
+ jclass list_cls = env->FindClass("java/util/ArrayList");
+ if (JNIUtil::isJavaExceptionThrown())
+ return;
+ mid_add = env->GetMethodID(list_cls, "add",
+ "(Ljava/lang/Object;)Z");
+ if (JNIUtil::isJavaExceptionThrown())
+ return;
+ }
+
+ jstring jpath = JNIUtil::makeJString(segment->path);
+ if (JNIUtil::isJavaExceptionThrown())
+ return;
+
+ env->CallBooleanMethod(m_jresult_list, mid_add,
+ env->NewObject(cls, mid, jpath,
+ jlong(segment->range_start),
+ jlong(segment->range_end)));
+ if (JNIUtil::isJavaExceptionThrown())
+ return;
+ env->DeleteLocalRef(jpath);
+ }
+
+ jobject m_jresult_list;
+};
+} // anonymous namespace
+
+jobject
+RemoteSession::getLocationSegments(jstring jpath, jlong jpeg_revision,
+ jlong jstart_revision, jlong jend_revision)
+{
+ SVN::Pool subPool(pool);
+ Relpath path(jpath, subPool);
+ if (JNIUtil::isExceptionThrown())
+ return NULL;
+ SVN_JNI_ERR(path.error_occurred(), NULL);
+
+ LocationSegmentHandler handler;
+ if (JNIUtil::isExceptionThrown())
+ return NULL;
+
+ SVN_JNI_ERR(svn_ra_get_location_segments(m_session, path.c_str(),
+ svn_revnum_t(jpeg_revision),
+ svn_revnum_t(jstart_revision),
+ svn_revnum_t(jend_revision),
+ handler.callback, &handler,
+ subPool.getPool()),
+ NULL);
+ return handler.get();
+}
+
// TODO: getFileRevisions
// TODO: lock
// TODO: unlock
Modified: subversion/trunk/subversion/bindings/javahl/native/RemoteSession.h
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/bindings/javahl/native/RemoteSession.h?rev=1509055&r1=1509054&r2=1509055&view=diff
==============================================================================
--- subversion/trunk/subversion/bindings/javahl/native/RemoteSession.h
(original)
+++ subversion/trunk/subversion/bindings/javahl/native/RemoteSession.h Thu Aug
1 00:24:07 2013
@@ -92,10 +92,11 @@ class RemoteSession : public SVNBase
jboolean jinclude_merged_revisions,
jobject jrevprops, jobject jlog_callback);
jobject checkPath(jstring jpath, jlong jrevision);
- // TODO: stat
+ jobject stat(jstring jpath, jlong jrevision);
jobject getLocations(jstring jpath, jlong jpeg_revision,
jobject jlocation_revisions);
- // TODO: getLocationSegments
+ jobject getLocationSegments(jstring jpath, jlong jpeg_revision,
+ jlong jstart_revision, jlong jend_revision);
// TODO: getFileRevisions
// TODO: lock
// TODO: unlock
Modified:
subversion/trunk/subversion/bindings/javahl/native/org_apache_subversion_javahl_remote_RemoteSession.cpp
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/bindings/javahl/native/org_apache_subversion_javahl_remote_RemoteSession.cpp?rev=1509055&r1=1509054&r2=1509055&view=diff
==============================================================================
---
subversion/trunk/subversion/bindings/javahl/native/org_apache_subversion_javahl_remote_RemoteSession.cpp
(original)
+++
subversion/trunk/subversion/bindings/javahl/native/org_apache_subversion_javahl_remote_RemoteSession.cpp
Thu Aug 1 00:24:07 2013
@@ -272,21 +272,42 @@ Java_org_apache_subversion_javahl_remote
return ras->checkPath(jpath, jrevision);
}
-// TODO: stat
+JNIEXPORT jobject JNICALL
+Java_org_apache_subversion_javahl_remote_RemoteSession_stat(
+ JNIEnv *env, jobject jthis, jstring jpath, jlong jrevision)
+{
+ JNIEntry(SVNReposAccess, stat);
+ RemoteSession *ras = RemoteSession::getCppObject(jthis);
+ CPPADDR_NULL_PTR(ras, NULL);
+
+ return ras->stat(jpath, jrevision);
+}
JNIEXPORT jobject JNICALL
Java_org_apache_subversion_javahl_remote_RemoteSession_getLocations(
JNIEnv *env, jobject jthis, jstring jpath, jlong jpeg_revision,
jobject jlocation_revisions)
{
- JNIEntry(SVNReposAccess, checkPath);
+ JNIEntry(SVNReposAccess, getLocations);
RemoteSession *ras = RemoteSession::getCppObject(jthis);
CPPADDR_NULL_PTR(ras, NULL);
return ras->getLocations(jpath, jpeg_revision, jlocation_revisions);
}
-// TODO: getLocationSegments
+JNIEXPORT jobject JNICALL
+Java_org_apache_subversion_javahl_remote_RemoteSession_getLocationSegments(
+ JNIEnv *env, jobject jthis, jstring jpath, jlong jpeg_revision,
+ jlong jstart_revision, jlong jend_revision)
+{
+ JNIEntry(SVNReposAccess, getLocationSegments);
+ RemoteSession *ras = RemoteSession::getCppObject(jthis);
+ CPPADDR_NULL_PTR(ras, NULL);
+
+ return ras->getLocationSegments(jpath, jpeg_revision,
+ jstart_revision, jend_revision);
+}
+
// TODO: getFileRevisions
// TODO: lock
// TODO: unlock
Modified:
subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/ISVNRemote.java
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/ISVNRemote.java?rev=1509055&r1=1509054&r2=1509055&view=diff
==============================================================================
---
subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/ISVNRemote.java
(original)
+++
subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/ISVNRemote.java
Thu Aug 1 00:24:07 2013
@@ -27,6 +27,7 @@ import org.apache.subversion.javahl.type
import org.apache.subversion.javahl.callback.*;
import java.util.Date;
+import java.util.List;
import java.util.Map;
import java.util.Set;
import java.io.OutputStream;
@@ -433,14 +434,24 @@ public interface ISVNRemote
throws ClientException;
/**
- * Return the kind of the node in path at revision.
+ * Return the kind of the node in <code>path</code> at
+ * <code>revision</code>.
* @param path A path relative to the sessionn URL
* @throws ClientException
*/
NodeKind checkPath(String path, long revision)
throws ClientException;
- // TODO: stat
+ /**
+ * Return the directory entry object for <code>path</code> at
+ * <code>revision</code>.
+ * @param path A path relative to the sessionn URL
+ * @return A directory entry obeject, or <code>null</code> if
+ * <code>path</code> at <code>revision</code> does not exist.
+ * @throws ClientException
+ */
+ DirEntry stat(String path, long revision)
+ throws ClientException;
/**
* Find the locations of the object identified by
@@ -458,7 +469,69 @@ public interface ISVNRemote
Iterable<Long> locationRevisions)
throws ClientException;
- // TODO: getLocationSegments
+ /**
+ * The object returned from {@link getLocationSegments}.
+ */
+ public static class LocationSegment implements java.io.Serializable
+ {
+ // Update the serialVersionUID when there is a incompatible change
+ // made to this class.
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * Private constructor called by the native implementation.
+ */
+ private LocationSegment(String path,
+ long startRevision,
+ long endRevision)
+ {
+ this.path = path;
+ this.startRevision = startRevision;
+ this.endRevision = endRevision;
+ }
+
+ /**
+ * @return The repository-relative path of the obejct in this
+ * history segment.
+ */
+ public String getPath() { return path; }
+
+ /**
+ * @return The start revision of the history segment.
+ */
+ public long getStartRevision() { return startRevision; }
+
+ /**
+ * @return The end revision of the history segment.
+ */
+ public long getEndRevision() { return endRevision; }
+
+ private String path;
+ private long startRevision;
+ private long endRevision;
+ }
+
+ /**
+ * Return a lost of segments in the location history of <code>path</code>
+ * at <code>pegRevision</code>, working backwards in time from
+ * <code>startRevision</code> to <code>endRevision</code>.
+ *
+ * @param path A session-relative path.
+ * @param pegRevision The peg revision to find <code>path</code> in.
+ * @param startRevision The upper bound of the revision range. Use
+ * {@link org.apache.subversion.javahl.types.Revision#SVN_INVALID_REVNUM}
+ * to indicate HEAD.
+ * @param endRevision The lower bound of the revision range. Use
+ * {@link org.apache.subversion.javahl.types.Revision#SVN_INVALID_REVNUM}
+ * to trace the history of the object to its origin.
+ * @throws ClientException
+ */
+ List<LocationSegment> getLocationSegments(String path,
+ long pegRevision,
+ long startRevision,
+ long endRevision)
+ throws ClientException;
+
// TODO: getFileRevisions
// TODO: lock
// TODO: unlock
Modified:
subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/remote/RemoteSession.java
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/remote/RemoteSession.java?rev=1509055&r1=1509054&r2=1509055&view=diff
==============================================================================
---
subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/remote/RemoteSession.java
(original)
+++
subversion/trunk/subversion/bindings/javahl/src/org/apache/subversion/javahl/remote/RemoteSession.java
Thu Aug 1 00:24:07 2013
@@ -35,6 +35,7 @@ import org.apache.subversion.javahl.Clie
import java.lang.ref.WeakReference;
import java.util.Date;
+import java.util.List;
import java.util.Map;
import java.util.Set;
import java.io.OutputStream;
@@ -197,14 +198,21 @@ public class RemoteSession extends JNIOb
public native NodeKind checkPath(String path, long revision)
throws ClientException;
- // TODO: stat
+ public native DirEntry stat(String path, long revision)
+ throws ClientException;
public native Map<Long, String>
getLocations(String path, long pegRevision,
Iterable<Long> locationRevisions)
throws ClientException;
- // TODO: getLocationSegments
+ public native
+ List<LocationSegment> getLocationSegments(String path,
+ long pegRevision,
+ long startRevision,
+ long endRevision)
+ throws ClientException;
+
// TODO: getFileRevisions
// TODO: lock
// TODO: unlock
Modified:
subversion/trunk/subversion/bindings/javahl/tests/org/apache/subversion/javahl/SVNRemoteTests.java
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/bindings/javahl/tests/org/apache/subversion/javahl/SVNRemoteTests.java?rev=1509055&r1=1509054&r2=1509055&view=diff
==============================================================================
---
subversion/trunk/subversion/bindings/javahl/tests/org/apache/subversion/javahl/SVNRemoteTests.java
(original)
+++
subversion/trunk/subversion/bindings/javahl/tests/org/apache/subversion/javahl/SVNRemoteTests.java
Thu Aug 1 00:24:07 2013
@@ -170,6 +170,20 @@ public class SVNRemoteTests extends SVNT
assertEquals(NodeKind.dir, kind);
}
+ public void testStat() throws Exception
+ {
+ ISVNRemote session = getSession();
+
+ DirEntry dirent = session.stat("iota", 1);
+ assertEquals(NodeKind.file, dirent.getNodeKind());
+
+ dirent = session.stat("iota", 0);
+ assertNull(dirent);
+
+ dirent = session.stat("A", 1);
+ assertEquals(NodeKind.dir, dirent.getNodeKind());
+ }
+
private String getTestRepoUrl()
{
return thisTest.getUrl().toASCIIString();
@@ -1099,4 +1113,19 @@ public class SVNRemoteTests extends SVNT
assertTrue(locs.containsKey(expected));
assertEquals("/A", locs.get(expected));
}
+
+ public void testGetLocationSegments() throws Exception
+ {
+ ISVNRemote session = getSession();
+
+ List<ISVNRemote.LocationSegment> result =
+ session.getLocationSegments("A", 1,
+ Revision.SVN_INVALID_REVNUM,
+ Revision.SVN_INVALID_REVNUM);
+ assertEquals(1, result.size());
+ ISVNRemote.LocationSegment seg = result.get(0);
+ assertEquals("A", seg.getPath());
+ assertEquals(1, seg.getStartRevision());
+ assertEquals(1, seg.getEndRevision());
+ }
}