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
4 changes: 3 additions & 1 deletion java/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ NATIVE_JAVA_CLASSES = org.rocksdb.AbstractCompactionFilter\
org.rocksdb.LRUCache\
org.rocksdb.MergeOperator\
org.rocksdb.Options\
org.rocksdb.OptionsUtil\
org.rocksdb.PlainTableConfig\
org.rocksdb.RateLimiter\
org.rocksdb.ReadOptions\
Expand Down Expand Up @@ -96,12 +97,13 @@ JAVA_TESTS = org.rocksdb.BackupableDBOptionsTest\
org.rocksdb.InfoLogLevelTest\
org.rocksdb.KeyMayExistTest\
org.rocksdb.LoggerTest\
org.rocksdb.LRUCacheTest\
org.rocksdb.LRUCacheTest\
org.rocksdb.MemTableTest\
org.rocksdb.MergeTest\
org.rocksdb.MixedOptionsTest\
org.rocksdb.MutableColumnFamilyOptionsTest\
org.rocksdb.NativeLibraryLoaderTest\
org.rocksdb.OptionsUtilTest\
org.rocksdb.OptionsTest\
org.rocksdb.PlainTableConfigTest\
org.rocksdb.RateLimiterTest\
Expand Down
114 changes: 114 additions & 0 deletions java/rocksjni/options_util.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,114 @@
// Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
// This source code is licensed under both the GPLv2 (found in the
// COPYING file in the root directory) and Apache 2.0 License
// (found in the LICENSE.Apache file in the root directory).
//
// This file implements the "bridge" between Java and C++ and enables
// calling C++ rocksdb::OptionsUtil methods from Java side.

#include <jni.h>

#include "include/org_rocksdb_OptionsUtil.h"

#include "rocksdb/db.h"
#include "rocksdb/env.h"
#include "rocksdb/utilities/options_util.h"
#include "rocksjni/portal.h"

void build_column_family_descriptor_list(
JNIEnv* env, jobject jcfds,
std::vector<rocksdb::ColumnFamilyDescriptor>& cf_descs) {
jmethodID add_mid = rocksdb::ListJni::getListAddMethodId(env);
if (add_mid == nullptr) {
// exception occurred accessing method
return;
}

// Column family descriptor
for (rocksdb::ColumnFamilyDescriptor& cfd : cf_descs) {
// Construct a ColumnFamilyDescriptor java object
jobject jcfd = rocksdb::ColumnFamilyDescriptorJni::construct(env, &cfd);
if (env->ExceptionCheck()) {
// exception occurred constructing object
if (jcfd != nullptr) {
env->DeleteLocalRef(jcfd);
}
return;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do you want to clear the objects already put in cf_descs?

}

// Add the object to java list.
jboolean rs = env->CallBooleanMethod(jcfds, add_mid, jcfd);
if (env->ExceptionCheck() || rs == JNI_FALSE) {
// exception occurred calling method, or could not add
if (jcfd != nullptr) {
env->DeleteLocalRef(jcfd);
}
return;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same here.

}
}
}

/*
* Class: org_rocksdb_OptionsUtil
* Method: loadLatestOptions
* Signature: (Ljava/lang/String;JLjava/util/List;Z)V
*/
void Java_org_rocksdb_OptionsUtil_loadLatestOptions(
JNIEnv* env, jclass jcls, jstring jdbpath, jlong jenv_handle,
jlong jdb_opts_handle, jobject jcfds, jboolean ignore_unknown_options) {
const char* db_path = env->GetStringUTFChars(jdbpath, nullptr);
std::vector<rocksdb::ColumnFamilyDescriptor> cf_descs;
rocksdb::Status s = rocksdb::LoadLatestOptions(
db_path, reinterpret_cast<rocksdb::Env*>(jenv_handle),
reinterpret_cast<rocksdb::DBOptions*>(jdb_opts_handle), &cf_descs,
ignore_unknown_options);
env->ReleaseStringUTFChars(jdbpath, db_path);

if (!s.ok()) {
rocksdb::RocksDBExceptionJni::ThrowNew(env, s);
}

build_column_family_descriptor_list(env, jcfds, cf_descs);
}

/*
* Class: org_rocksdb_OptionsUtil
* Method: loadOptionsFromFile
* Signature: (Ljava/lang/String;JJLjava/util/List;Z)V
*/
void Java_org_rocksdb_OptionsUtil_loadOptionsFromFile(
JNIEnv* env, jclass jcls, jstring jopts_file_name, jlong jenv_handle,
jlong jdb_opts_handle, jobject jcfds, jboolean ignore_unknown_options) {
const char* opts_file_name = env->GetStringUTFChars(jopts_file_name, nullptr);
std::vector<rocksdb::ColumnFamilyDescriptor> cf_descs;
rocksdb::Status s = rocksdb::LoadOptionsFromFile(
opts_file_name, reinterpret_cast<rocksdb::Env*>(jenv_handle),
reinterpret_cast<rocksdb::DBOptions*>(jdb_opts_handle), &cf_descs,
ignore_unknown_options);
env->ReleaseStringUTFChars(jopts_file_name, opts_file_name);

if (!s.ok()) {
rocksdb::RocksDBExceptionJni::ThrowNew(env, s);
}

build_column_family_descriptor_list(env, jcfds, cf_descs);
}

