Commit Graph

3263 Commits

Author SHA1 Message Date
michael-grunder
38115decb9 Fix VISMEMBER unit test 2025-09-01 09:41:12 -07:00
michael-grunder
b8de91c9e0 Fix errors and a warning
* PHP < 8.0 took a `char*` as `php_json_decode` input, whereas newer
  versions take a const char * so ifdef around this.

* Fix compilation errors due to `false` not being defined. So as to make
  a minimal change we can just use 0 and 1
2025-09-01 09:41:12 -07:00
michael-grunder
92dd256f98 Implement VISMEMBER command. 2025-09-01 09:41:12 -07:00
michael-grunder
c4b2ea6ca5 Fix VEMB reply handling in RedisCluster 2025-09-01 09:41:12 -07:00
michael-grunder
0b4b4ed2c3 Add a test for VGETATTR 2025-09-01 09:41:12 -07:00
michael-grunder
d80b725824 Implement VGETATTR command 2025-09-01 09:41:12 -07:00
michael-grunder
7f9b1f416e Implement VLINKS command 2025-09-01 09:41:12 -07:00
michael-grunder
ea11d62aec Test for VSETATTR 2025-09-01 09:41:12 -07:00
michael-grunder
92716ed0c5 Implement VSETATTR command 2025-09-01 09:41:12 -07:00
michael-grunder
65927b53b1 We can use redis_kv_cmd instead of a specific vrem command. 2025-09-01 09:41:12 -07:00
michael-grunder
5fe188416d Add a test for VRANDMEMBER 2025-09-01 09:41:12 -07:00
michael-grunder
bbae745a93 Add a test for VREM
See #2543
2025-09-01 09:41:12 -07:00
michael-grunder
dc91631b3f Implement VREM command
See #2543
2025-09-01 09:41:12 -07:00
michael-grunder
1deca62841 Implement VRANDMEMBER
`VRANDMEMBER` has the exact same semantics of `SRANDMEMBER` so make
`SRANDMEMBER` a keyword based command and use it for `VRANDMEMBER`.

See #2543
2025-09-01 09:41:12 -07:00
michael-grunder
96378b70fd Implement VEMB and slightly rework VINFO
Unfortunately `VEMB` has a unique `RESP2` reply as far as I can tell,
where it sends the embedding mode (int8, bin, fp32) as a simple string.

This would cause any of PhpRedis' generic reply handlers to turn that
into `true` which isn't useful. For that reason we need a custom reply
handler.

Additionally slightly rework `VINFO` to short circuit and return failure
if we read anything other than a bulk string or an integer reply type.
Otherwise we may get out of sync on the socket.

See #2543
2025-09-01 09:41:12 -07:00
michael-grunder
8f8a49bec2 Tests for VCARD, VDIM, and VINFO. 2025-09-01 09:41:12 -07:00
michael-grunder
0fda9f293b Implement VCARD, VDIM, and VINFO
All of these commands have the same form `<cmd> key`. `VINFO` is a bit
of an outlier however that uses simple strings as opposed to bulk
strings for the key names, meaning we had to create a custom handler.

See #2543
2025-09-01 09:41:12 -07:00
michael-grunder
0ed0fc0562 Add Redis::REDIS_VECTORSET type.
Redis >= 8.0 has a new type `vectorset` that we should support like all
the other types.
2025-08-28 09:34:07 -07:00
michael-grunder
659dc763e0 Refactor redis_replicaof_cmd
It was the last place we were using `REDIS_SPPRINTF` in
`redis_commands.c`.
2025-08-27 16:37:08 -07:00
michael-grunder
8d369f4d62 Implement GEOSEARCH[STORE] BYPOLYGON.
Valkey 9.0.0 implemented a new variant of `GEOSEARCH` where you supply
the verticies to an arbitrary polygon.

Since we can't modify the `geosearch` prototype using it is a little
wonky (you need to just pass empty strings for position and unit).

