ckb_rocksdb/ops/
get.rs

1// Copyright 2019 Tyler Neely
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14//
15
16use crate::ffi;
17use libc::{c_char, size_t};
18
19use crate::{handle::Handle, ColumnFamily, DBVector, Error, ReadOptions};
20
21pub trait Get<R> {
22    fn get_full<K: AsRef<[u8]>>(
23        &self,
24        key: K,
25        readopts: Option<&R>,
26    ) -> Result<Option<DBVector>, Error>;
27
28    /// Return the bytes associated with a key value
29    fn get<K: AsRef<[u8]>>(&self, key: K) -> Result<Option<DBVector>, Error> {
30        self.get_full(key, None)
31    }
32
33    fn get_opt<K: AsRef<[u8]>>(&self, key: K, readopts: &R) -> Result<Option<DBVector>, Error> {
34        self.get_full(key, Some(readopts))
35    }
36}
37
38pub trait GetCF<R> {
39    fn get_cf_full<K: AsRef<[u8]>>(
40        &self,
41        cf: Option<&ColumnFamily>,
42        key: K,
43        readopts: Option<&R>,
44    ) -> Result<Option<DBVector>, Error>;
45
46    fn get_cf<K: AsRef<[u8]>>(&self, cf: &ColumnFamily, key: K) -> Result<Option<DBVector>, Error> {
47        self.get_cf_full(Some(cf), key, None)
48    }
49
50    fn get_cf_opt<K: AsRef<[u8]>>(
51        &self,
52        cf: &ColumnFamily,
53        key: K,
54        readopts: &R,
55    ) -> Result<Option<DBVector>, Error> {
56        self.get_cf_full(Some(cf), key, Some(readopts))
57    }
58}
59
60impl<T, R> Get<R> for T
61where
62    T: GetCF<R>,
63{
64    fn get_full<K: AsRef<[u8]>>(
65        &self,
66        key: K,
67        readopts: Option<&R>,
68    ) -> Result<Option<DBVector>, Error> {
69        self.get_cf_full(None, key, readopts)
70    }
71}
72
73impl<T> GetCF<ReadOptions> for T
74where
75    T: Handle<ffi::rocksdb_t> + super::Read,
76{
77    fn get_cf_full<K: AsRef<[u8]>>(
78        &self,
79        cf: Option<&ColumnFamily>,
80        key: K,
81        readopts: Option<&ReadOptions>,
82    ) -> Result<Option<DBVector>, Error> {
83        let mut default_readopts = None;
84
85        let ro_handle = ReadOptions::input_or_default(readopts, &mut default_readopts)?;
86
87        let key = key.as_ref();
88        let key_ptr = key.as_ptr() as *const c_char;
89        let key_len = key.len() as size_t;
90
91        unsafe {
92            let mut val_len: size_t = 0;
93
94            let val = match cf {
95                Some(cf) => ffi_try!(ffi::rocksdb_get_cf(
96                    self.handle(),
97                    ro_handle,
98                    cf.handle(),
99                    key_ptr,
100                    key_len,
101                    &mut val_len,
102                )),
103                None => ffi_try!(ffi::rocksdb_get(
104                    self.handle(),
105                    ro_handle,
106                    key_ptr,
107                    key_len,
108                    &mut val_len,
109                )),
110            } as *mut u8;
111
112            if val.is_null() {
113                Ok(None)
114            } else {
115                Ok(Some(DBVector::from_c(val, val_len)))
116            }
117        }
118    }
119}