Hazelcast C++ Client
Hazelcast C++ Client Library
imap.h
1 /*
2  * Copyright (c) 2008-2022, Hazelcast, Inc. All Rights Reserved.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 #pragma once
17 
18 #include <string>
19 #include <unordered_map>
20 #include <unordered_set>
21 #include <vector>
22 #include <stdexcept>
23 #include <climits>
24 #include <assert.h>
25 
26 #include <boost/container/vector.hpp>
27 
28 #include "hazelcast/client/monitor/local_map_stats.h"
29 #include "hazelcast/client/monitor/impl/NearCacheStatsImpl.h"
30 #include "hazelcast/client/monitor/impl/LocalMapStatsImpl.h"
31 #include "hazelcast/client/proxy/IMapImpl.h"
32 #include "hazelcast/client/impl/EntryEventHandler.h"
33 #include "hazelcast/client/entry_listener.h"
34 #include "hazelcast/client/serialization/serialization.h"
35 #include "hazelcast/util/exception_util.h"
36 #include "hazelcast/client/protocol/codec/codecs.h"
37 #include "hazelcast/client/spi/ClientContext.h"
38 
39 #if defined(WIN32) || defined(_WIN32) || defined(WIN64) || defined(_WIN64)
40 #pragma warning(push)
41 #pragma warning(disable : 4251) // for dll export
42 #endif
43 
44 namespace hazelcast {
45 namespace client {
46 class hazelcast_client;
47 
48 namespace spi {
49 class ProxyManager;
50 }
51 
62 class HAZELCAST_API imap : public proxy::IMapImpl
63 {
64  friend class spi::ProxyManager;
65 
66 public:
67  static constexpr const char* SERVICE_NAME = "hz:impl:mapService";
68 
69  imap(const std::string& instance_name, spi::ClientContext* context)
70  : proxy::IMapImpl(instance_name, context)
71  {}
72 
78  template<typename K>
79  boost::future<bool> contains_key(const K& key)
80  {
81  return contains_key_internal(to_data(key));
82  }
83 
89  template<typename V>
90  boost::future<bool> contains_value(const V& value)
91  {
92  return proxy::IMapImpl::contains_value(to_data(value));
93  }
94 
101  template<typename K, typename V>
102  boost::future<boost::optional<V>> get(const K& key)
103  {
104  return to_object<V>(get_internal(to_data(key)));
105  }
106 
114  template<typename K, typename V, typename R = V>
115  boost::future<boost::optional<R>> put(const K& key, const V& value)
116  {
117  return put<K, V, R>(key, value, UNSET);
118  }
119 
132  template<typename K, typename V, typename R = V>
133  boost::future<boost::optional<R>> put(const K& key,
134  const V& value,
135  std::chrono::milliseconds ttl)
136  {
137  return to_object<R>(put_internal(to_data(key), to_data(value), ttl));
138  }
139 
146  template<typename K, typename V>
147  boost::future<boost::optional<V>> remove(const K& key)
148  {
149  return to_object<V>(remove_internal(to_data(key)));
150  }
151 
159  template<typename K, typename V>
160  boost::future<bool> remove(const K& key, const V& value)
161  {
162  return remove_internal(to_data(key), to_data(value));
163  }
164 
176  template<typename P>
177  boost::future<void> remove_all(const P& predicate)
178  {
179  return to_void_future(remove_all_internal(to_data<P>(predicate)));
180  }
181 
187  template<typename K>
188  boost::future<void> delete_entry(const K& key)
189  {
190  return to_void_future(delete_internal(to_data(key)));
191  }
192 
202  template<typename K>
203  boost::future<bool> try_remove(const K& key,
204  std::chrono::milliseconds timeout)
205  {
206  return try_remove_internal(to_data(key), timeout);
207  }
208 
221  template<typename K, typename V>
222  boost::future<bool> try_put(const K& key,
223  const V& value,
224  std::chrono::milliseconds timeout)
225  {
226  return try_put_internal(to_data(key), to_data(value), timeout);
227  }
228 
239  template<typename K, typename V>
240  boost::future<void> put_transient(const K& key,
241  const V& value,
242  std::chrono::milliseconds ttl)
243  {
244  return to_void_future(
245  try_put_transient_internal(to_data(key), to_data(value), ttl));
246  }
247 
257  template<typename K, typename V, typename R = V>
258  boost::future<boost::optional<V>> put_if_absent(const K& key,
259  const V& value)
260  {
261  return put_if_absent(key, value, UNSET);
262  }
263 
275  template<typename K, typename V, typename R = V>
276  boost::future<boost::optional<V>>
277  put_if_absent(const K& key, const V& value, std::chrono::milliseconds ttl)
278  {
279  return to_object<R>(
280  put_if_absent_internal(to_data(key), to_data(value), ttl));
281  }
282 
290  template<typename K, typename V, typename N = V>
291  boost::future<bool> replace(const K& key,
292  const V& old_value,
293  const N& new_value)
294  {
295  return replace_if_same_internal(
296  to_data(key), to_data(old_value), to_data(new_value));
297  }
298 
306  template<typename K, typename V, typename R = V>
307  boost::future<boost::optional<R>> replace(const K& key, const V& value)
308  {
309  return to_object<R>(replace_internal(to_data(key), to_data(value)));
310  }
311 
319  template<typename K, typename V, typename R = V>
320  boost::future<void> set(const K& key, const V& value)
321  {
322  return to_void_future(set(key, value, UNSET));
323  }
324 
334  template<typename K, typename V>
335  boost::future<void> set(const K& key,
336  const V& value,
337  std::chrono::milliseconds ttl)
338  {
339  return to_void_future(set_internal(to_data(key), to_data(value), ttl));
340  }
341 
356  template<typename K>
357  boost::future<void> lock(const K& key)
358  {
359  return to_void_future(lock(key, UNSET));
360  }
361 
380  template<typename K>
381  boost::future<void> lock(const K& key, std::chrono::milliseconds lease_time)
382  {
383  return to_void_future(proxy::IMapImpl::lock(to_data(key), lease_time));
384  }
385 
394  template<typename K>
395  boost::future<bool> is_locked(const K& key)
396  {
397  return proxy::IMapImpl::is_locked(to_data(key));
398  }
399 
409  template<typename K>
410  boost::future<bool> try_lock(const K& key)
411  {
412  return try_lock(key, std::chrono::milliseconds(0));
413  }
414 
431  template<typename K>
432  boost::future<bool> try_lock(const K& key,
433  std::chrono::milliseconds timeout)
434  {
435  return proxy::IMapImpl::try_lock(to_data(key), timeout);
436  }
437 
455  template<typename K>
456  boost::future<bool> try_lock(const K& key,
457  std::chrono::milliseconds timeout,
458  std::chrono::milliseconds lease_time)
459  {
460  return proxy::IMapImpl::try_lock(to_data(key), timeout, lease_time);
461  }
462 
477  template<typename K>
478  boost::future<void> unlock(const K& key)
479  {
480  return to_void_future(proxy::IMapImpl::unlock(to_data(key)));
481  }
482 
491  template<typename K>
492  boost::future<void> force_unlock(const K& key)
493  {
494  return to_void_future(proxy::IMapImpl::force_unlock(to_data(key)));
495  }
496 
509  template<typename MapInterceptor>
510  boost::future<std::string> add_interceptor(
511  const MapInterceptor& interceptor)
512  {
513  return proxy::IMapImpl::add_interceptor(to_data(interceptor));
514  }
515 
531  boost::future<boost::uuids::uuid> add_entry_listener(
532  entry_listener&& listener,
533  bool include_value)
534  {
535  const auto listener_flags = listener.flags_;
536  return proxy::IMapImpl::add_entry_listener(
537  std::unique_ptr<impl::BaseEventHandler>(
538  new impl::EntryEventHandler<
539  protocol::codec::map_addentrylistener_handler>(
540  get_name(),
541  get_context().get_client_cluster_service(),
542  get_context().get_serialization_service(),
543  std::move(listener),
544  include_value,
545  get_context().get_logger())),
546  include_value,
547  listener_flags);
548  }
549 
567  template<typename P>
568  boost::future<boost::uuids::uuid> add_entry_listener(
569  entry_listener&& listener,
570  const P& predicate,
571  bool include_value)
572  {
573  const auto listener_flags = listener.flags_;
574  return proxy::IMapImpl::add_entry_listener(
575  std::unique_ptr<impl::BaseEventHandler>(
576  new impl::EntryEventHandler<
577  protocol::codec::map_addentrylistenerwithpredicate_handler>(
578  get_name(),
579  get_context().get_client_cluster_service(),
580  get_context().get_serialization_service(),
581  std::move(listener),
582  include_value,
583  get_context().get_logger())),
584  to_data<P>(predicate),
585  include_value,
586  listener_flags);
587  }
588 
602  template<typename K>
603  boost::future<boost::uuids::uuid> add_entry_listener(
604  entry_listener&& listener,
605  bool include_value,
606  const K& key)
607  {
608  const auto listener_flags = listener.flags_;
609  return proxy::IMapImpl::add_entry_listener(
610  std::shared_ptr<impl::BaseEventHandler>(
611  new impl::EntryEventHandler<
612  protocol::codec::map_addentrylistenertokey_handler>(
613  get_name(),
614  get_context().get_client_cluster_service(),
615  get_context().get_serialization_service(),
616  std::move(listener),
617  include_value,
618  get_context().get_logger())),
619  include_value,
620  to_data<K>(key),
621  listener_flags);
622  }
623 
632  template<typename K, typename V>
633  boost::future<boost::optional<entry_view<K, V>>> get_entry_view(
634  const K& key)
635  {
636  auto f = proxy::IMapImpl::get_entry_view_data(to_data(key));
637  return to_object_entry_view<K, V>(std::move(f));
638  }
639 
650  template<typename K>
651  boost::future<bool> evict(const K& key)
652  {
653  return evict_internal(to_data(key));
654  }
655 
662  template<typename K, typename V>
663  boost::future<std::unordered_map<K, V>> get_all(
664  const std::unordered_set<K>& keys)
665  {
666  if (keys.empty()) {
667  return boost::make_ready_future(std::unordered_map<K, V>());
668  }
669 
670  std::unordered_map<int, std::vector<serialization::pimpl::data>>
671  partition_to_key_data;
672  // group the request per server
673  for (auto& key : keys) {
674  auto key_data = to_data<K>(key);
675 
676  auto partitionId = get_partition_id(key_data);
677  partition_to_key_data[partitionId].push_back(std::move(key_data));
678  }
679 
680  std::vector<boost::future<EntryVector>> futures;
681  futures.reserve(partition_to_key_data.size());
682  for (auto& entry : partition_to_key_data) {
683  futures.push_back(get_all_internal(entry.first, entry.second));
684  }
685 
686  return to_object_map<K, V>(futures);
687  }
688 
697  template<typename K>
698  boost::future<std::vector<K>> key_set()
699  {
700  return to_object_vector<K>(proxy::IMapImpl::key_set_data());
701  }
702 
714  template<
715  typename K,
716  typename P,
717  class = typename std::enable_if<
718  !std::is_base_of<query::paging_predicate_marker, P>::value>::type>
719  boost::future<std::vector<K>> key_set(const P& predicate)
720  {
721  return to_object_vector<K>(
722  proxy::IMapImpl::key_set_data(to_data(predicate)));
723  }
724 
736  template<typename K, typename V>
737  boost::future<std::vector<K>> key_set(
739  {
740  predicate.set_iteration_type(query::iteration_type::KEY);
741  auto future = key_set_for_paging_predicate_data(
742  protocol::codec::holder::paging_predicate_holder::of(
743  predicate, serialization_service_));
744  return keys_to_object_vector_with_predicate(std::move(future),
745  predicate);
746  }
747 
756  template<typename V>
757  boost::future<std::vector<V>> values()
758  {
759  return to_object_vector<V>(proxy::IMapImpl::values_data());
760  }
761 
771  template<
772  typename V,
773  typename P,
774  class = typename std::enable_if<
775  !std::is_base_of<query::paging_predicate_marker, P>::value>::type>
776  boost::future<std::vector<V>> values(const P& predicate)
777  {
778  return to_object_vector<V>(
779  proxy::IMapImpl::values_data(to_data(predicate)));
780  }
781 
792  template<typename K, typename V>
793  boost::future<std::vector<V>> values(
795  {
796  predicate.set_iteration_type(query::iteration_type::VALUE);
797  auto future = values_for_paging_predicate_data(
798  protocol::codec::holder::paging_predicate_holder::of(
799  predicate, serialization_service_));
800  return values_to_object_vector_with_predicate(std::move(future),
801  predicate);
802  }
803 
811  template<typename K, typename V>
812  boost::future<std::vector<std::pair<K, V>>> entry_set()
813  {
814  return to_entry_object_vector<K, V>(proxy::IMapImpl::entry_set_data());
815  }
816 
827  template<
828  typename K,
829  typename V,
830  typename P,
831  class = typename std::enable_if<
832  !std::is_base_of<query::paging_predicate_marker, P>::value>::type>
833  boost::future<std::vector<std::pair<K, V>>> entry_set(const P& predicate)
834  {
835  return to_entry_object_vector<K, V>(
836  proxy::IMapImpl::entry_set_data(to_data(predicate)));
837  }
838 
849  template<typename K, typename V>
850  boost::future<std::vector<std::pair<K, V>>> entry_set(
852  {
853  predicate.set_iteration_type(query::iteration_type::ENTRY);
854  auto future = entry_set_for_paging_predicate_data(
855  protocol::codec::holder::paging_predicate_holder::of(
856  predicate, serialization_service_));
857  return entry_set_to_object_vector_with_predicate<K, V>(
858  std::move(future), predicate);
859  }
860 
901  boost::future<void> add_index(const config::index_config& config)
902  {
903  return to_void_future(proxy::IMapImpl::add_index_data(config));
904  }
905 
913  template<typename... T>
914  boost::future<void> add_index(config::index_config::index_type type,
915  T... attributes)
916  {
917  return add_index(
918  config::index_config(type, std::forward<T>(attributes)...));
919  }
920 
921  boost::future<void> clear()
922  {
923  return to_void_future(proxy::IMapImpl::clear_data());
924  }
925 
941  template<typename K, typename ResultType, typename EntryProcessor>
942  boost::future<boost::optional<ResultType>> execute_on_key(
943  const K& key,
944  const EntryProcessor& entry_processor)
945  {
946  return to_object<ResultType>(
947  execute_on_key_internal(to_data(key), to_data(entry_processor)));
948  }
949 
959  template<typename K, typename ResultType, typename EntryProcessor>
960  boost::future<boost::optional<ResultType>> submit_to_key(
961  const K& key,
962  const EntryProcessor& entry_processor)
963  {
964  return to_object<ResultType>(
965  submit_to_key_internal(to_data(key), to_data(entry_processor)));
966  }
967 
981  template<typename K, typename ResultType, typename EntryProcessor>
982  boost::future<std::unordered_map<K, boost::optional<ResultType>>>
983  execute_on_keys(const std::unordered_set<K>& keys,
984  const EntryProcessor& entry_processor)
985  {
986  return to_object_map<K, ResultType>(
987  execute_on_keys_internal<K, EntryProcessor>(keys, entry_processor));
988  }
989 
1003  template<typename K, typename ResultType, typename EntryProcessor>
1004  boost::future<std::unordered_map<K, boost::optional<ResultType>>>
1005  execute_on_entries(const EntryProcessor& entry_processor)
1006  {
1007  return to_object_map<K, ResultType>(
1008  proxy::IMapImpl::execute_on_entries_data(to_data(entry_processor)));
1009  }
1010 
1026  template<typename K,
1027  typename ResultType,
1028  typename EntryProcessor,
1029  typename P>
1030  boost::future<std::unordered_map<K, boost::optional<ResultType>>>
1031  execute_on_entries(const EntryProcessor& entry_processor,
1032  const P& predicate)
1033  {
1034  return to_object_map<K, ResultType>(
1035  proxy::IMapImpl::execute_on_entries_data(to_data(entry_processor),
1036  to_data(predicate)));
1037  }
1038 
1049  template<typename K, typename V>
1050  boost::future<void> put_all(const std::unordered_map<K, V>& entries)
1051  {
1052  std::unordered_map<int, EntryVector> entryMap;
1053  for (auto& entry : entries) {
1054  serialization::pimpl::data key_data = to_data(entry.first);
1055  int partitionId = get_partition_id(key_data);
1056  entryMap[partitionId].push_back(
1057  std::make_pair(key_data, to_data(entry.second)));
1058  }
1059 
1060  std::vector<boost::future<protocol::ClientMessage>> resultFutures;
1061  for (auto&& partitionEntry : entryMap) {
1062  auto partitionId = partitionEntry.first;
1063  resultFutures.push_back(
1064  put_all_internal(partitionId, std::move(partitionEntry.second)));
1065  }
1066  return boost::when_all(resultFutures.begin(), resultFutures.end())
1067  .then(boost::launch::sync,
1068  [](boost::future<boost::csbl::vector<
1069  boost::future<protocol::ClientMessage>>> futures) {
1070  for (auto& f : futures.get()) {
1071  f.get();
1072  }
1073  });
1074  }
1075 
1088  monitor::local_map_stats& get_local_map_stats() { return local_map_stats_; }
1089 
1090  template<typename K, typename V>
1091  query::paging_predicate<K, V> new_paging_predicate(
1092  size_t predicate_page_size)
1093  {
1094  return query::paging_predicate<K, V>(get_serialization_service(),
1095  predicate_page_size);
1096  }
1097 
1098  template<typename K, typename V, typename INNER_PREDICATE>
1099  query::paging_predicate<K, V> new_paging_predicate(
1100  size_t predicate_page_size,
1101  const INNER_PREDICATE& predicate)
1102  {
1103  return query::paging_predicate<K, V>(
1104  get_serialization_service(), predicate_page_size, predicate);
1105  }
1106 
1107  template<typename K, typename V, typename COMPARATOR>
1108  query::paging_predicate<K, V> new_paging_predicate(
1109  COMPARATOR&& comparator,
1110  size_t predicate_page_size)
1111  {
1112  return query::paging_predicate<K, V>(get_serialization_service(),
1113  std::move(comparator),
1114  predicate_page_size);
1115  }
1116 
1117  template<typename K,
1118  typename V,
1119  typename INNER_PREDICATE,
1120  typename COMPARATOR>
1121  query::paging_predicate<K, V> new_paging_predicate(
1122  const INNER_PREDICATE& predicate,
1123  COMPARATOR&& comparator,
1124  size_t predicate_page_size)
1125  {
1126  return query::paging_predicate<K, V>(get_serialization_service(),
1127  predicate,
1128  std::move(comparator),
1129  predicate_page_size);
1130  }
1131 
1132 protected:
1136  static const std::chrono::milliseconds UNSET;
1137 
1138  monitor::impl::LocalMapStatsImpl local_map_stats_;
1139 
1140  virtual boost::future<boost::optional<serialization::pimpl::data>>
1141  get_internal(const serialization::pimpl::data& key_data)
1142  {
1143  return proxy::IMapImpl::get_data(key_data);
1144  }
1145 
1146  virtual boost::future<bool> contains_key_internal(
1147  const serialization::pimpl::data& key_data)
1148  {
1149  return proxy::IMapImpl::contains_key(key_data);
1150  }
1151 
1152  virtual boost::future<boost::optional<serialization::pimpl::data>>
1153  remove_internal(const serialization::pimpl::data& key_data)
1154  {
1155  return proxy::IMapImpl::remove_data(key_data);
1156  }
1157 
1158  virtual boost::future<bool> remove_internal(
1159  const serialization::pimpl::data& key_data,
1160  const serialization::pimpl::data& value_data)
1161  {
1162  return proxy::IMapImpl::remove(key_data, value_data);
1163  }
1164 
1165  virtual boost::future<protocol::ClientMessage> remove_all_internal(
1166  const serialization::pimpl::data& predicate_data)
1167  {
1168  return proxy::IMapImpl::remove_all(predicate_data);
1169  }
1170 
1171  virtual boost::future<protocol::ClientMessage> delete_internal(
1172  const serialization::pimpl::data& key_data)
1173  {
1174  return proxy::IMapImpl::delete_entry(key_data);
1175  }
1176 
1177  virtual boost::future<bool> try_remove_internal(
1178  const serialization::pimpl::data& key_data,
1179  std::chrono::milliseconds timeout)
1180  {
1181  return proxy::IMapImpl::try_remove(key_data, timeout);
1182  }
1183 
1184  virtual boost::future<bool> try_put_internal(
1185  const serialization::pimpl::data& key_data,
1186  const serialization::pimpl::data& value_data,
1187  std::chrono::milliseconds timeout)
1188  {
1189  return proxy::IMapImpl::try_put(key_data, value_data, timeout);
1190  }
1191 
1192  virtual boost::future<boost::optional<serialization::pimpl::data>>
1193  put_internal(const serialization::pimpl::data& key_data,
1194  const serialization::pimpl::data& value_data,
1195  std::chrono::milliseconds ttl)
1196  {
1197  return proxy::IMapImpl::put_data(key_data, value_data, ttl);
1198  }
1199 
1200  virtual boost::future<protocol::ClientMessage> try_put_transient_internal(
1201  const serialization::pimpl::data& key_data,
1202  const serialization::pimpl::data& value_data,
1203  std::chrono::milliseconds ttl)
1204  {
1205  return proxy::IMapImpl::put_transient(key_data, value_data, ttl);
1206  }
1207 
1208  virtual boost::future<boost::optional<serialization::pimpl::data>>
1209  put_if_absent_internal(const serialization::pimpl::data& key_data,
1210  const serialization::pimpl::data& value_data,
1211  std::chrono::milliseconds ttl)
1212  {
1213  return proxy::IMapImpl::put_if_absent_data(key_data, value_data, ttl);
1214  }
1215 
1216  virtual boost::future<bool> replace_if_same_internal(
1217  const serialization::pimpl::data& key_data,
1218  const serialization::pimpl::data& value_data,
1219  const serialization::pimpl::data& new_value_data)
1220  {
1221  return proxy::IMapImpl::replace(key_data, value_data, new_value_data);
1222  }
1223 
1224  virtual boost::future<boost::optional<serialization::pimpl::data>>
1225  replace_internal(const serialization::pimpl::data& key_data,
1226  const serialization::pimpl::data& value_data)
1227  {
1228  return proxy::IMapImpl::replace_data(key_data, value_data);
1229  }
1230 
1231  virtual boost::future<protocol::ClientMessage> set_internal(
1232  const serialization::pimpl::data& key_data,
1233  const serialization::pimpl::data& value_data,
1234  std::chrono::milliseconds ttl)
1235  {
1236  return proxy::IMapImpl::set(key_data, value_data, ttl);
1237  }
1238 
1239  virtual boost::future<bool> evict_internal(
1240  const serialization::pimpl::data& key_data)
1241  {
1242  return proxy::IMapImpl::evict(key_data);
1243  }
1244 
1245  virtual boost::future<EntryVector> get_all_internal(
1246  int partition_id,
1247  const std::vector<serialization::pimpl::data>& partition_keys)
1248  {
1249  return proxy::IMapImpl::get_all_data(partition_id, partition_keys);
1250  }
1251 
1252  virtual boost::future<boost::optional<serialization::pimpl::data>>
1253  execute_on_key_internal(const serialization::pimpl::data& key_data,
1254  const serialization::pimpl::data& processor)
1255  {
1256  return proxy::IMapImpl::execute_on_key_data(key_data, processor);
1257  }
1258 
1259  boost::future<boost::optional<serialization::pimpl::data>>
1260  submit_to_key_internal(const serialization::pimpl::data& key_data,
1261  const serialization::pimpl::data& processor)
1262  {
1263  return submit_to_key_data(key_data, processor);
1264  }
1265 
1266  template<typename K, typename EntryProcessor>
1267  boost::future<EntryVector> execute_on_keys_internal(
1268  const std::unordered_set<K>& keys,
1269  const EntryProcessor& entry_processor)
1270  {
1271  if (keys.empty()) {
1272  return boost::make_ready_future(EntryVector());
1273  }
1274  std::vector<serialization::pimpl::data> keysData;
1275  for (const auto& k : keys) {
1276  keysData.push_back(to_data<K>(k));
1277  }
1278  return proxy::IMapImpl::execute_on_keys_data(
1279  keysData, to_data<EntryProcessor>(entry_processor));
1280  }
1281 
1282  virtual boost::future<protocol::ClientMessage> put_all_internal(
1283  int partition_id,
1284  const EntryVector& entries)
1285  {
1286  return proxy::IMapImpl::put_all_data(partition_id, entries);
1287  }
1288 
1289 private:
1290  template<typename K, typename V>
1291  std::vector<std::pair<K, boost::optional<V>>> sort_and_get(
1292  query::paging_predicate<K, V>& predicate,
1293  query::iteration_type iteration_type,
1294  std::vector<std::pair<K, V>> entries)
1295  {
1296  std::vector<std::pair<K, boost::optional<V>>> optionalEntries;
1297  optionalEntries.reserve(entries.size());
1298  for (auto&& pair : entries) {
1299  optionalEntries.emplace_back(pair.first,
1300  boost::make_optional(pair.second));
1301  }
1302  return sortAndGet(predicate, iteration_type, optionalEntries);
1303  }
1304 
1305  template<typename K, typename V>
1306  std::vector<std::pair<K, boost::optional<V>>> sort_and_get(
1307  query::paging_predicate<K, V>& predicate,
1308  query::iteration_type iteration_type,
1309  std::vector<std::pair<K, boost::optional<V>>> entries)
1310  {
1311  std::sort(entries.begin(),
1312  entries.end(),
1313  [&](const std::pair<K, boost::optional<V>>& lhs,
1314  const std::pair<K, boost::optional<V>>& rhs) {
1315  auto comparator = predicate.getComparator();
1316  if (!comparator) {
1317  switch (predicate.getIterationType()) {
1318  case query::iteration_type::VALUE:
1319  return lhs.second < rhs.second;
1320  default:
1321  return lhs.first < rhs.first;
1322  }
1323  }
1324 
1325  std::pair<const K*, const V*> leftVal(
1326  &lhs.first, lhs.second.get_ptr());
1327  std::pair<const K*, const V*> rightVal(
1328  &rhs.first, rhs.second.get_ptr());
1329  int result = comparator->compare(&leftVal, &rightVal);
1330  if (0 != result) {
1331  // std sort: comparison function object returns
1332  // ​true if the first argument is less than (i.e. is
1333  // ordered before) the second.
1334  return result < 0;
1335  }
1336 
1337  return lhs.first < rhs.first;
1338  });
1339 
1340  std::pair<size_t, size_t> range =
1341  update_anchor<K, V>(entries, predicate, iteration_type);
1342 
1343  std::vector<std::pair<K, boost::optional<V>>> result;
1344  for (size_t i = range.first; i < range.second; ++i) {
1345  auto entry = entries[i];
1346  result.push_back(std::make_pair(entry.first, entry.second));
1347  }
1348  return result;
1349  }
1350 };
1351 } // namespace client
1352 } // namespace hazelcast
1353 
1354 #if defined(WIN32) || defined(_WIN32) || defined(WIN64) || defined(_WIN64)
1355 #pragma warning(pop)
1356 #endif
Map entry listener to get notified when a map entry is added, removed, updated, evicted,...
Concurrent, distributed, observable and queryable map client.
Definition: imap.h:63
boost::future< std::vector< std::pair< K, V > > > entry_set()
Returns a std::vector< std::pair<K, V> > clone of the mappings contained in this map.
Definition: imap.h:812
boost::future< boost::optional< V > > put_if_absent(const K &key, const V &value, std::chrono::milliseconds ttl)
Puts an entry into this map with a given ttl (time to live) value if the specified key is not already...
Definition: imap.h:277
boost::future< void > lock(const K &key, std::chrono::milliseconds lease_time)
Acquires the lock for the specified key for the specified lease time.
Definition: imap.h:381
boost::future< bool > try_lock(const K &key, std::chrono::milliseconds timeout, std::chrono::milliseconds lease_time)
Tries to acquire the lock for the specified key for the specified lease time.
Definition: imap.h:456
boost::future< boost::uuids::uuid > add_entry_listener(entry_listener &&listener, bool include_value)
Adds an entry listener for this map.
Definition: imap.h:531
boost::future< bool > remove(const K &key, const V &value)
removes entry from map if there is an entry with same key and value.
Definition: imap.h:160
boost::future< boost::uuids::uuid > add_entry_listener(entry_listener &&listener, bool include_value, const K &key)
Adds the specified entry listener for the specified key.
Definition: imap.h:603
boost::future< boost::optional< V > > get(const K &key)
get the value.
Definition: imap.h:102
boost::future< std::vector< std::pair< K, V > > > entry_set(const P &predicate)
Queries the map based on the specified predicate and returns the matching entries.
Definition: imap.h:833
boost::future< void > remove_all(const P &predicate)
Removes all entries which match with the supplied predicate.
Definition: imap.h:177
boost::future< boost::optional< R > > replace(const K &key, const V &value)
Replaces the entry for a key only if currently mapped to some value.
Definition: imap.h:307
boost::future< std::vector< V > > values(const P &predicate)
Returns a vector clone of the values contained in this map.
Definition: imap.h:776
boost::future< boost::optional< ResultType > > submit_to_key(const K &key, const EntryProcessor &entry_processor)
Applies the user defined EntryProcessor to the entry mapped by the key.
Definition: imap.h:960
boost::future< boost::optional< R > > put(const K &key, const V &value)
put new entry into map.
Definition: imap.h:115
boost::future< boost::optional< V > > remove(const K &key)
remove entry form map
Definition: imap.h:147
boost::future< void > set(const K &key, const V &value)
Puts an entry into this map.
Definition: imap.h:320
boost::future< std::unordered_map< K, boost::optional< ResultType > > > execute_on_entries(const EntryProcessor &entry_processor, const P &predicate)
Applies the user defined EntryProcessor to the all entries in the map.
Definition: imap.h:1031
boost::future< std::unordered_map< K, V > > get_all(const std::unordered_set< K > &keys)
Returns the entries for the given keys.
Definition: imap.h:663
boost::future< void > add_index(config::index_config::index_type type, T... attributes)
Convenient method to add an index to this map with the given type and attributes.
Definition: imap.h:914
boost::future< std::vector< std::pair< K, V > > > entry_set(query::paging_predicate< K, V > &predicate)
Queries the map based on the specified predicate and returns the matching entries.
Definition: imap.h:850
boost::future< bool > replace(const K &key, const V &old_value, const N &new_value)
Replaces the entry for a key only if currently mapped to a given value.
Definition: imap.h:291
boost::future< void > force_unlock(const K &key)
Releases the lock for the specified key regardless of the lock owner.
Definition: imap.h:492
boost::future< boost::uuids::uuid > add_entry_listener(entry_listener &&listener, const P &predicate, bool include_value)
Adds an entry listener for this map.
Definition: imap.h:568
boost::future< bool > contains_key(const K &key)
check if this map contains key.
Definition: imap.h:79
boost::future< bool > try_remove(const K &key, std::chrono::milliseconds timeout)
Tries to remove the entry with the given key from this map within specified timeout value.
Definition: imap.h:203
boost::future< void > lock(const K &key)
Acquires the lock for the specified key.
Definition: imap.h:357
boost::future< std::string > add_interceptor(const MapInterceptor &interceptor)
Adds an interceptor for this map.
Definition: imap.h:510
boost::future< std::vector< V > > values()
Returns a vector clone of the values contained in this map.
Definition: imap.h:757
boost::future< std::vector< K > > key_set(query::paging_predicate< K, V > &predicate)
Queries the map based on the specified predicate and returns the keys of matching entries.
Definition: imap.h:737
boost::future< boost::optional< ResultType > > execute_on_key(const K &key, const EntryProcessor &entry_processor)
Applies the user defined EntryProcessor to the entry mapped by the key.
Definition: imap.h:942
monitor::local_map_stats & get_local_map_stats()
Returns LocalMapStats for this map.
Definition: imap.h:1088
boost::future< std::vector< V > > values(query::paging_predicate< K, V > &predicate)
Returns a vector clone of the values contained in this map.
Definition: imap.h:793
boost::future< void > put_all(const std::unordered_map< K, V > &entries)
Copies all of the mappings from the specified map to this map (optional operation).
Definition: imap.h:1050
boost::future< std::vector< K > > key_set()
Returns a vector clone of the keys contained in this map.
Definition: imap.h:698
boost::future< std::unordered_map< K, boost::optional< ResultType > > > execute_on_keys(const std::unordered_set< K > &keys, const EntryProcessor &entry_processor)
Applies the user defined EntryProcessor to the entries mapped by the collection of keys.
Definition: imap.h:983
boost::future< bool > contains_value(const V &value)
check if this map contains value.
Definition: imap.h:90
boost::future< boost::optional< R > > put(const K &key, const V &value, std::chrono::milliseconds ttl)
Puts an entry into this map with a given ttl (time to live) value.
Definition: imap.h:133
static const std::chrono::milliseconds UNSET
Default TTL value of a record.
Definition: imap.h:1136
boost::future< bool > is_locked(const K &key)
Checks the lock for the specified key.
Definition: imap.h:395
boost::future< void > add_index(const config::index_config &config)
Adds an index to this map for the specified entries so that queries can run faster.
Definition: imap.h:901
boost::future< std::vector< K > > key_set(const P &predicate)
Queries the map based on the specified predicate and returns the keys of matching entries.
Definition: imap.h:719
boost::future< bool > try_lock(const K &key, std::chrono::milliseconds timeout)
Tries to acquire the lock for the specified key.
Definition: imap.h:432
boost::future< boost::optional< V > > put_if_absent(const K &key, const V &value)
Puts an entry into this map, if the specified key is not already associated with a value.
Definition: imap.h:258
boost::future< std::unordered_map< K, boost::optional< ResultType > > > execute_on_entries(const EntryProcessor &entry_processor)
Applies the user defined EntryProcessor to the all entries in the map.
Definition: imap.h:1005
boost::future< void > delete_entry(const K &key)
removes entry from map.
Definition: imap.h:188
boost::future< bool > try_lock(const K &key)
Tries to acquire the lock for the specified key.
Definition: imap.h:410
boost::future< bool > evict(const K &key)
Evicts the specified key from this map.
Definition: imap.h:651
boost::future< bool > try_put(const K &key, const V &value, std::chrono::milliseconds timeout)
Tries to put the given key, value into this map within specified timeout value.
Definition: imap.h:222
boost::future< boost::optional< entry_view< K, V > > > get_entry_view(const K &key)
Returns the EntryView for the specified key.
Definition: imap.h:633
boost::future< void > set(const K &key, const V &value, std::chrono::milliseconds ttl)
Puts an entry into this map.
Definition: imap.h:335
boost::future< void > unlock(const K &key)
Releases the lock for the specified key.
Definition: imap.h:478
boost::future< void > put_transient(const K &key, const V &value, std::chrono::milliseconds ttl)
Same as put(K, V, int64_t, TimeUnit) but MapStore, if defined, will not be called to store/persist th...
Definition: imap.h:240
NOTE: paging_predicate can only be used with values(), keySet() and entries() methods!...
Configuration of an index.
Definition: index_config.h:41