Commit 542eb4bb authored by siddontang's avatar siddontang

*: support get property

parent 5b805d74
......@@ -5,3 +5,4 @@ authors = ["Jay Lee <busyjaylee@gmail.com>"]
[dependencies]
libc = "0.1.8"
tempdir = "0.3"
\ No newline at end of file
......@@ -14,6 +14,8 @@
//
extern crate libc;
#[cfg(test)]
extern crate tempdir;
use libc::{c_char, c_int, c_void, size_t, uint64_t};
use std::ffi::CStr;
......@@ -147,7 +149,8 @@ extern "C" {
pub fn rocksdb_options_set_bytes_per_sync(options: DBOptions, bytes: u64);
pub fn rocksdb_options_set_disable_data_sync(options: DBOptions,
v: c_int);
pub fn rocksdb_options_set_allow_os_buffer(options: DBOptions, is_allow: bool);
pub fn rocksdb_options_set_allow_os_buffer(options: DBOptions,
is_allow: bool);
pub fn rocksdb_options_optimize_for_point_lookup(options: DBOptions,
block_cache_size_mb: u64);
pub fn rocksdb_options_set_table_cache_numshardbits(options: DBOptions,
......@@ -168,7 +171,8 @@ extern "C" {
bytes: u64);
pub fn rocksdb_options_set_target_file_size_multiplier(options: DBOptions,
mul: c_int);
pub fn rocksdb_options_set_max_bytes_for_level_base(options: DBOptions, bytes: u64);
pub fn rocksdb_options_set_max_bytes_for_level_base(options: DBOptions,
bytes: u64);
pub fn rocksdb_options_set_max_bytes_for_level_multiplier(options: DBOptions, mul: c_int);
pub fn rocksdb_options_set_max_log_file_size(options: DBOptions,
bytes: u64);
......@@ -443,12 +447,20 @@ extern "C" {
range_limit_key: *const *const u8,
range_limit_key_len: *const size_t,
sizes: *mut uint64_t);
pub fn rocksdb_property_value(db: DBInstance,
propname: *const c_char)
-> *mut c_char;
pub fn rocksdb_property_value_cf(db: DBInstance,
cf: DBCFHandle,
propname: *const c_char)
-> *mut c_char;
}
#[cfg(test)]
mod test {
use super::*;
use std::ffi::CString;
use std::ffi::{CStr, CString};
use libc::{self, c_void};
use tempdir::TempDir;
#[test]
......@@ -462,9 +474,9 @@ mod test {
rocksdb_options_set_create_if_missing(opts, true);
let rustpath = TempDir::new("_rust_rocksdb_internaltest")
.expect("");
.expect("");
let cpath = CString::new(rustpath.path().to_str().unwrap())
.unwrap();
.unwrap();
let cpath_ptr = cpath.as_ptr();
let mut err = 0 as *const i8;
......@@ -517,6 +529,21 @@ mod test {
assert_eq!(sizes.len(), 1);
assert!(sizes[0] > 0);
let propname = CString::new("rocksdb.total-sst-files-size")
.unwrap();
let value = rocksdb_property_value(db, propname.as_ptr());
assert!(!value.is_null());
let sst_size =
CStr::from_ptr(value).to_str().unwrap().parse::<u64>().unwrap();
assert!(sst_size > 0);
libc::free(value as *mut c_void);
let propname = CString::new("fake_key").unwrap();
let value = rocksdb_property_value(db, propname.as_ptr());
assert!(value.is_null());
libc::free(value as *mut c_void);
rocksdb_close(db);
rocksdb_destroy_db(opts, cpath_ptr, &mut err);
assert!(err.is_null());
......
......@@ -13,7 +13,7 @@
// limitations under the License.
//
use std::collections::BTreeMap;
use std::ffi::CString;
use std::ffi::{CStr, CString};
use std::fs;
use std::ops::Deref;
use std::path::Path;
......@@ -814,6 +814,65 @@ impl DB {
}
sizes
}
fn get_property_value(&self, name: &str) -> Option<String> {
self.get_property_value_cf_opt(None, name)
}
fn get_property_value_cf(&self,
cf: DBCFHandle,
name: &str)
-> Option<String> {
self.get_property_value_cf_opt(Some(cf), name)
}
fn get_property_int(&self, name: &str) -> Option<u64> {
self.get_property_int_cf_opt(None, name)
}
fn get_property_int_cf(&self, cf: DBCFHandle, name: &str) -> Option<u64> {
self.get_property_int_cf_opt(Some(cf), name)
}
fn get_property_value_cf_opt(&self,
cf: Option<DBCFHandle>,
name: &str)
-> Option<String> {
unsafe {
let prop_name = CString::new(name).unwrap();
let value = match cf {
None => {
rocksdb_ffi::rocksdb_property_value(self.inner,
prop_name.as_ptr())
}
Some(cf) => {
rocksdb_ffi::rocksdb_property_value_cf(self.inner,
cf,
prop_name.as_ptr())
}
};
if value.is_null() {
return None;
}
// Must valid UTF-8 format.
let s = CStr::from_ptr(value).to_str().unwrap().to_owned();
libc::free(value as *mut c_void);
Some(s)
}
}
fn get_property_int_cf_opt(&self,
cf: Option<DBCFHandle>,
name: &str)
-> Option<u64> {
// Rocksdb guarantee that the return property int
// value is u64 if exists.
self.get_property_value_cf_opt(cf, name)
.map(|value| value.as_str().parse::<u64>().unwrap())
}
}
impl Writable for DB {
......@@ -1121,6 +1180,21 @@ mod test {
}
assert_eq!(sizes[4], 0);
}
#[test]
fn property_test() {
let path = TempDir::new("_rust_rocksdb_iteratortest").expect("");
let db = DB::open_default(path.path().to_str().unwrap()).unwrap();
db.put(b"a1", b"v1").unwrap();
db.flush(true).unwrap();
let prop_name = "rocksdb.total-sst-files-size";
let st1 = db.get_property_int(prop_name).unwrap();
assert!(st1 > 0);
db.put(b"a2", b"v2").unwrap();
db.flush(true).unwrap();
let st2 = db.get_property_int(prop_name).unwrap();
assert!(st2 > st1);
}
}
#[test]
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment