| // Licensed to the Apache Software Foundation (ASF) under one |
| // or more contributor license agreements. See the NOTICE file |
| // distributed with this work for additional information |
| // regarding copyright ownership. The ASF licenses this file |
| // to you under the Apache License, Version 2.0 (the |
| // "License"); you may not use this file except in compliance |
| // with the License. You may obtain a copy of the License at |
| // |
| // http://www.apache.org/licenses/LICENSE-2.0 |
| // |
| // Unless required by applicable law or agreed to in writing, |
| // software distributed under the License is distributed on an |
| // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| // KIND, either express or implied. See the License for the |
| // specific language governing permissions and limitations |
| // under the License. |
| #ifndef KUDU_COMMON_PARTIAL_ROW_H |
| #define KUDU_COMMON_PARTIAL_ROW_H |
| |
| #include <stdint.h> |
| #include <string> |
| #include <vector> |
| |
| #ifdef KUDU_HEADERS_NO_STUBS |
| #include "kudu/gutil/macros.h" |
| #include "kudu/gutil/port.h" |
| #include <gtest/gtest_prod.h> |
| #else |
| // This is a poor module interdependency, but the stubs are header-only and |
| // it's only for exported header builds, so we'll make an exception. |
| #include "kudu/client/stubs.h" |
| #endif |
| |
| #include "kudu/util/kudu_export.h" |
| #include "kudu/util/slice.h" |
| |
| namespace kudu { |
| class ColumnSchema; |
| namespace client { |
| class KuduWriteOperation; |
| template<typename KeyTypeWrapper> struct SliceKeysTestSetup; |
| template<typename KeyTypeWrapper> struct IntKeysTestSetup; |
| } // namespace client |
| |
| class Schema; |
| class PartialRowPB; |
| |
| // A row which may only contain values for a subset of the columns. |
| // This type contains a normal contiguous row, plus a bitfield indicating |
| // which columns have been set. Additionally, this type may optionally own |
| // copies of indirect data for variable length columns. |
| class KUDU_EXPORT KuduPartialRow { |
| public: |
| // The given Schema object must remain valid for the lifetime of this |
| // row. |
| explicit KuduPartialRow(const Schema* schema); |
| virtual ~KuduPartialRow(); |
| |
| KuduPartialRow(const KuduPartialRow& other); |
| |
| KuduPartialRow& operator=(KuduPartialRow other); |
| |
| //------------------------------------------------------------ |
| // Setters |
| //------------------------------------------------------------ |
| |
| Status SetBool(const Slice& col_name, bool val) WARN_UNUSED_RESULT; |
| |
| Status SetInt8(const Slice& col_name, int8_t val) WARN_UNUSED_RESULT; |
| Status SetInt16(const Slice& col_name, int16_t val) WARN_UNUSED_RESULT; |
| Status SetInt32(const Slice& col_name, int32_t val) WARN_UNUSED_RESULT; |
| Status SetInt64(const Slice& col_name, int64_t val) WARN_UNUSED_RESULT; |
| Status SetTimestamp(const Slice& col_name, int64_t micros_since_utc_epoch) WARN_UNUSED_RESULT; |
| |
| Status SetFloat(const Slice& col_name, float val) WARN_UNUSED_RESULT; |
| Status SetDouble(const Slice& col_name, double val) WARN_UNUSED_RESULT; |
| |
| // Same as above setters, but with numeric column indexes. |
| // These are faster since they avoid a hashmap lookup, so should |
| // be preferred in performance-sensitive code (eg bulk loaders). |
| Status SetBool(int col_idx, bool val) WARN_UNUSED_RESULT; |
| |
| Status SetInt8(int col_idx, int8_t val) WARN_UNUSED_RESULT; |
| Status SetInt16(int col_idx, int16_t val) WARN_UNUSED_RESULT; |
| Status SetInt32(int col_idx, int32_t val) WARN_UNUSED_RESULT; |
| Status SetInt64(int col_idx, int64_t val) WARN_UNUSED_RESULT; |
| Status SetTimestamp(int col_idx, int64_t micros_since_utc_epoch) WARN_UNUSED_RESULT; |
| |
| Status SetFloat(int col_idx, float val) WARN_UNUSED_RESULT; |
| Status SetDouble(int col_idx, double val) WARN_UNUSED_RESULT; |
| |
| // Sets the string/binary value but does not copy the value. The slice |
| // must remain valid until the call to AppendToPB(). |
| Status SetString(const Slice& col_name, const Slice& val) WARN_UNUSED_RESULT; |
| Status SetString(int col_idx, const Slice& val) WARN_UNUSED_RESULT; |
| Status SetBinary(const Slice& col_name, const Slice& val) WARN_UNUSED_RESULT; |
| Status SetBinary(int col_idx, const Slice& val) WARN_UNUSED_RESULT; |
| |
| // Copies 'val' immediately. |
| Status SetStringCopy(const Slice& col_name, const Slice& val) WARN_UNUSED_RESULT; |
| Status SetStringCopy(int col_idx, const Slice& val) WARN_UNUSED_RESULT; |
| Status SetBinaryCopy(const Slice& col_name, const Slice& val) WARN_UNUSED_RESULT; |
| Status SetBinaryCopy(int col_idx, const Slice& val) WARN_UNUSED_RESULT; |
| |
| // Set the given column to NULL. This will only succeed on nullable |
| // columns. Use Unset(...) to restore a column to its default. |
| Status SetNull(const Slice& col_name) WARN_UNUSED_RESULT; |
| Status SetNull(int col_idx) WARN_UNUSED_RESULT; |
| |
| // Unsets the given column. Note that this is different from setting |
| // it to NULL. |
| Status Unset(const Slice& col_name) WARN_UNUSED_RESULT; |
| Status Unset(int col_idx) WARN_UNUSED_RESULT; |
| |
| //------------------------------------------------------------ |
| // Getters |
| //------------------------------------------------------------ |
| // These getters return a bad Status if the type does not match, |
| // the value is unset, or the value is NULL. Otherwise they return |
| // the current set value in *val. |
| |
| // Return true if the given column has been specified. |
| bool IsColumnSet(const Slice& col_name) const; |
| bool IsColumnSet(int col_idx) const; |
| |
| bool IsNull(const Slice& col_name) const; |
| bool IsNull(int col_idx) const; |
| |
| Status GetBool(const Slice& col_name, bool* val) const WARN_UNUSED_RESULT; |
| |
| Status GetInt8(const Slice& col_name, int8_t* val) const WARN_UNUSED_RESULT; |
| Status GetInt16(const Slice& col_name, int16_t* val) const WARN_UNUSED_RESULT; |
| Status GetInt32(const Slice& col_name, int32_t* val) const WARN_UNUSED_RESULT; |
| Status GetInt64(const Slice& col_name, int64_t* val) const WARN_UNUSED_RESULT; |
| Status GetTimestamp(const Slice& col_name, |
| int64_t* micros_since_utc_epoch) const WARN_UNUSED_RESULT; |
| |
| Status GetFloat(const Slice& col_name, float* val) const WARN_UNUSED_RESULT; |
| Status GetDouble(const Slice& col_name, double* val) const WARN_UNUSED_RESULT; |
| |
| // Same as above getters, but with numeric column indexes. |
| // These are faster since they avoid a hashmap lookup, so should |
| // be preferred in performance-sensitive code. |
| Status GetBool(int col_idx, bool* val) const WARN_UNUSED_RESULT; |
| |
| Status GetInt8(int col_idx, int8_t* val) const WARN_UNUSED_RESULT; |
| Status GetInt16(int col_idx, int16_t* val) const WARN_UNUSED_RESULT; |
| Status GetInt32(int col_idx, int32_t* val) const WARN_UNUSED_RESULT; |
| Status GetInt64(int col_idx, int64_t* val) const WARN_UNUSED_RESULT; |
| Status GetTimestamp(int col_idx, int64_t* micros_since_utc_epoch) const WARN_UNUSED_RESULT; |
| |
| Status GetFloat(int col_idx, float* val) const WARN_UNUSED_RESULT; |
| Status GetDouble(int col_idx, double* val) const WARN_UNUSED_RESULT; |
| |
| // Gets the string/binary value but does not copy the value. Callers should |
| // copy the resulting Slice if necessary. |
| Status GetString(const Slice& col_name, Slice* val) const WARN_UNUSED_RESULT; |
| Status GetString(int col_idx, Slice* val) const WARN_UNUSED_RESULT; |
| Status GetBinary(const Slice& col_name, Slice* val) const WARN_UNUSED_RESULT; |
| Status GetBinary(int col_idx, Slice* val) const WARN_UNUSED_RESULT; |
| |
| //------------------------------------------------------------ |
| // Key-encoding related functions |
| //------------------------------------------------------------ |
| |
| // Encode a row key suitable for use as a tablet split key, an encoded |
| // key range, etc. |
| // |
| // Requires that all of the key columns must be set; otherwise, returns |
| // InvalidArgument. |
| Status EncodeRowKey(std::string* encoded_key) const; |
| |
| // Convenience method which is equivalent to the above, but triggers a |
| // FATAL error on failure. |
| std::string ToEncodedRowKeyOrDie() const; |
| |
| //------------------------------------------------------------ |
| // Utility code |
| //------------------------------------------------------------ |
| |
| // Return true if all of the key columns have been specified |
| // for this mutation. |
| bool IsKeySet() const; |
| |
| // Return true if all columns have been specified. |
| bool AllColumnsSet() const; |
| |
| std::string ToString() const; |
| |
| const Schema* schema() const { return schema_; } |
| |
| private: |
| friend class client::KuduWriteOperation; // for row_data_. |
| friend class KeyUtilTest; |
| friend class PartitionSchema; |
| friend class RowOperationsPBDecoder; |
| friend class RowOperationsPBEncoder; |
| friend class TestScanSpec; |
| template<typename KeyTypeWrapper> friend struct client::SliceKeysTestSetup; |
| template<typename KeyTypeWrapper> friend struct client::IntKeysTestSetup; |
| FRIEND_TEST(TestPartitionPruner, TestPrimaryKeyRangePruning); |
| FRIEND_TEST(TestPartitionPruner, TestPartialPrimaryKeyRangePruning); |
| |
| template<typename T> |
| Status Set(const Slice& col_name, const typename T::cpp_type& val, |
| bool owned = false); |
| |
| template<typename T> |
| Status Set(int col_idx, const typename T::cpp_type& val, |
| bool owned = false); |
| |
| // Runtime version of the generic setter. |
| Status Set(int32_t column_idx, const uint8_t* val); |
| |
| template<typename T> |
| Status Get(const Slice& col_name, typename T::cpp_type* val) const; |
| |
| template<typename T> |
| Status Get(int col_idx, typename T::cpp_type* val) const; |
| |
| template<typename T> |
| Status SetSliceCopy(const Slice& col_name, const Slice& val); |
| |
| template<typename T> |
| Status SetSliceCopy(int col_idx, const Slice& val); |
| |
| // If the given column is a variable length column whose memory is owned by this instance, |
| // deallocates the value. |
| // NOTE: Does not mutate the isset bitmap. |
| // REQUIRES: col_idx must be a variable length column. |
| void DeallocateStringIfSet(int col_idx, const ColumnSchema& col); |
| |
| // Deallocate any string/binary values whose memory is managed by this object. |
| void DeallocateOwnedStrings(); |
| |
| const Schema* schema_; |
| |
| // 1-bit set for any field which has been explicitly set. This is distinct |
| // from NULL -- an "unset" field will take the server-side default on insert, |
| // whereas a field explicitly set to NULL will override the default. |
| uint8_t* isset_bitmap_; |
| |
| // 1-bit set for any variable length columns whose memory is managed by this instance. |
| // These strings need to be deallocated whenever the value is reset, |
| // or when the instance is destructed. |
| uint8_t* owned_strings_bitmap_; |
| |
| // The normal "contiguous row" format row data. Any column whose data is unset |
| // or NULL can have undefined bytes. |
| uint8_t* row_data_; |
| }; |
| |
| } // namespace kudu |
| #endif /* KUDU_COMMON_PARTIAL_ROW_H */ |