Skip to content
This repository has been archived by the owner on Feb 26, 2020. It is now read-only.

Added support for the touch command ... #27

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 38 additions & 8 deletions lib/Client.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -35,10 +35,10 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include <sstream>
#include <string.h>

//#define PRINTMARK() fprintf(stderr, "%s: MARK(%d)\n", __FILE__, __LINE__)
#define PRINTMARK()
//#define PRINTMARK() fprintf(stderr, "%s: MARK(%d)\n", __FILE__, __LINE__)
#define PRINTMARK()

Client::Client (SOCKETDESC *sockdesc)
Client::Client (SOCKETDESC *sockdesc)
: m_writer (1024 * 1200)
, m_reader (1024 * 1200)
{
Expand Down Expand Up @@ -289,6 +289,36 @@ bool Client::prepend(const char *key, size_t cbKey, void *data, size_t cbData, t
return command ("prepend", 7, key, cbKey, data, cbData, expiration, flags, async, maxSize);
}

bool Client::touch(const char *key, size_t cbKey, time_t *expiration, bool async)
{
m_writer.writeChars("touch ", 6);
m_writer.writeChars(key, cbKey);
m_writer.writeChar(' ');
m_writer.writeNumeric(*expiration);
if (async)
{
m_writer.writeChars(" noreply", 8);
}
m_writer.writeChars("\r\n", 2);

if (!sendWriteBuffer())
{
return false;
}

if (async)
{
return true;
}

if (!readLine())
{
return false;
}

return true;
}

bool Client::del(const char *key, size_t cbKey, time_t *expiration, bool async)
{
m_writer.writeChars("delete ", 7);
Expand Down Expand Up @@ -432,7 +462,7 @@ bool Client::version(char **pVersion, size_t *cbVersion)
if (m_reader.readBytes(8) == NULL)
{
return false;
}
}

*pVersion= (char *) m_reader.readUntil(cbVersion, '\r');

Expand Down Expand Up @@ -538,8 +568,8 @@ bool Client::extractErrorFromReader(void)
static const size_t RESPONSE_CLIENT_ERROR_SIZE = strlen(RESPONSE_CLIENT_ERROR);
static const size_t RESPONSE_SERVER_ERROR_SIZE = strlen(RESPONSE_SERVER_ERROR);

if (m_reader.beginsWithString(RESPONSE_ERROR, RESPONSE_ERROR_SIZE) ||
m_reader.beginsWithString(RESPONSE_CLIENT_ERROR, RESPONSE_CLIENT_ERROR_SIZE) ||
if (m_reader.beginsWithString(RESPONSE_ERROR, RESPONSE_ERROR_SIZE) ||
m_reader.beginsWithString(RESPONSE_CLIENT_ERROR, RESPONSE_CLIENT_ERROR_SIZE) ||
m_reader.beginsWithString(RESPONSE_SERVER_ERROR, RESPONSE_SERVER_ERROR_SIZE))
{
size_t cbError = 0;
Expand Down Expand Up @@ -590,10 +620,10 @@ bool Client::getReadNext(char **key, size_t *cbKey, char **data, size_t *cbData,
{
*bError = true;
setError("malformed response: expected VALUE");
m_reader.skip();
m_reader.skip();
return false;
}

*key = (char *) m_reader.readUntil(cbKey, ' ');

if (*key == NULL)
Expand Down
3 changes: 2 additions & 1 deletion lib/Client.h
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ class Client

bool set(const char *key, size_t cbKey, void *data, size_t cbData, time_t expiration, int flags, bool async, size_t maxSize);
bool del(const char *key, size_t cbKey, time_t *expiration, bool async);
bool touch(const char *key, size_t cbKey, time_t *expiration, bool async);
bool add(const char *key, size_t cbKey, void *data, size_t cbData, time_t expiration, int flags, bool async, size_t maxSize);

bool replace(const char *key, size_t cbKey, void *data, size_t cbData, time_t expiration, int flags, bool async, size_t maxSize);
Expand All @@ -94,7 +95,7 @@ class Client
private:
bool command(const char *cmd, size_t cbCmd, const char *key, size_t cbKey, void *data, size_t cbData, time_t expiration, int flags, bool async, size_t maxSize);
bool readLine(void);

void setError(const char *message);
bool extractErrorFromReader(void);

Expand Down
47 changes: 46 additions & 1 deletion python/umemcache.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -696,6 +696,50 @@ PyObject *Client_gets_multi(PyClient *self, PyObject *okeys)
return odict;
}


PyObject *Client_touch(PyClient *self, PyObject *args)
{
char *pResult;
size_t cbResult;
char *pKey;
size_t cbKey;
int expire = -1;
int async = 0;

if (!PyArg_ParseTuple (args, "s#|ib", &pKey, &cbKey, &expire, &async))
{
return NULL;
}

time_t tsExpire = expire;

if (!self->client->touch(pKey, cbKey, (tsExpire == -1) ? NULL : (time_t *) &tsExpire, async ? true : false))
{
if (!PyErr_Occurred())
{
return PyErr_Format(umemcache_MemcachedError, "umemcache: %s", self->client->getError());
}

return NULL;
}

if (!async)
{
if (self->client->getResult(&pResult, &cbResult))
{
return PyString_FromStringAndSize(pResult, cbResult);
}
else
{
return PyErr_Format(umemcache_MemcachedError, "Could not retrieve result");
}
}

Py_RETURN_NONE;
}



PyObject *Client_delete(PyClient *self, PyObject *args)
{
char *pResult;
Expand Down Expand Up @@ -1035,6 +1079,7 @@ static PyMethodDef Client_methods[] = {
{"replace", (PyCFunction) Client_replace, METH_VARARGS, "def replace(self, key, data, expiration = 0, flags = 0, async = False)"},
{"append", (PyCFunction) Client_append, METH_VARARGS, "def append(self, key, data, expiration = 0, flags = 0, async = False)"},
{"prepend", (PyCFunction) Client_prepend, METH_VARARGS, "def prepend(self, key, data, expiration = 0, flags = 0, async = False)"},
{"touch", (PyCFunction) Client_touch, METH_VARARGS, "def touch(self, key, expiration = 0, async = False)"},
{"delete", (PyCFunction) Client_delete, METH_VARARGS, "def delete(self, key, expiration = 0, async = False)"},
{"cas", (PyCFunction) Client_cas, METH_VARARGS, "def cas(self, key, data, cas_unique, expiration = 0, flags = 0, async = False)"},
{"incr", (PyCFunction) Client_incr, METH_VARARGS, "def incr(self, key, increment, async = False)"},
Expand Down Expand Up @@ -1121,6 +1166,6 @@ PyMODINIT_FUNC
PyModule_AddObject(m, "Client", (PyObject *)&ClientType);

umemcache_MemcachedError = PyErr_NewException("umemcache.MemcachedError",
PyExc_RuntimeError, NULL);
PyExc_RuntimeError, NULL);
PyModule_AddObject(m, "MemcachedError", (PyObject *)umemcache_MemcachedError);
}
2 changes: 1 addition & 1 deletion setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@


setup (name = 'umemcache',
version = "1.6.3",
version = "1.6.4",
description = "Ultra fast memcache client written in highly optimized C++ with Python bindings",
long_description = README,
ext_modules = [module1],
Expand Down