```php
$redis->geosearch('ca:cities', '', [
    -121.90, 39.65, -121.77, 39.65, -121.77, 39.80, -121.90, 39.80
], '');
$redis->geosearchstore('ca:cities', 'dst', '', [
    -121.90, 39.65, -121.77, 39.65, -121.77, 39.80, -121.90, 39.80
], '');
```
2025-08-24 06:37:51 -07:00
michael-grunder
b1b0c19142 Implement DELIFEQ command
Implement the command and add a test.
2025-08-24 06:37:28 -07:00
Jacob Brown
b0ba827be2 Fixing segfault in cluster_update_slot
When the slot's->slaves was null, it was dereferencing null, causing
segfault.
This happens in weird scenario when some of the nodes in cluster are
down or having changed IP addresses without knowing about it.
2025-08-22 11:59:38 -07:00
Michael Grunder
8685c49c70 Use continue not break if we get a NULL node
This is likely to never happen but just skipping NULL nodes is better than aborting the reset.

Co-authored-by: Pavlo Yatsukhnenko <yatsukhnenko@users.noreply.github.com>
2025-08-21 08:53:51 -07:00
michael-grunder
f4ec5e2bb0 Use ZEND_STRL instead of literal, len 2025-08-21 08:53:51 -07:00
michael-grunder
a0621555b5 Reduce to < 80 chars 2025-08-21 08:53:51 -07:00
michael-grunder
03837f0230 Remove pointless casts
You never have to explicitly cast between `void*` and any other pointer
type.
2025-08-21 08:53:51 -07:00
michael-grunder
7769194757 Change int flags to zend_bool since we only use them as booleans 2025-08-21 08:53:51 -07:00
michael-grunder
9802fc0e46 Rework REDIS_SAVE_CALLBACK to be a function. 2025-08-21 08:53:51 -07:00
michael-grunder
58e1a04f76 Remove wrapper macro which hides branching logic
This wrapper macro implicitly defines an `} else {` block but this is
not clear at the callsite which obsures what is actually going on.

