Skip to content
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
18 changes: 11 additions & 7 deletions library.c
Original file line number Diff line number Diff line change
Expand Up @@ -1037,18 +1037,17 @@ int redis_cmd_append_sstr(smart_string *str, char *append, int append_len) {
* Append an integer to a smart string command
*/
int redis_cmd_append_sstr_int(smart_string *str, int append) {
char int_buf[32];
int int_len = snprintf(int_buf, sizeof(int_buf), "%d", append);
return redis_cmd_append_sstr(str, int_buf, int_len);
return redis_cmd_append_sstr_long(str, (long) append);
}

/*
* Append a long to a smart string command
*/
int redis_cmd_append_sstr_long(smart_string *str, long append) {
char long_buf[32];
int long_len = snprintf(long_buf, sizeof(long_buf), "%ld", append);
return redis_cmd_append_sstr(str, long_buf, long_len);
char *result = zend_print_long_to_buf(long_buf + sizeof(long_buf) - 1, append);
int int_len = long_buf + sizeof(long_buf) - 1 - result;
return redis_cmd_append_sstr(str, result, int_len);
}

/*
Expand Down Expand Up @@ -3920,10 +3919,15 @@ redis_serialize(RedisSock *redis_sock, zval *z, char **val, size_t *val_len)
break;

default: { /* copy */
zend_string *zstr = zval_get_string(z);
zend_string *zstr = zval_get_string_func(z);
if (ZSTR_IS_INTERNED(zstr)) { // do not reallocate interned strings
*val = ZSTR_VAL(zstr);
*val_len = ZSTR_LEN(zstr);
return 0;
}
*val = estrndup(ZSTR_VAL(zstr), ZSTR_LEN(zstr));
*val_len = ZSTR_LEN(zstr);
zend_string_release(zstr);
zend_string_efree(zstr);
return 1;
}
}
Expand Down
8 changes: 8 additions & 0 deletions redis.c
Original file line number Diff line number Diff line change
Expand Up @@ -1379,6 +1379,14 @@ PHP_METHOD(Redis, pexpiretime) {
REDIS_PROCESS_KW_CMD("PEXPIRETIME", redis_key_cmd, redis_long_response);
}

PHP_METHOD(Redis, expiremember) {
REDIS_PROCESS_CMD(expiremember, redis_long_response);
}

PHP_METHOD(Redis, expirememberat) {
REDIS_PROCESS_CMD(expirememberat, redis_long_response);
}