/*
* Class: org_rocksdb_OptionsUtil
* Method: getLatestOptionsFileName
* Signature: (Ljava/lang/String;J)Ljava/lang/String;
*/
jstring Java_org_rocksdb_OptionsUtil_getLatestOptionsFileName(
JNIEnv* env, jclass jcls, jstring jdbpath, jlong jenv_handle) {
const char* db_path = env->GetStringUTFChars(jdbpath, nullptr);
std::string options_file_name;
if (db_path != nullptr) {
rocksdb::GetLatestOptionsFileName(
db_path, reinterpret_cast<rocksdb::Env*>(jenv_handle),
&options_file_name);
}
env->ReleaseStringUTFChars(jdbpath, db_path);

return env->NewStringUTF(options_file_name.c_str());
}
168 changes: 117 additions & 51 deletions java/rocksjni/portal.h
Original file line number Diff line number Diff line change
Expand Up @@ -584,10 +584,13 @@ class DBOptionsJni : public RocksDBNativeClass<
}
};

class ColumnFamilyDescriptorJni : public JavaClass {
// The portal class for org.rocksdb.ColumnFamilyOptions
class ColumnFamilyOptionsJni
: public RocksDBNativeClass<rocksdb::ColumnFamilyOptions*,
ColumnFamilyOptionsJni> {
public:
/**
* Get the Java Class org.rocksdb.ColumnFamilyDescriptor
* Get the Java Class org.rocksdb.ColumnFamilyOptions
*
* @param env A pointer to the Java environment
*
Expand All @@ -596,69 +599,40 @@ class ColumnFamilyDescriptorJni : public JavaClass {
* OutOfMemoryError or ExceptionInInitializerError exceptions is thrown
*/
static jclass getJClass(JNIEnv* env) {
return JavaClass::getJClass(env, "org/rocksdb/ColumnFamilyDescriptor");
return RocksDBNativeClass::getJClass(env,
"org/rocksdb/ColumnFamilyOptions");
}

/**
* Get the Java Method: ColumnFamilyDescriptor#columnFamilyName
* Create a new Java org.rocksdb.ColumnFamilyOptions object with the same
* properties as the provided C++ rocksdb::ColumnFamilyOptions object
*
* @param env A pointer to the Java environment
* @param cfoptions A pointer to rocksdb::ColumnFamilyOptions object
*
* @return The Java Method ID or nullptr if the class or method id could not
* be retieved
* @return A reference to a Java org.rocksdb.ColumnFamilyOptions object, or
* nullptr if an an exception occurs
*/
static jmethodID getColumnFamilyNameMethod(JNIEnv* env) {
static jobject construct(JNIEnv* env, const ColumnFamilyOptions* cfoptions) {
auto* cfo = new rocksdb::ColumnFamilyOptions(*cfoptions);
jclass jclazz = getJClass(env);
if(jclazz == nullptr) {
// exception occurred accessing class
return nullptr;
}

static jmethodID mid =
env->GetMethodID(jclazz, "columnFamilyName", "()[B");
assert(mid != nullptr);
return mid;
}

/**
* Get the Java Method: ColumnFamilyDescriptor#columnFamilyOptions
*
* @param env A pointer to the Java environment
*
* @return The Java Method ID or nullptr if the class or method id could not
* be retieved
*/
static jmethodID getColumnFamilyOptionsMethod(JNIEnv* env) {
jclass jclazz = getJClass(env);
if(jclazz == nullptr) {
// exception occurred accessing class
jmethodID mid = env->GetMethodID(jclazz, "<init>", "(J)V");
if (mid == nullptr) {
// exception thrown: NoSuchMethodException or OutOfMemoryError
return nullptr;
}

static jmethodID mid =
env->GetMethodID(jclazz, "columnFamilyOptions",
"()Lorg/rocksdb/ColumnFamilyOptions;");
assert(mid != nullptr);
return mid;
}
};
jobject jcfd = env->NewObject(jclazz, mid, reinterpret_cast<long>(cfo));
if (env->ExceptionCheck()) {
return nullptr;
}

// The portal class for org.rocksdb.ColumnFamilyOptions
class ColumnFamilyOptionsJni : public RocksDBNativeClass<
rocksdb::ColumnFamilyOptions*, ColumnFamilyOptionsJni> {
public:
/**
* Get the Java Class org.rocksdb.ColumnFamilyOptions
*
* @param env A pointer to the Java environment
*
* @return The Java Class or nullptr if one of the
* ClassFormatError, ClassCircularityError, NoClassDefFoundError,
* OutOfMemoryError or ExceptionInInitializerError exceptions is thrown
*/
static jclass getJClass(JNIEnv* env) {
return RocksDBNativeClass::getJClass(env,
"org/rocksdb/ColumnFamilyOptions");
return jcfd;
}
};

Expand Down Expand Up @@ -1202,7 +1176,7 @@ class SliceJni : public NativeRocksMutableObject<
// exception occurred accessing method
return nullptr;
}

jobject jslice = env->NewObject(jclazz, mid);
if(env->ExceptionCheck()) {
return nullptr;
Expand Down Expand Up @@ -1719,7 +1693,7 @@ class WBWIRocksIteratorJni : public JavaClass {
/**
* Gets the value of the WBWIRocksIterator#entry
*
* @param env A pointer to the Java environment
* @param env A pointer to the Java environment
* @param jwbwi_rocks_iterator A reference to a WBWIIterator
*
* @return A reference to a Java WBWIRocksIterator.WriteEntry object, or
Expand Down Expand Up @@ -2479,7 +2453,7 @@ class TickerTypeJni {
return 0x5C;
case rocksdb::Tickers::TICKER_ENUM_MAX:
return 0x5D;

default:
// undefined/default
return 0x0;
Expand Down Expand Up @@ -3337,5 +3311,97 @@ class JniUtil {
}
};

class ColumnFamilyDescriptorJni : public JavaClass {
public:
/**
* Get the Java Class org.rocksdb.ColumnFamilyDescriptor
*
* @param env A pointer to the Java environment
*
* @return The Java Class or nullptr if one of the
* ClassFormatError, ClassCircularityError, NoClassDefFoundError,
* OutOfMemoryError or ExceptionInInitializerError exceptions is thrown
*/
static jclass getJClass(JNIEnv* env) {
return JavaClass::getJClass(env, "org/rocksdb/ColumnFamilyDescriptor");
}

/**
* Create a new Java org.rocksdb.ColumnFamilyDescriptor object with the same
* properties as the provided C++ rocksdb::ColumnFamilyDescriptor object
*
* @param env A pointer to the Java environment
* @param cfd A pointer to rocksdb::ColumnFamilyDescriptor object
*
* @return A reference to a Java org.rocksdb.ColumnFamilyDescriptor object, or
* nullptr if an an exception occurs
*/
static jobject construct(JNIEnv* env, ColumnFamilyDescriptor* cfd) {
jbyteArray cfname = JniUtil::copyBytes(env, cfd->name);
jobject cfopts = ColumnFamilyOptionsJni::construct(env, &(cfd->options));

jclass jclazz = getJClass(env);
if (jclazz == nullptr) {
// exception occurred accessing class
return nullptr;
}

jmethodID mid = env->GetMethodID(jclazz, "<init>",
"([BLorg/rocksdb/ColumnFamilyOptions;)V");
if (mid == nullptr) {
// exception thrown: NoSuchMethodException or OutOfMemoryError
return nullptr;
}

jobject jcfd = env->NewObject(jclazz, mid, cfname, cfopts);
if (env->ExceptionCheck()) {
return nullptr;
}

return jcfd;
}

/**
* Get the Java Method: ColumnFamilyDescriptor#columnFamilyName
*
* @param env A pointer to the Java environment
*
* @return The Java Method ID or nullptr if the class or method id could not
* be retieved
*/
static jmethodID getColumnFamilyNameMethod(JNIEnv* env) {
jclass jclazz = getJClass(env);
if (jclazz == nullptr) {
// exception occurred accessing class
return nullptr;
}

static jmethodID mid = env->GetMethodID(jclazz, "columnFamilyName", "()[B");
assert(mid != nullptr);
return mid;
}

/**
* Get the Java Method: ColumnFamilyDescriptor#columnFamilyOptions
*
* @param env A pointer to the Java environment
*
* @return The Java Method ID or nullptr if the class or method id could not
* be retieved
*/
static jmethodID getColumnFamilyOptionsMethod(JNIEnv* env) {
jclass jclazz = getJClass(env);
if (jclazz == nullptr) {
// exception occurred accessing class
return nullptr;
}

static jmethodID mid = env->GetMethodID(
jclazz, "columnFamilyOptions", "()Lorg/rocksdb/ColumnFamilyOptions;");
assert(mid != nullptr);
return mid;
}
};

} // namespace rocksdb
#endif // JAVA_ROCKSJNI_PORTAL_H_
5 changes: 3 additions & 2 deletions java/src/main/java/org/rocksdb/ColumnFamilyOptions.java
Original file line number Diff line number Diff line change
Expand Up @@ -736,12 +736,13 @@ public boolean forceConsistencyChecks() {
}

/**
* <p>Private constructor to be used by
* <p>Constructor to be used by
* {@link #getColumnFamilyOptionsFromProps(java.util.Properties)}</p>
* and also called via JNI.
*
* @param handle native handle to ColumnFamilyOptions instance.
*/
private ColumnFamilyOptions(final long handle) {
public ColumnFamilyOptions(final long handle) {
super(handle);
}

Expand Down
Loading