There's no real advantage to the wrapping macro. Instead just call the
underlying macro in an explicit else branch.
2025-08-21 08:53:51 -07:00
michael-grunder
8f0931bbed Rework REDIS_PROCESS_REQUEST to be a function. 2025-08-21 08:53:51 -07:00
michael-grunder
7c953d458b Remove dead legacy code. 2025-08-21 08:53:51 -07:00
michael-grunder
950d2bc79d Rework REDIS_PROCESS_KW_CMD as a function 2025-08-21 08:53:51 -07:00
michael-grunder
601ebbff2b Rework REDIS_PROCESS_CMD into a static function 2025-08-21 08:53:51 -07:00
michael-grunder
c3a7163108 Rework CLUSTER_RESET_MULTI to be a static function 2025-08-21 08:53:51 -07:00
michael-grunder
b004051499 Rewowrk CLUSTER_FREE_QUEUE as a static function 2025-08-21 08:53:51 -07:00
michael-grunder
fae89fa992 Remove dead macro CLUSTER_BUILD_CMD 2025-08-21 08:53:51 -07:00
michael-grunder
f880e1f727 Make CLUSTER_ENQUEUE_RESPONSE a static function 2025-08-21 08:53:51 -07:00
michael-grunder
b90e27f285 Rework CLUSTER_PROCESS_KW_CMD to be a small wrapper macro + function
This commit is similar to the last one reworking processing keyword
commands to work to use a function instead of a big multiline macro.
2025-08-21 08:53:51 -07:00
michael-grunder
1db3908914 Rework CLUSTER_PROCESS_CMD to use an underlying function
In theory this should reduce PhpRedis' code size and likely doesn't
affect performance in a measurable way.
2025-08-21 08:53:51 -07:00
michael-grunder
d564e8cf3c Fix dead assignment 2025-08-21 08:53:51 -07:00
michael-grunder
8be2306e4f Fix several issues surfaced by gcc -fanzlyze
Mostly null pointer derefs or use of uninitialized values. Some were
probably false positives since hte analyzer can't fully reason about how
the zend internals use `zval` structs but the fixes don't really have
any downside.
2025-08-15 07:52:21 -07:00
Michael Grunder
b83981aaeb Rework HEXPIRE test inclusion + bump Valkey (#2684)
* Rework `HEXPIRE` test inclusion + bump Valkey

* Add a little `haveCommand` helper which uses `COMMAND INFO` to check
  if a given server has a specific command. This way when we bump valkey
  to an official release that supports the commands we will start
  testing.
* Bump Valkey from 7.2.5 to 8.1.3 which is much newer.

* Rework `haveCommand` to explicitly check for the command name

COMMAND INFO will return the command name as one of the first bits of
data so we can check for it that way.

* Fix incorrect logic
2025-08-06 10:08:49 -07:00
michael-grunder
6e5faf4226 Refactor EVAL[SHA] command and add a regression test
* We can make the code simpler by using `zend_empty_array` when no args
  are passed as well as the new argument parsing macros and newer internal
  redis command appending functions that take zend strings.

* Add a regression test for when we execute `EVAL[SHA]` with arguments
  but do not send any keys. This was causing UB in RedisCluster (#2681).
2025-08-05 13:20:36 -07:00
michael-grunder
f61e8cd7ba Fix RedisCluster segfault
We were previously only picking a random slot if the user didn't pass
any arguments at all whereas we want to pick a random slot if they don't
pass any *keys*.

This change just universally picks a random slot at the beginning and
then if any keys are processed those keys will override the random
selection.

Fixes #2681
2025-08-05 08:28:43 -07:00
Pavlo Yatsukhnenko
334937cb98 Add PHP 8.5 to CI 2025-08-04 07:39:25 -07:00
michael-grunder
d1d690053f Implement VSIM command
This command is similar to `VADD` in that it's pretty simple but allows
for a great many options.

In it's most basic form:

```php
// To get similarity of a different element
$redis->vsim('myvec', 'some-element');

// To get similarity for a vector of scores
```

As seen above the method attempts to infer element or vector from the
argument passed to $member`. However, since we do serialize the member
when doing `ELE` mode, the user can also specify `ELE` explicitly in the
options array to force an `ELE` search sending serialized values.

```php
$redis->setOption(Redis::OPT_SERIALIZER, Redis::SERIALIZER_PHP);
$redis->vsim('myvec', [3.14, 2.71], ['ELE']);
```

See #2543
2025-07-31 08:30:47 -07:00
michael-grunder
286fa63064 Implement VADD command
This is for Redis 8.0's vector sets.

The command itself can be quite complex with all of the various options but
pretty simple using all defaults.

```php
$redis->vadd('myvec', [3.14, 2.17], 'myelement');
```

The implementation takes a default argument `$options` which can be an array in
order to specify the myriad of other knobs users can send. We just do a bit of
validation on inputs (e.g. certain numeric options must be positive) and make
sure the command is constructed in a valid way (e.g. REDUCE <dim> must come
before the floating point values).

By default we deliver `FP32` blobs but allow the user to send `VALUES` in the
options array which will cause PhpRedis to send N individual values. Sending
values is slower but might be nice for debugging (e.g. watching monitor)

See #2543
2025-07-31 00:57:28 -07:00
Wyatt OʼDay
9cae7815da Make changes requested by @yatsukhnenko 2025-07-30 09:37:32 -07:00
Wyatt OʼDay
d18db84c68 Link to the correct header 2025-07-30 09:37:32 -07:00
Wyatt OʼDay
1e6f5477cb Fix compiling with PHP 8.5.0 alpha3 and newer 2025-07-30 09:37:32 -07:00