yii2 icon indicating copy to clipboard operation
yii2 copied to clipboard

yii\rbac\DbManager serialization issue

Open donny26utama opened this issue 3 years ago • 6 comments

I got this error image

for emergency I solve this with extends yii\rbac\DbManager and overwrite function:

public function getRule($name)
    {
        if ($this->rules !== null) {
            return isset($this->rules[$name]) ? $this->rules[$name] : null;
        }

        $row = (new Query())->select(['data'])
            ->from($this->ruleTable)
            ->where(['name' => $name])
            ->one($this->db);
        if ($row === false) {
            return null;
        }
        $data = $row['data'];
        if (is_resource($data)) {
            $data = stream_get_contents($data);
        }

        return unserialize($data);
    }

to this

public function getRule($name)
    {
        if ($this->rules !== null) {
            return isset($this->rules[$name]) ? $this->rules[$name] : null;
        }

        $row = (new Query())->select(['data' => 'convert_from("data", \'UTF-8\')'])
            ->from($this->ruleTable)
            ->where(['name' => $name])
            ->one($this->db);
        if ($row === false) {
            return null;
        }
        $data = $row['data'];
        if (is_resource($data)) {
            $data = stream_get_contents($data);
        }

        return unserialize($data);
    }

how data stored in auth_rule table: image

any suggestion? why this happens?

Additional info

Q A
Yii version 2.0.40
PHP version 5.6
Operating system MacOS
Postgresql 13.2

donny26utama avatar May 24 '21 15:05 donny26utama

This is well known problem with unserialize and utf8 data. I'm not sure if we can do much about it. Maybe switching to json would be better...

bizley avatar May 24 '21 15:05 bizley

@bizley JSON isn't supported by all DBMS we have.

samdark avatar May 24 '21 20:05 samdark

I was thinking more of a text column with json-encoded data than json column.

But...

I did some testing because I remembered that unserializing issue from way back and I realized everything works... as long as the data is utf8. Then I saw that OP is converting the data to utf8 in the database so this is the reason. While we can easily enforce "encoding" as UTF8 in MySQL (and this is done in RBAC migration) this is not that trivial for other DBs including PostgreSQL. So I think that first of all we should have it mentioned somewhere that UTF8 is really needed for that table, and second - maybe we can have rules not serialized in the DB?

bizley avatar May 25 '21 07:05 bizley

Having rules not serialized sounds interesting. I wonder why we serialize them...

samdark avatar May 25 '21 07:05 samdark

I believe (absolutely no data supporting this statement) that 99% of users are not having rules that require their data to be stored in DB. I think the same applies to the items with additional data property. Anyway, we could have only info, that a rule is used, stored in DB and then just instantiate its object when executing it is required. Having the rule object is required anyway and I cannot image a case where one rule has so many customizations that we need to serialize them and store the snapshots in DB.

Can anyone prove me wrong?

bizley avatar May 25 '21 16:05 bizley

https://github.com/yiisoft/yii2/issues/13501

samdark avatar May 26 '21 22:05 samdark