libmemcached: add MEMCACHED_BEHAVIOR_META_PROTOCOL
[awesomized/libmemcached] / test / lib / MemcachedCluster.cpp
1 #include "MemcachedCluster.hpp"
2 #include "Retry.hpp"
3
4 const memcached_st MemcachedCluster::empty_memc{};
5
6 void MemcachedCluster::init() {
7 REQUIRE(cluster.start());
8
9 while (!cluster.ensureListening()) {
10 cluster.restart();
11 }
12
13 if (auto br = getenv_else("MEMCACHED_BREAK", "0")) {
14 if (*br && *br != '0') {
15 string in;
16
17 cout << "Started servers:\n";
18 for (const auto &server : cluster.getServers()) {
19 cout << server.getPid() << " ";
20 }
21 cout << "\nPress ENTER to continue... " << ::flush;
22 cin.get();
23 }
24 }
25
26 REQUIRE(memcached_create(&memc));
27
28 for (const auto &[behavior, value] : to_set) {
29 REQUIRE(MEMCACHED_SUCCESS == memcached_behavior_set(&memc, behavior, value));
30 }
31
32 for (const auto &server : cluster.getServers()) {
33 auto target = server.getSocketOrPort();
34 if (holds_alternative<string>(target)) {
35 REQUIRE(MEMCACHED_SUCCESS == memcached_server_add_unix_socket(&memc, get<string>(target).c_str()));
36 } else {
37 REQUIRE(MEMCACHED_SUCCESS == memcached_server_add(&memc, "localhost", get<int>(target)));
38 }
39 }
40
41 }
42
43 MemcachedCluster::~MemcachedCluster() {
44 if (!!memcmp(&memc, &empty_memc, sizeof(memc))) {
45 memcached_free(&memc);
46 }
47 }
48
49 void MemcachedCluster::flush() {
50 REQUIRE(MEMCACHED_SUCCESS == memcached_flush(&memc, 0));
51 }
52
53 MemcachedCluster::MemcachedCluster()
54 : cluster{Server{
55 MEMCACHED_BINARY,
56 {random_socket_or_port_arg()}
57 }}
58 {
59 init();
60 }
61
62 MemcachedCluster::MemcachedCluster(Cluster &&cluster_, behaviors_t to_set_)
63 : cluster{move(cluster_)}
64 , to_set{move(to_set_)}
65 {
66 init();
67 }
68
69 MemcachedCluster::MemcachedCluster(MemcachedCluster &&mc) noexcept
70 : cluster{Server{}}
71 {
72 *this = move(mc);
73 }
74
75 MemcachedCluster &MemcachedCluster::operator=(MemcachedCluster &&mc) noexcept {
76 cluster = move(mc.cluster);
77 memcached_clone(&memc, &mc.memc);
78 returns = &memc;
79 return *this;
80 }
81
82 MemcachedCluster MemcachedCluster::mixed() {
83 return MemcachedCluster{};
84 }
85
86 MemcachedCluster MemcachedCluster::network() {
87 return MemcachedCluster{Cluster{Server{
88 MEMCACHED_BINARY,
89 {"-p", random_socket_or_port_string}
90 }}};
91 }
92
93 MemcachedCluster MemcachedCluster::socket() {
94 return MemcachedCluster{Cluster{Server{
95 MEMCACHED_BINARY,
96 {"-s", random_socket_or_port_string}
97 }}};
98 }
99
100 MemcachedCluster MemcachedCluster::udp() {
101 return MemcachedCluster{Cluster{Server{
102 MEMCACHED_BINARY,
103 {
104 Server::arg_pair_t{"-U", random_socket_or_port_string},
105 Server::arg_t{"-v"}
106 }
107 }}, {
108 {MEMCACHED_BEHAVIOR_USE_UDP, 1}
109 }};
110 }
111
112 #if LIBMEMCACHED_WITH_SASL_SUPPORT
113 MemcachedCluster MemcachedCluster::sasl() {
114 auto mc = MemcachedCluster{Cluster{Server{
115 MEMCACHED_BINARY,
116 {
117 Server::arg_pair_t{"-p", random_socket_or_port_string},
118 Server::arg_t{"-S"}
119 }
120 }}, {
121 {MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 1},
122 }};
123 REQUIRE(MEMCACHED_SUCCESS == memcached_set_sasl_auth_data(&mc.memc,
124 "memcached", "memcached"));
125 return mc;
126 }
127 #endif
128
129 void MemcachedCluster::enableBinaryProto(bool enable) {
130 REQUIRE(MEMCACHED_SUCCESS == memcached_behavior_set(&memc,
131 MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, enable));
132 }
133
134 void MemcachedCluster::enableMetaProto(bool enable) {
135 REQUIRE(MEMCACHED_SUCCESS == memcached_behavior_set(&memc,
136 MEMCACHED_BEHAVIOR_META_PROTOCOL, enable));
137 }
138
139 void MemcachedCluster::enableBuffering(bool enable) {
140 REQUIRE(MEMCACHED_SUCCESS == memcached_behavior_set(&memc,
141 MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, enable));
142 }
143
144 void MemcachedCluster::enableReplication() {
145 REQUIRE(MEMCACHED_SUCCESS == memcached_behavior_set(&memc,
146 MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS, memcached_server_count(&memc) - 1));
147 }
148
149 void MemcachedCluster::killOneServer() const {
150 const auto &servers = cluster.getServers();
151 const auto &victim = servers[random_num((size_t)0, servers.size() - 1)];
152 ::kill(victim.getPid(), SIGKILL);
153 }
154
155 bool MemcachedCluster::isGEVersion(uint8_t major, uint8_t minor, uint8_t micro) {
156 REQUIRE(MEMCACHED_SUCCESS == memcached_version(&memc));
157 auto inst = memcached_server_instance_by_position(&memc, 0);
158 auto maj = memcached_server_major_version(inst);
159 auto min = memcached_server_minor_version(inst);
160 auto mic = memcached_server_micro_version(inst);
161
162 return (maj > major)
163 || (maj == major && min > minor)
164 || (maj == major && min == minor && mic >= micro);
165 }