awesomized / libmemcached

Resurrection of libmemcached
https://awesomized.github.io/libmemcached/
BSD 3-Clause "New" or "Revised" License
45 stars 26 forks source link

memcached_get return NOT FOUND for exists key after buffered delete/increment #142

Open degtyaryov opened 9 months ago

degtyaryov commented 9 months ago

For command DeleteQ and IncrementQ server memcached return answer:

Memcache Protocol, Delete Quietly Response
    Magic: Response (129)
    Opcode: Delete Quietly (20)
    Key Length: 0
    Extras length: 0
    Data type: Raw bytes (0)
    Status: Key not found (1)
        [Expert Info (Note/Response): Delete Quietly: Key not found]
            [Delete Quietly: Key not found]
            [Severity level: Note]
            [Group: Response]
    [Value length: 9]
    Total body length: 9
    Opaque: 1835008
    CAS: 0
    Value: Not found
Memcache Protocol, Increment Quietly Response
    Magic: Response (129)
    Opcode: Increment Quietly (21)
    Key Length: 0
    Extras length: 0
    Data type: Raw bytes (0)
    Status: Unknown (6)
        [Expert Info (Note/Response): Increment Quietly: Status: 6]
            [Increment Quietly: Status: 6]
            [Severity level: Note]
            [Group: Response]
    [Value length: 46]
    Total body length: 46
    Opaque: 262144
    CAS: 0
    Value: Non-numeric server-side value for incr or decr

For next request GET response exists in TCP package:

Memcache Protocol, Get Key Response
    Magic: Response (129)
    Opcode: Get Key (12)
    Key Length: 4
    Extras length: 4
    Data type: Raw bytes (0)
    Status: No error (0)
    [Value length: 6]
    Total body length: 14
    Opaque: 3473408
    CAS: 365468
    Extras
        Flags: 0x00000000
    Key: KEY1
    Value: VALUE1

But libmemcached return NOT FOUND

memcached_mget loses all results for all keys.

Environment:

Example for delete:

#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <libmemcached/memcached.h>

int main(int argc, char *argv[])
{
    char *key1= "KEY1";
    char *value1= "VALUE1";

    char *key2= "KEY2";
    char *value2= "VALUE2";

    memcached_server_st *servers = NULL;
    memcached_st *memc;
    memcached_return rc;

    size_t key1_length = strlen(key1);
    size_t key2_length = strlen(key2);

    char *return_value;
    size_t return_value_length;
    uint32_t flags;

    memcached_server_st *memcached_servers_parse (const char *server_strings);

    memc= memcached_create(NULL);

    servers= memcached_server_list_append(servers, "127.0.0.1", 11211, &rc);
    rc= memcached_server_push(memc, servers);

    memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 1);
    memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 1);

    rc= memcached_set(memc, key1, key1_length, value1, strlen(value1), (time_t)0, (uint32_t)0);

    memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, 1);
    memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NOREPLY, 1);

    for (int i = 0; i < 100; ++i) {
        rc= memcached_delete(memc, key2, key2_length, (time_t)0);
    }

    return_value = memcached_get(memc, key1, key1_length, &return_value_length, &flags, &rc);
    fprintf(stdout,"Value: %s\n",return_value);

Example for increment:

#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <libmemcached/memcached.h>

int main(int argc, char *argv[])
{
    char *key= "KEY";
    char *value= "VALUE";

    memcached_server_st *servers = NULL;
    memcached_st *memc;
    memcached_return rc;

    uint64_t incr = UINT64_MAX;
    size_t key_length = strlen(key);

    char return_key[MEMCACHED_MAX_KEY];
    size_t return_key_length;
    char *return_value;
    size_t return_value_length;
    uint32_t flags;

    const char* keys[] = {key};
    size_t keys_length[] = {key_length};

    memcached_server_st *memcached_servers_parse (const char *server_strings);

    memc= memcached_create(NULL);

    servers= memcached_server_list_append(servers, "127.0.0.1", 11211, &rc);
    rc= memcached_server_push(memc, servers);

    memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 1);
    memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 1);
    memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, 1);
    memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NOREPLY, 1);

    rc= memcached_set(memc, key, key_length, value, strlen(value), (time_t)0, (uint32_t)0);
    rc = memcached_increment_with_initial(memc, key, key_length, 1, 1, (time_t)600, &incr);

    rc = memcached_mget(memc, keys, keys_length, 1);

    return_value = memcached_fetch(memc, return_key, &return_key_length, &return_value_length, &flags, &rc);
    fprintf(stdout,"Value: %s\n",return_value);

    return_value = memcached_fetch(memc, return_key, &return_key_length, &return_value_length, &flags, &rc);
    fprintf(stdout,"Value: %s\n",return_value);

    memcached_quit(memc);

    return 0;
}

https://github.com/php-memcached-dev/php-memcached/issues/554