/* }}} */
/* {{{ proto array Redis::lSet(string key, int index, string value) */
PHP_METHOD(Redis, lSet) {
Expand Down
22 changes: 22 additions & 0 deletions redis.stub.php
Original file line number Diff line number Diff line change
Expand Up @@ -1903,6 +1903,28 @@ public function hVals(string $key): Redis|array|false;
*/
public function hscan(string $key, null|int|string &$iterator, ?string $pattern = null, int $count = 0): Redis|array|bool;

/**
* Set an expiration on a key member (KeyDB only).
*
* @see https://docs.keydb.dev/docs/commands/#expiremember
*
* @param string $key The key to expire
* @param string $field The field to expire
* @param string|null $unit The unit of the ttl (s, or ms).
*/
public function expiremember(string $key, string $field, int $ttl, ?string $unit = null): Redis|int|false;

/**
* Set an expiration on a key membert to a specific unix timestamp (KeyDB only).
*
* @see https://docs.keydb.dev/docs/commands/#expirememberat
*
* @param string $key The key to expire
* @param string $field The field to expire
* @param int $timestamp The unix timestamp to expire at.
*/
public function expirememberat(string $key, string $field, int $timestamp): Redis|int|false;

/**
* Increment a key's value, optionally by a specific amount.
*
Expand Down
29 changes: 25 additions & 4 deletions redis_arginfo.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/* This is a generated file, edit the .stub.php file instead.
* Stub hash: 1cc5fe0df8dfa7d95f2bc45c2383132a68629f24 */
* Stub hash: bacbe6b1d55da4ba6d370fff1090e8de0363c4c2 */

ZEND_BEGIN_ARG_INFO_EX(arginfo_class_Redis___construct, 0, 0, 0)
ZEND_ARG_TYPE_INFO_WITH_DEFAULT_VALUE(0, options, IS_ARRAY, 1, "null")
Expand Down Expand Up @@ -464,6 +464,19 @@ ZEND_BEGIN_ARG_WITH_RETURN_OBJ_TYPE_MASK_EX(arginfo_class_Redis_hscan, 0, 2, Red
ZEND_ARG_TYPE_INFO_WITH_DEFAULT_VALUE(0, count, IS_LONG, 0, "0")
ZEND_END_ARG_INFO()

ZEND_BEGIN_ARG_WITH_RETURN_OBJ_TYPE_MASK_EX(arginfo_class_Redis_expiremember, 0, 3, Redis, MAY_BE_LONG|MAY_BE_FALSE)
ZEND_ARG_TYPE_INFO(0, key, IS_STRING, 0)
ZEND_ARG_TYPE_INFO(0, field, IS_STRING, 0)
ZEND_ARG_TYPE_INFO(0, ttl, IS_LONG, 0)
ZEND_ARG_TYPE_INFO_WITH_DEFAULT_VALUE(0, unit, IS_STRING, 1, "null")
ZEND_END_ARG_INFO()

ZEND_BEGIN_ARG_WITH_RETURN_OBJ_TYPE_MASK_EX(arginfo_class_Redis_expirememberat, 0, 3, Redis, MAY_BE_LONG|MAY_BE_FALSE)
ZEND_ARG_TYPE_INFO(0, key, IS_STRING, 0)
ZEND_ARG_TYPE_INFO(0, field, IS_STRING, 0)
ZEND_ARG_TYPE_INFO(0, timestamp, IS_LONG, 0)
ZEND_END_ARG_INFO()

#define arginfo_class_Redis_incr arginfo_class_Redis_decr

#define arginfo_class_Redis_incrBy arginfo_class_Redis_decrBy
Expand Down Expand Up @@ -1270,6 +1283,8 @@ ZEND_METHOD(Redis, hSetNx);
ZEND_METHOD(Redis, hStrLen);
ZEND_METHOD(Redis, hVals);
ZEND_METHOD(Redis, hscan);
ZEND_METHOD(Redis, expiremember);
ZEND_METHOD(Redis, expirememberat);
ZEND_METHOD(Redis, incr);
ZEND_METHOD(Redis, incrBy);
ZEND_METHOD(Redis, incrByFloat);
Expand Down Expand Up @@ -1526,6 +1541,8 @@ static const zend_function_entry class_Redis_methods[] = {
ZEND_ME(Redis, hStrLen, arginfo_class_Redis_hStrLen, ZEND_ACC_PUBLIC)
ZEND_ME(Redis, hVals, arginfo_class_Redis_hVals, ZEND_ACC_PUBLIC)
ZEND_ME(Redis, hscan, arginfo_class_Redis_hscan, ZEND_ACC_PUBLIC)
ZEND_ME(Redis, expiremember, arginfo_class_Redis_expiremember, ZEND_ACC_PUBLIC)
ZEND_ME(Redis, expirememberat, arginfo_class_Redis_expirememberat, ZEND_ACC_PUBLIC)
ZEND_ME(Redis, incr, arginfo_class_Redis_incr, ZEND_ACC_PUBLIC)
ZEND_ME(Redis, incrBy, arginfo_class_Redis_incrBy, ZEND_ACC_PUBLIC)
ZEND_ME(Redis, incrByFloat, arginfo_class_Redis_incrByFloat, ZEND_ACC_PUBLIC)
Expand Down Expand Up @@ -2027,12 +2044,16 @@ static zend_class_entry *register_class_Redis(void)
zend_string *const_OPT_BACKOFF_CAP_name = zend_string_init_interned("OPT_BACKOFF_CAP", sizeof("OPT_BACKOFF_CAP") - 1, 1);
zend_declare_class_constant_ex(class_entry, const_OPT_BACKOFF_CAP_name, &const_OPT_BACKOFF_CAP_value, ZEND_ACC_PUBLIC, NULL);
zend_string_release(const_OPT_BACKOFF_CAP_name);
#if (PHP_VERSION_ID >= 80200)
#if (PHP_VERSION_ID >= 80000)


zend_add_parameter_attribute(zend_hash_str_find_ptr(&class_entry->function_table, "auth", sizeof("auth") - 1), 0, ZSTR_KNOWN(ZEND_STR_SENSITIVEPARAMETER), 0);
zend_string *attribute_name_SensitiveParameter_func_auth_arg0_0 = zend_string_init_interned("SensitiveParameter", sizeof("SensitiveParameter") - 1, 1);
zend_add_parameter_attribute(zend_hash_str_find_ptr(&class_entry->function_table, "auth", sizeof("auth") - 1), 0, attribute_name_SensitiveParameter_func_auth_arg0_0, 0);
zend_string_release(attribute_name_SensitiveParameter_func_auth_arg0_0);

zend_add_parameter_attribute(zend_hash_str_find_ptr(&class_entry->function_table, "migrate", sizeof("migrate") - 1), 7, ZSTR_KNOWN(ZEND_STR_SENSITIVEPARAMETER), 0);
zend_string *attribute_name_SensitiveParameter_func_migrate_arg7_0 = zend_string_init_interned("SensitiveParameter", sizeof("SensitiveParameter") - 1, 1);
zend_add_parameter_attribute(zend_hash_str_find_ptr(&class_entry->function_table, "migrate", sizeof("migrate") - 1), 7, attribute_name_SensitiveParameter_func_migrate_arg7_0, 0);
zend_string_release(attribute_name_SensitiveParameter_func_migrate_arg7_0);
#endif

return class_entry;
Expand Down
8 changes: 8 additions & 0 deletions redis_cluster.c
Original file line number Diff line number Diff line change
Expand Up @@ -1303,6 +1303,14 @@ PHP_METHOD(RedisCluster, getbit) {
}
/* }}} */

PHP_METHOD(RedisCluster, expiremember) {
CLUSTER_PROCESS_CMD(expiremember, cluster_long_resp, 0);
}

PHP_METHOD(RedisCluster, expirememberat) {
CLUSTER_PROCESS_CMD(expiremember, cluster_long_resp, 0);
}

/* {{{ proto long RedisCluster::setbit(string key, long offset, bool onoff) */
PHP_METHOD(RedisCluster, setbit) {
CLUSTER_PROCESS_CMD(setbit, cluster_long_resp, 0);
Expand Down
10 changes: 10 additions & 0 deletions redis_cluster.stub.php
Original file line number Diff line number Diff line change
Expand Up @@ -495,6 +495,16 @@ public function hmset(string $key, array $key_values): RedisCluster|bool;
*/
public function hscan(string $key, null|int|string &$iterator, ?string $pattern = null, int $count = 0): array|bool;

/**
* @see Redis::expiremember
*/
public function expiremember(string $key, string $field, int $ttl, ?string $unit = null): Redis|int|false;

/**
* @see Redis::expirememberat
*/
public function expirememberat(string $key, string $field, int $timestamp): Redis|int|false;

/**
* @see https://redis.io/commands/hrandfield
*/
Expand Down
25 changes: 22 additions & 3 deletions redis_cluster_arginfo.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/* This is a generated file, edit the .stub.php file instead.
* Stub hash: 5713c5b2f88ddead50088f14026447801120fa33 */
* Stub hash: b9310b607794caa862d509ba316a2a512d2736fe */

ZEND_BEGIN_ARG_INFO_EX(arginfo_class_RedisCluster___construct, 0, 0, 1)
ZEND_ARG_TYPE_INFO(0, name, IS_STRING, 1)
Expand Down Expand Up @@ -416,6 +416,19 @@ ZEND_BEGIN_ARG_WITH_RETURN_TYPE_MASK_EX(arginfo_class_RedisCluster_hscan, 0, 2,
ZEND_ARG_TYPE_INFO_WITH_DEFAULT_VALUE(0, count, IS_LONG, 0, "0")
ZEND_END_ARG_INFO()

ZEND_BEGIN_ARG_WITH_RETURN_OBJ_TYPE_MASK_EX(arginfo_class_RedisCluster_expiremember, 0, 3, Redis, MAY_BE_LONG|MAY_BE_FALSE)
ZEND_ARG_TYPE_INFO(0, key, IS_STRING, 0)
ZEND_ARG_TYPE_INFO(0, field, IS_STRING, 0)
ZEND_ARG_TYPE_INFO(0, ttl, IS_LONG, 0)
ZEND_ARG_TYPE_INFO_WITH_DEFAULT_VALUE(0, unit, IS_STRING, 1, "null")
ZEND_END_ARG_INFO()

ZEND_BEGIN_ARG_WITH_RETURN_OBJ_TYPE_MASK_EX(arginfo_class_RedisCluster_expirememberat, 0, 3, Redis, MAY_BE_LONG|MAY_BE_FALSE)
ZEND_ARG_TYPE_INFO(0, key, IS_STRING, 0)
ZEND_ARG_TYPE_INFO(0, field, IS_STRING, 0)
ZEND_ARG_TYPE_INFO(0, timestamp, IS_LONG, 0)
ZEND_END_ARG_INFO()

ZEND_BEGIN_ARG_WITH_RETURN_OBJ_TYPE_MASK_EX(arginfo_class_RedisCluster_hrandfield, 0, 1, RedisCluster, MAY_BE_STRING|MAY_BE_ARRAY)
ZEND_ARG_TYPE_INFO(0, key, IS_STRING, 0)
ZEND_ARG_TYPE_INFO_WITH_DEFAULT_VALUE(0, options, IS_ARRAY, 1, "null")
Expand Down Expand Up @@ -1135,6 +1148,8 @@ ZEND_METHOD(RedisCluster, hlen);
ZEND_METHOD(RedisCluster, hmget);
ZEND_METHOD(RedisCluster, hmset);
ZEND_METHOD(RedisCluster, hscan);
ZEND_METHOD(RedisCluster, expiremember);
ZEND_METHOD(RedisCluster, expirememberat);
ZEND_METHOD(RedisCluster, hrandfield);
ZEND_METHOD(RedisCluster, hset);
ZEND_METHOD(RedisCluster, hsetnx);
Expand Down Expand Up @@ -1362,6 +1377,8 @@ static const zend_function_entry class_RedisCluster_methods[] = {
ZEND_ME(RedisCluster, hmget, arginfo_class_RedisCluster_hmget, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hmset, arginfo_class_RedisCluster_hmset, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hscan, arginfo_class_RedisCluster_hscan, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, expiremember, arginfo_class_RedisCluster_expiremember, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, expirememberat, arginfo_class_RedisCluster_expirememberat, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hrandfield, arginfo_class_RedisCluster_hrandfield, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hset, arginfo_class_RedisCluster_hset, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hsetnx, arginfo_class_RedisCluster_hsetnx, ZEND_ACC_PUBLIC)
Expand Down Expand Up @@ -1541,10 +1558,12 @@ static zend_class_entry *register_class_RedisCluster(void)
zend_string *const_FAILOVER_DISTRIBUTE_SLAVES_name = zend_string_init_interned("FAILOVER_DISTRIBUTE_SLAVES", sizeof("FAILOVER_DISTRIBUTE_SLAVES") - 1, 1);
zend_declare_class_constant_ex(class_entry, const_FAILOVER_DISTRIBUTE_SLAVES_name, &const_FAILOVER_DISTRIBUTE_SLAVES_value, ZEND_ACC_PUBLIC, NULL);
zend_string_release(const_FAILOVER_DISTRIBUTE_SLAVES_name);
#if (PHP_VERSION_ID >= 80200)
#if (PHP_VERSION_ID >= 80000)


zend_add_parameter_attribute(zend_hash_str_find_ptr(&class_entry->function_table, "__construct", sizeof("__construct") - 1), 5, ZSTR_KNOWN(ZEND_STR_SENSITIVEPARAMETER), 0);
zend_string *attribute_name_SensitiveParameter_func___construct_arg5_0 = zend_string_init_interned("SensitiveParameter", sizeof("SensitiveParameter") - 1, 1);
zend_add_parameter_attribute(zend_hash_str_find_ptr(&class_entry->function_table, "__construct", sizeof("__construct") - 1), 5, attribute_name_SensitiveParameter_func___construct_arg5_0, 0);
zend_string_release(attribute_name_SensitiveParameter_func___construct_arg5_0);
#endif

return class_entry;
Expand Down
19 changes: 18 additions & 1 deletion redis_cluster_legacy_arginfo.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/* This is a generated file, edit the .stub.php file instead.
* Stub hash: 5713c5b2f88ddead50088f14026447801120fa33 */
* Stub hash: b9310b607794caa862d509ba316a2a512d2736fe */

ZEND_BEGIN_ARG_INFO_EX(arginfo_class_RedisCluster___construct, 0, 0, 1)
ZEND_ARG_INFO(0, name)
Expand Down Expand Up @@ -368,6 +368,19 @@ ZEND_BEGIN_ARG_INFO_EX(arginfo_class_RedisCluster_hscan, 0, 0, 2)
ZEND_ARG_INFO(0, count)
ZEND_END_ARG_INFO()

ZEND_BEGIN_ARG_INFO_EX(arginfo_class_RedisCluster_expiremember, 0, 0, 3)
ZEND_ARG_INFO(0, key)
ZEND_ARG_INFO(0, field)
ZEND_ARG_INFO(0, ttl)
ZEND_ARG_INFO(0, unit)
ZEND_END_ARG_INFO()

ZEND_BEGIN_ARG_INFO_EX(arginfo_class_RedisCluster_expirememberat, 0, 0, 3)
ZEND_ARG_INFO(0, key)
ZEND_ARG_INFO(0, field)
ZEND_ARG_INFO(0, timestamp)
ZEND_END_ARG_INFO()

#define arginfo_class_RedisCluster_hrandfield arginfo_class_RedisCluster_getex

#define arginfo_class_RedisCluster_hset arginfo_class_RedisCluster_hincrby
Expand Down Expand Up @@ -977,6 +990,8 @@ ZEND_METHOD(RedisCluster, hlen);
ZEND_METHOD(RedisCluster, hmget);
ZEND_METHOD(RedisCluster, hmset);
ZEND_METHOD(RedisCluster, hscan);
ZEND_METHOD(RedisCluster, expiremember);
ZEND_METHOD(RedisCluster, expirememberat);
ZEND_METHOD(RedisCluster, hrandfield);
ZEND_METHOD(RedisCluster, hset);
ZEND_METHOD(RedisCluster, hsetnx);
Expand Down Expand Up @@ -1204,6 +1219,8 @@ static const zend_function_entry class_RedisCluster_methods[] = {
ZEND_ME(RedisCluster, hmget, arginfo_class_RedisCluster_hmget, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hmset, arginfo_class_RedisCluster_hmset, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hscan, arginfo_class_RedisCluster_hscan, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, expiremember, arginfo_class_RedisCluster_expiremember, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, expirememberat, arginfo_class_RedisCluster_expirememberat, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hrandfield, arginfo_class_RedisCluster_hrandfield, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hset, arginfo_class_RedisCluster_hset, ZEND_ACC_PUBLIC)
ZEND_ME(RedisCluster, hsetnx, arginfo_class_RedisCluster_hsetnx, ZEND_ACC_PUBLIC)
Expand Down
51 changes: 51 additions & 0 deletions redis_commands.c
Original file line number Diff line number Diff line change
Expand Up @@ -6079,6 +6079,57 @@ int redis_expire_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
return SUCCESS;
}

static int
generic_expiremember_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
char *kw, size_t kw_len, int has_unit, char **cmd,
int *cmd_len, short *slot)
{
zend_string *key, *mem, *unit = NULL;
smart_string cmdstr = {0};
zend_long expiry;

ZEND_PARSE_PARAMETERS_START(3, has_unit ? 4 : 3)
Z_PARAM_STR(key)
Z_PARAM_STR(mem)
Z_PARAM_LONG(expiry)
if (has_unit) {
Z_PARAM_OPTIONAL
Z_PARAM_STR_OR_NULL(unit)
}
ZEND_PARSE_PARAMETERS_END_EX(return FAILURE);

redis_cmd_init_sstr(&cmdstr, 3 + (unit != NULL), kw, kw_len);
redis_cmd_append_sstr_key_zstr(&cmdstr, key, redis_sock, slot);
redis_cmd_append_sstr_zstr(&cmdstr, mem);
redis_cmd_append_sstr_long(&cmdstr, expiry);

if (unit != NULL) {
redis_cmd_append_sstr_zstr(&cmdstr, unit);
}

*cmd = cmdstr.c;
*cmd_len = cmdstr.len;

return SUCCESS;
}


int redis_expiremember_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
char **cmd, int *cmd_len, short *slot, void **ctx)
{
return generic_expiremember_cmd(INTERNAL_FUNCTION_PARAM_PASSTHRU,
redis_sock, ZEND_STRL("EXPIREMEMBER"), 1,
cmd, cmd_len, slot);
}

int redis_expirememberat_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
char **cmd, int *cmd_len, short *slot, void **ctx)
{
return generic_expiremember_cmd(INTERNAL_FUNCTION_PARAM_PASSTHRU,
redis_sock, ZEND_STRL("EXPIREMEMBERAT"), 0,
cmd, cmd_len, slot);
}

int
redis_sentinel_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
char *kw, char **cmd, int *cmd_len, short *slot, void **ctx)
Expand Down
6 changes: 6 additions & 0 deletions redis_commands.h
Original file line number Diff line number Diff line change
Expand Up @@ -350,6 +350,12 @@ int redis_xreadgroup_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
int redis_xtrim_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
char **cmd, int *cmd_len, short *slot, void **ctx);

int redis_expiremember_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
char **cmd, int *cmd_len, short *slot, void **ctx);

int redis_expirememberat_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
char **cmd, int *cmd_len, short *slot, void **ctx);

int redis_lmove_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
char *kw, char **cmd, int *cmd_len, short *slot, void **ctx);

Expand Down
Loading
Loading