RTBKit
0.9
Open-source framework to create real-time ad bidding systems.
|
00001 /* account_key.h -*- C++ -*- 00002 Jeremy Barnes, 24 November 2012 00003 Copyright (c) 2012 Datacratic. All rights reserved. 00004 00005 Key to identify an account. 00006 */ 00007 00008 #pragma once 00009 00010 #include <string> 00011 #include <vector> 00012 #include "jml/utils/string_functions.h" 00013 #include "jml/arch/exception.h" 00014 #include "jml/db/persistent_fwd.h" 00015 #include "soa/jsoncpp/json.h" 00016 #include "soa/service/json_codec.h" 00017 #include <city.h> 00018 00019 00020 namespace RTBKIT { 00021 00031 void validateSlug(const std::string & slug); 00032 00033 00034 typedef std::vector<std::string> AccountKeyBase; 00035 00036 00037 /*****************************************************************************/ 00038 /* ACCOUNT KEY */ 00039 /*****************************************************************************/ 00040 00044 struct AccountKey : public AccountKeyBase { 00045 AccountKey() 00046 { 00047 } 00048 00049 AccountKey(const std::string & str, char delimiter = ':') 00050 : AccountKeyBase(ML::split(str, delimiter)) 00051 { 00052 validate(); 00053 } 00054 00055 AccountKey(const std::vector<std::string> & vals) 00056 : AccountKeyBase(vals) 00057 { 00058 validate(); 00059 } 00060 00061 AccountKey(const std::initializer_list<std::string> & vals) 00062 : AccountKeyBase(vals) 00063 { 00064 validate(); 00065 } 00066 00067 void validate() const 00068 { 00069 for (const std::string & slug: *this) 00070 validateSlug(slug); 00071 } 00072 00073 std::string toString(char delimiter = ':') const 00074 { 00075 std::string result; 00076 for (unsigned i = 0; i < size(); ++i) { 00077 if (i != 0) 00078 result += delimiter; 00079 result += (*this)[i]; 00080 } 00081 return result; 00082 } 00083 00084 AccountKey parent() const 00085 { 00086 if (empty()) 00087 throw ML::Exception("no parent"); 00088 AccountKey result = *this; 00089 result.pop_back(); 00090 return result; 00091 } 00092 00093 AccountKey childKey(const std::string & childName) const 00094 { 00095 AccountKey result = *this; 00096 result.push_back(childName); 00097 return result; 00098 } 00099 00100 bool hasPrefix(const AccountKey & otherKey) const 00101 { 00102 return size() >= otherKey.size() 00103 && std::equal(otherKey.begin(), otherKey.end(), begin()); 00104 } 00105 00106 Json::Value toJson() const 00107 { 00108 return Datacratic::jsonEncode(static_cast<AccountKeyBase>(*this)); 00109 } 00110 00111 static AccountKey fromJson(const Json::Value & json) 00112 { 00113 return Datacratic::jsonDecode(json, (AccountKeyBase *)0); 00114 } 00115 00116 uint64_t hash() const 00117 { 00118 uint64_t res = 1232134; 00119 for (auto s: *this) 00120 res = CityHash64WithSeed(s.c_str(), s.size(), res); 00121 return res; 00122 } 00123 00124 bool operator< (const AccountKey& other) 00125 { 00126 for (size_t i = 0, n = std::min(size(), other.size()); i < n; ++i) { 00127 int comp = at(i).compare(other[i]); 00128 if (comp < 0) return true; 00129 if (comp > 0) return false; 00130 } 00131 return size() < other.size(); 00132 } 00133 00134 00135 void serialize(ML::DB::Store_Writer & store) const; 00136 void reconstitute(ML::DB::Store_Reader & store); 00137 }; 00138 00139 inline std::ostream & 00140 operator << (std::ostream & stream, const AccountKey & key) 00141 { 00142 return stream << key.toString(); 00143 } 00144 00145 } // namespace RTBKIT 00146 00147 namespace std { 00148 00149 template<> 00150 struct hash<RTBKIT::AccountKey> { 00151 uint64_t operator () (const RTBKIT::AccountKey & key) const 00152 { 00153 return key.hash(); 00154 } 00155 }; 00156 00157 } // namespace std