#include <string.h>
+#include <sstream>
#include <string>
#include <vector>
#include <map>
Memcache()
:
+ servers_list(),
memc(),
+ servers(NULL),
result()
{
memcached_create(&memc);
}
+ Memcache(const std::string &in_servers_list)
+ :
+ servers_list(in_servers_list),
+ memc(),
+ servers(NULL),
+ result()
+ {
+ memcached_create(&memc);
+ servers= memcached_servers_parse(servers_list.c_str());
+ memcached_server_push(&memc, servers);
+ }
+
+ Memcache(const std::string &hostname,
+ unsigned int port)
+ :
+ servers_list(),
+ memc(),
+ servers(NULL),
+ result()
+ {
+ memcached_create(&memc);
+ servers_list.append(hostname);
+ servers_list.append(":");
+ std::ostringstream strsmt;
+ strsmt << port;
+ servers_list.append(strsmt.str());
+ servers= memcached_servers_parse(servers_list.c_str());
+ memcached_server_push(&memc, servers);
+ }
+
Memcache(memcached_st *clone)
:
+ servers_list(),
memc(),
+ servers(NULL),
result()
{
memcached_clone(&memc, clone);
Memcache(const Memcache &rhs)
:
+ servers_list(rhs.servers_list),
memc(),
+ servers(NULL),
result()
{
memcached_clone(&memc, const_cast<memcached_st *>(&rhs.getImpl()));
+ servers= memcached_servers_parse(servers_list.c_str());
+ memcached_server_push(&memc, servers);
+ }
+
+ Memcache &operator=(const Memcache &rhs)
+ {
+ if (this != &rhs)
+ {
+ memcached_clone(&memc, const_cast<memcached_st *>(&rhs.getImpl()));
+ servers= memcached_servers_parse(servers_list.c_str());
+ memcached_server_push(&memc, servers);
+ }
+ return *this;
}
~Memcache()
{
memcached_free(&memc);
+ memcached_server_list_free(servers);
}
/**
return memcached_strerror(NULL, rc);
}
+ /**
+ * Return the string which contains the list of memcached servers being
+ * used.
+ *
+ * @return a std::string containing the list of memcached servers
+ */
+ const std::string getServersList() const
+ {
+ return servers_list;
+ }
+
+ /**
+ * Set the list of memcached servers to use.
+ *
+ * @param[in] in_servers_list list of servers
+ * @return true on success; false otherwise
+ */
+ bool setServers(const std::string &in_servers_list)
+ {
+ servers_list.assign(in_servers_list);
+ servers= memcached_servers_parse(in_servers_list.c_str());
+ memcached_server_push(&memc, servers);
+ return (servers == NULL);
+ }
+
+ /**
+ * Add a server to the list of memcached servers to use.
+ *
+ * @param[in] server_name name of the server to add
+ * @param[in] port port number of server to add
+ * @return true on success; false otherwise
+ */
+ bool addServer(const std::string &server_name, unsigned int port)
+ {
+ memcached_return rc;
+ std::ostringstream strstm;
+ servers_list.append(",");
+ servers_list.append(server_name);
+ servers_list.append(":");
+ strstm << port;
+ servers_list.append(strstm.str());
+ servers= memcached_server_list_append(servers,
+ server_name.c_str(),
+ port,
+ &rc);
+ memcached_server_push(&memc, servers);
+ return (rc == MEMCACHED_SUCCESS);
+ }
+
+ /**
+ * Remove a server from the list of memcached servers to use.
+ *
+ * @param[in] server_name name of the server to remove
+ * @param[in] port port number of server to remove
+ * @return true on success; false otherwise
+ */
+ bool removeServer(const std::string &server_name, size_t port)
+ {
+ std::string tmp_str;
+ std::ostringstream strstm;
+ tmp_str.append(",");
+ tmp_str.append(server_name);
+ tmp_str.append(":");
+ strstm << port;
+ tmp_str.append(strstm.str());
+ memcached_server_st *server= memcached_servers_parse(tmp_str.c_str());
+ memcached_return rc= memcached_server_remove(server);
+ return (rc == MEMCACHED_SUCCESS);
+ }
+
/**
* Fetches an individual value from the server. mget() must always
* be called before using this method.
ret_val.reserve(value_length);
ret_val.assign(value, value + value_length);
key.assign(ret_key);
+ free(value);
+ }
+ else if (value)
+ {
+ free(value);
}
+
return rc;
}
{
ret_val.reserve(value_length);
ret_val.assign(value, value + value_length);
+ free(value);
return true;
}
return false;
{
ret_val.reserve(value_length);
ret_val.assign(value, value + value_length);
+ free(value);
return true;
}
return false;
retval= set(it->first, it->second, expiration, flags);
if (retval == false)
{
- char err_buff[64];
- sprintf(err_buff, "There was an error setting the key %s",
- it->first.c_str());
+ std::string err_buff("There was an error setting the key ");
+ err_buff.append(it->first);
throw(Error(err_buff, false));
}
++it;
return version;
}
+ /**
+ * Retrieve memcached statistics. Populate a std::map with the retrieved
+ * stats. Each server will map to another std::map of the key:value stats.
+ *
+ * @param[out] stats_map a std::map to be populated with the memcached
+ * stats
+ * @return true on success; false otherwise
+ */
+ bool getStats(std::map< std::string, std::map<std::string, std::string> >
+ &stats_map)
+ {
+ memcached_return rc;
+ memcached_stat_st *stats= memcached_stat(&memc, NULL, &rc);
+
+ if (rc != MEMCACHED_SUCCESS &&
+ rc != MEMCACHED_SOME_ERRORS)
+ {
+ return false;
+ }
+
+ uint32_t server_count= memcached_server_count(&memc);
+
+ /*
+ * For each memcached server, construct a std::map for its stats and add
+ * it to the std::map of overall stats.
+ */
+ for (uint32_t x= 0; x < server_count; x++)
+ {
+ std::ostringstream strstm;
+ std::string server_name(memcached_server_name(&memc, servers[x]));
+ server_name.append(":");
+ strstm << memcached_server_port(&memc, servers[x]);
+ server_name.append(strstm.str());
+
+ std::map<std::string, std::string> server_stats;
+ char **list= NULL;
+ char **ptr= NULL;
+
+ list= memcached_stat_get_keys(&memc, &stats[x], &rc);
+ for (ptr= list; *ptr; ptr++)
+ {
+ char *value= memcached_stat_get_value(&memc, &stats[x], *ptr, &rc);
+ server_stats[*ptr]= value;
+ free(value);
+ }
+
+ stats_map[server_name]= server_stats;
+ free(list);
+ }
+
+ memcached_stat_free(&memc, stats);
+ return true;
+ }
+
private:
+ std::string servers_list;
memcached_st memc;
+ memcached_server_st *servers;
memcached_result_st result;
};