1dfe32fa1Soh_ci/* 2dfe32fa1Soh_ci * Copyright (c) 2023 Huawei Device Co., Ltd. 3dfe32fa1Soh_ci * Licensed under the Apache License, Version 2.0 (the "License"); 4dfe32fa1Soh_ci * you may not use this file except in compliance with the License. 5dfe32fa1Soh_ci * You may obtain a copy of the License at 6dfe32fa1Soh_ci * 7dfe32fa1Soh_ci * http://www.apache.org/licenses/LICENSE-2.0 8dfe32fa1Soh_ci * 9dfe32fa1Soh_ci * Unless required by applicable law or agreed to in writing, software 10dfe32fa1Soh_ci * distributed under the License is distributed on an "AS IS" BASIS, 11dfe32fa1Soh_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12dfe32fa1Soh_ci * See the License for the specific language governing permissions and 13dfe32fa1Soh_ci * limitations under the License. 14dfe32fa1Soh_ci */ 15dfe32fa1Soh_ci 16dfe32fa1Soh_ci//! This module extends the function of Asset data structure. 17dfe32fa1Soh_ci 18dfe32fa1Soh_ciuse std::{collections::HashMap, fmt::Display, hash::Hash, io}; 19dfe32fa1Soh_ci 20dfe32fa1Soh_ciuse asset_log::loge; 21dfe32fa1Soh_ci 22dfe32fa1Soh_ciuse super::{ 23dfe32fa1Soh_ci impl_from_for_u32, log_throw_error, Accessibility, AssetError, AuthType, Conversion, DataType, ErrCode, Extension, 24dfe32fa1Soh_ci Result, Tag, Value, 25dfe32fa1Soh_ci}; 26dfe32fa1Soh_ci 27dfe32fa1Soh_ci/// The mask used to obtain the data type of Asset attribute value. 28dfe32fa1Soh_ciconst DATA_TYPE_MASK: u32 = 0xF << 28; 29dfe32fa1Soh_ci 30dfe32fa1Soh_ciimpl Conversion for Tag { 31dfe32fa1Soh_ci fn data_type(&self) -> DataType { 32dfe32fa1Soh_ci let mask = (*self as u32) & DATA_TYPE_MASK; 33dfe32fa1Soh_ci match mask { 34dfe32fa1Soh_ci _ if DataType::Bool as u32 == mask => DataType::Bool, 35dfe32fa1Soh_ci _ if DataType::Number as u32 == mask => DataType::Number, 36dfe32fa1Soh_ci _ if DataType::Bytes as u32 == mask => DataType::Bytes, 37dfe32fa1Soh_ci _ => { 38dfe32fa1Soh_ci panic!("Unexpected data type, it should be bool, uint32 or bytes."); 39dfe32fa1Soh_ci }, 40dfe32fa1Soh_ci } 41dfe32fa1Soh_ci } 42dfe32fa1Soh_ci 43dfe32fa1Soh_ci fn into_value(self) -> Value { 44dfe32fa1Soh_ci Value::Number(self as u32) 45dfe32fa1Soh_ci } 46dfe32fa1Soh_ci} 47dfe32fa1Soh_ci 48dfe32fa1Soh_ciimpl Conversion for Value { 49dfe32fa1Soh_ci fn data_type(&self) -> DataType { 50dfe32fa1Soh_ci match self { 51dfe32fa1Soh_ci Value::Bool(_) => DataType::Bool, 52dfe32fa1Soh_ci Value::Number(_) => DataType::Number, 53dfe32fa1Soh_ci Value::Bytes(_) => DataType::Bytes, 54dfe32fa1Soh_ci } 55dfe32fa1Soh_ci } 56dfe32fa1Soh_ci 57dfe32fa1Soh_ci fn into_value(self) -> Value { 58dfe32fa1Soh_ci self 59dfe32fa1Soh_ci } 60dfe32fa1Soh_ci} 61dfe32fa1Soh_ci 62dfe32fa1Soh_ciimpl Conversion for Vec<u8> { 63dfe32fa1Soh_ci fn data_type(&self) -> DataType { 64dfe32fa1Soh_ci DataType::Bytes 65dfe32fa1Soh_ci } 66dfe32fa1Soh_ci 67dfe32fa1Soh_ci fn into_value(self) -> Value { 68dfe32fa1Soh_ci Value::Bytes(self) 69dfe32fa1Soh_ci } 70dfe32fa1Soh_ci} 71dfe32fa1Soh_ci 72dfe32fa1Soh_ciimpl Conversion for bool { 73dfe32fa1Soh_ci fn data_type(&self) -> DataType { 74dfe32fa1Soh_ci DataType::Bool 75dfe32fa1Soh_ci } 76dfe32fa1Soh_ci 77dfe32fa1Soh_ci fn into_value(self) -> Value { 78dfe32fa1Soh_ci Value::Bool(self) 79dfe32fa1Soh_ci } 80dfe32fa1Soh_ci} 81dfe32fa1Soh_ci 82dfe32fa1Soh_ciimpl Conversion for u32 { 83dfe32fa1Soh_ci fn data_type(&self) -> DataType { 84dfe32fa1Soh_ci DataType::Number 85dfe32fa1Soh_ci } 86dfe32fa1Soh_ci 87dfe32fa1Soh_ci fn into_value(self) -> Value { 88dfe32fa1Soh_ci Value::Number(self) 89dfe32fa1Soh_ci } 90dfe32fa1Soh_ci} 91dfe32fa1Soh_ci 92dfe32fa1Soh_ciimpl<K> Extension<K> for HashMap<K, Value> 93dfe32fa1Soh_ciwhere 94dfe32fa1Soh_ci K: Eq + PartialEq + Hash + std::fmt::Display, 95dfe32fa1Soh_ci{ 96dfe32fa1Soh_ci fn insert_attr(&mut self, key: K, value: impl Conversion) { 97dfe32fa1Soh_ci self.insert(key, value.into_value()); 98dfe32fa1Soh_ci } 99dfe32fa1Soh_ci 100dfe32fa1Soh_ci fn get_bool_attr(&self, key: &K) -> Result<bool> { 101dfe32fa1Soh_ci if let Some(Value::Bool(b)) = self.get(key) { 102dfe32fa1Soh_ci Ok(*b) 103dfe32fa1Soh_ci } else { 104dfe32fa1Soh_ci log_throw_error!(ErrCode::InvalidArgument, "[FATAL]Get attribute of bool type failed, key: {}", key) 105dfe32fa1Soh_ci } 106dfe32fa1Soh_ci } 107dfe32fa1Soh_ci 108dfe32fa1Soh_ci fn get_enum_attr<T: TryFrom<u32, Error = AssetError>>(&self, key: &K) -> Result<T> { 109dfe32fa1Soh_ci if let Some(Value::Number(num)) = self.get(key) { 110dfe32fa1Soh_ci T::try_from(*num) 111dfe32fa1Soh_ci } else { 112dfe32fa1Soh_ci log_throw_error!(ErrCode::InvalidArgument, "[FATAL]Get attribute of enum type failed, key: {}", key) 113dfe32fa1Soh_ci } 114dfe32fa1Soh_ci } 115dfe32fa1Soh_ci 116dfe32fa1Soh_ci fn get_num_attr(&self, key: &K) -> Result<u32> { 117dfe32fa1Soh_ci if let Some(Value::Number(num)) = self.get(key) { 118dfe32fa1Soh_ci Ok(*num) 119dfe32fa1Soh_ci } else { 120dfe32fa1Soh_ci log_throw_error!(ErrCode::InvalidArgument, "[FATAL]Get attribute of number type failed, key: {}", key) 121dfe32fa1Soh_ci } 122dfe32fa1Soh_ci } 123dfe32fa1Soh_ci 124dfe32fa1Soh_ci fn get_bytes_attr(&self, key: &K) -> Result<&Vec<u8>> { 125dfe32fa1Soh_ci if let Some(Value::Bytes(bytes)) = self.get(key) { 126dfe32fa1Soh_ci Ok(bytes) 127dfe32fa1Soh_ci } else { 128dfe32fa1Soh_ci log_throw_error!(ErrCode::InvalidArgument, "[FATAL]Get attribute of bytes type failed, key: {}", key) 129dfe32fa1Soh_ci } 130dfe32fa1Soh_ci } 131dfe32fa1Soh_ci} 132dfe32fa1Soh_ci 133dfe32fa1Soh_ciimpl Display for AssetError { 134dfe32fa1Soh_ci fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { 135dfe32fa1Soh_ci write!(f, "[{}]: {}", self.code, self.msg) 136dfe32fa1Soh_ci } 137dfe32fa1Soh_ci} 138dfe32fa1Soh_ci 139dfe32fa1Soh_ciimpl AssetError { 140dfe32fa1Soh_ci /// Create an AssetError instance. 141dfe32fa1Soh_ci pub fn new(code: ErrCode, msg: String) -> AssetError { 142dfe32fa1Soh_ci loge!("{}", msg); 143dfe32fa1Soh_ci AssetError { code, msg } 144dfe32fa1Soh_ci } 145dfe32fa1Soh_ci} 146dfe32fa1Soh_ci 147dfe32fa1Soh_ciimpl From<io::Error> for AssetError { 148dfe32fa1Soh_ci fn from(error: io::Error) -> Self { 149dfe32fa1Soh_ci AssetError { 150dfe32fa1Soh_ci code: (ErrCode::FileOperationError), 151dfe32fa1Soh_ci msg: (format!("[FATAL]Backup db failed! error is [{error}]")), 152dfe32fa1Soh_ci } 153dfe32fa1Soh_ci } 154dfe32fa1Soh_ci} 155dfe32fa1Soh_ci 156dfe32fa1Soh_ciimpl_from_for_u32!(AuthType); 157dfe32fa1Soh_ciimpl_from_for_u32!(Accessibility); 158