0

When using a sorted set and doing a zScan call on it, I get a Notice for Array to String conversion and I do wonder where that comes from. Does anyone have an idea?

This is the code:

$redis = new Redis();
$redis->connect('127.0.0.1');
$redis->setOption(Redis::OPT_SERIALIZER, Redis::SERIALIZER_PHP);
$redis->zAdd('check', 0, array('a'));
$it = NULL;
$redis->zScan('check', $it);

Tried that with Redis::SERIALIZER_IGBINARY too but got the same results. It must be the value set because if I do a $redis->zAdd('check', 0,'a'); everything is fine.

I am using PHP 7.1.12 with php-redis 3.1.4

4thfloorstudios
  • 388
  • 1
  • 6
  • 16

1 Answers1

0

PHP doesn't allow array keys to be arrays. The following script will cause an illegal offset type error.

<?php
$array = [
    ['one'] => 0,
    ['two'] => 1
];
?>

A few phpredis commands "zip" the responses which means the actual Redis reply of [key, value, key, value] is turned into the PHP like associative array [key => value, key => value].

You're running into this problem with zScan as internally when it is attempting to zip the values, PHP is forced to use the value "Array" as an array key cannot be an array.

You would see the same problem if you tried to do this:

$redis->zRange('check', 0, -1, true);

I didn't step through the code but my guess is that the problem happens precisely here.

I don't know anything about what you're trying to build, so it's difficult to say what a proper workaround might be. You can always disable serialization before attempting to execute ZSCAN or ZRANGE WITHSCORES but then you'd need to deal with the serialized data manually.

  • I do not add an array as key but as a value. 'check' is the key. According to https://github.com/phpredis/phpredis#zadd the value can only be a string. I am using hSet now which works even with arrays which are serialized before setting. Thanks for your answer! – 4thfloorstudios Jan 04 '18 at 11:12
  • Yes, a serialized array as the ZSET member, and if you run `zScan` on that set, phpredis attempts to return `[member => score]`. Your member is a serialized array, so it attempts to unserialize the array and use it as an array key, which is illegal. I wrote that part of phpredis. Glad you got it working! :) – Michael Grunder Jan 04 '18 at 19:34