php - Symfony2 - 安全角色 - 从 PHP 5.3 到 PHP >5.4 - 非对象上的 getRole()

标签 php symfony serialization

我已经看过这个问题了:https://github.com/symfony/symfony/issues/3691

我的问题是我无法找到让它工作的解决方案。

我使用 Symfony 2.8.3

这是我遇到的错误:

FatalErrorException in RoleHierarchy.php line 43: Error: Call to a member function getRole() on a non-object

我正确地序列化了所有内容,这是我的类(class):

用户

<?php
/**
 */

namespace CNAMTS\PHPK\SecurityBundle\Security\User;

use Symfony\Component\Security\Core\User\UserInterface;
use CNAMTS\PHPK\SecurityBundle\Security\Role;

/**
 * Classe abstraite implémentant la classe Symfony UserInterface.
 */
abstract class User implements UserInterface
{
    public function __construct() {
        $this->roles = array();
    }

    /**
     * Concaténation du nom et du numéro d'agent : NOM-NUMERO.
     *
     * @var String
     */
    protected $ismum;
    /**
     * Nom de l'utilisateur.
     *
     * @var String
     */
    protected $nom;
    /**
     * Prénom de l'utilisateur.
     *
     * @var String
     */
    protected $prenom;
    /**
     * Id de l'utilisateur.
     *
     * @var String
     */
    protected $id;
    /**
     * Numéro d'agent.
     *
     * @var String
     */
    protected $chrono;
    /**
     * Code de l'organisme
     *
     * @var String
     */
    protected $codeOrganisme;
    /**
     * Numéro Siret de l'organisme.
     *
     * @var String
     */
    protected $siret;
    /**
     * Services AccessMaster de l'utilisateur.
     *
     * @var array(Symfony\Component\Security\Core\Role\Role)
     */
    protected $roles;
    /**
     * Système de l'utilisateur.
     *
     * @var String
     */
    protected $systeme;

    /**
     * Défini l'Ismum (Concaténation du nom et du numéro d'agent : NOM-NUMERO).
     *
     * @param String $ismum
     */
    public function setIsmum($ismum)
    {
        $this->ismum = $ismum;
    }
    /**
     * Retourne l'Ismum (Concaténation du nom et du numéro d'agent : NOM-NUMERO).
     *
     * @return String
     */
    public function getIsmum()
    {
        return $this->ismum;
    }
    /**
     * Défini le nom de l'utilisateur.
     *
     * @param String $nom
     */
    public function setNom($nom)
    {
        $this->nom = $nom;
    }
    /**
     * Retourne le nom de l'utilisateur.
     *
     * @return String
     */
    public function getNom()
    {
        return $this->nom;
    }
    /**
     * Défini le prénom de l'utilisateur.
     *
     * @param String $prenom
     */
    public function setPrenom($prenom)
    {
        $this->prenom = $prenom;
    }
    /**
     * Retourne le nom de l'utilisateur.
     *
     * @return String
     */
    public function getPrenom()
    {
        return $this->prenom;
    }
    /**
     * Défini l'id de l'utilisateur.
     *
     * @param String $id
     */
    public function setId($id)
    {
        $this->id = $id;
    }
    /**
     * Retourne l'id de l'utilisateur.
     *
     * @return String
     */
    public function getId()
    {
        return $this->id;
    }
    /**
     * Défini le numéro d'agent.
     *
     * @param String $chrono
     */
    public function setChrono($chrono)
    {
        $this->chrono = $chrono;
    }
    /**
     * Retourne le numéro d'agent.
     *
     * @return String
     */
    public function getChrono()
    {
        return $this->chrono;
    }
    /**
     * Défini le code organisme
     * @param String $codeOrganisme
     */
    public function setCodeOrganisme($codeOrganisme)
    {
        $this->codeOrganisme = $codeOrganisme;
    }
    /**
     * Retourne le code organisme
     * @return String
     */
    public function getCodeOrganisme()
    {
        return $this->codeOrganisme;
    }
    /**
     * Défini le SIRET de l'utilisateur.
     *
     * @param String $siret
     */
    public function setSiret($siret)
    {
        $this->siret = $siret;
    }
    /**
     * Retourne le SIRET de l'utilisateur.
     *
     * @return String
     */
    public function getSiret()
    {
        return $this->siret;
    }

    /**
     * Ajoute un service AccessMaster à l'utilisateur.
     *
     * @param String $role
     */
    public function addRole(Role $role)
    {
        $this->roles[] = $role;
    }
    /**
     * Retourne les services AccessMaster de l'utilisateur.
     *
     * @return array(CNAMTS\PHPK\SecurityBundle\Security\Role)
     */
    public function getRoles()
    {
        return $this->roles;
    }

    /**
     * Défini le système de l'utilisateur.
     *
     * @param String $systeme
     */
    public function setSysteme($systeme)
    {
        $this->systeme = $systeme;
    }
    /**
     * Retourne le système de l'utilisateur.
     *
     * @return String
     */
    public function getSysteme()
    {
        return $this->systeme;
    }

    /**
     * @ignore
     */
    public function eraseCredentials()
    {
    }

    /**
     * Permet de tester si deux instances de UserInterface sont égales.
     *
     * @param UserInterface $user
     *
     * @return boolean
     */
    public function equals(UserInterface $user)
    {
        if (!$user instanceof User) {
            return false;
        }

        if ($this->username !== $user->getUsername()) {
            return false;
        }
        if ($this->organisme !== $user->getOrganisme()) {
            return false;
        }
        if ($this->jeton !== $user->getJeton()) {
            return false;
        }

        return true;
    }

    /**
     * Retourne true si l'utilisateur possède le service passé en paramètre
     * Prend en paramètre une chaîne ou un tableau de chaînes.
     *
     * @param mixed $role
     *
     * @return boolean
     */
    public function isGranted($role)
    {
        if (is_array($role)) {
            foreach ($role as $r) {
                foreach ($this->getRoles() as $own) {
                    if ($own->getRole() === $r) {
                        return true;
                    }
                }
            }
        } elseif (is_string($role)) {
            foreach ($this->getRoles() as $own) {
                if ($own->getRole() === $role) {
                    return true;
                }
            }
        }

        return false;
    }

    /**
     * @ignore
     */
    public function getUsername()
    {
        return $this->getIsmum();
    }
    /**
     * @ignore
     */
    public function getPassword()
    {
        return;
    }
    /**
     * @ignore
     */
    public function getSalt()
    {
        return;
    }
}

这个抽象用户的实现

<?php
namespace CNAMTS\PHPK\SecurityBundle\Security\User;

/**
 * Classe décrivant un User lorsque le mode AccessMaster pour la sécurité est activé.
 */
class AccessMasterUser extends User implements \Serializable
{
    public function serialize()
    {
        return \json_encode(array(
            $this->civilite,
            $this->chrono,
            $this->codeOrganisme,
            $this->id,
            $this->ismum,
            $this->nom,
            $this->prenom,
            serialize($this->roles),
            $this->siret,
            $this->systeme
        ));
    }
    public function unserialize($serialized)
    {
        list(
            $this->civilite,
            $this->chrono,
            $this->codeOrganisme,
            $this->id,
            $this->ismum,
            $this->nom,
            $this->prenom,
            $roles,
            $this->siret,
            $this->systeme
        ) = \json_decode($serialized);

        $this->roles = unserialize($roles);
    }

    /**
     * Civilité de l'utilisateur.
     *
     * @var String
     */
    private $civilite;

    /**
     * Défini la civilité de l'utilisateur.
     *
     * @param String $civilite
     */
    public function setCivilite($civilite)
    {
        $this->civilite = $civilite;
    }
    /**
     * Retourne la civilité de l'utilisateur.
     *
     * @return String
     */
    public function getCivilite()
    {
        return $this->civilite;
    }
}

角色

<?php
namespace CNAMTS\PHPK\SecurityBundle\Security;

use Symfony\Component\Security\Core\Role\RoleInterface;

class Role implements RoleInterface, \Serializable
{
    private $role;
    private $attributes;

    public function serialize() {
        return \json_encode(array(
            $this->role,
            $this->attributes
        ));
    }

    public function unserialize($serialized) {
        list(
            $this->role,
            $this->attributes
        ) = \json_decode($serialized);
    }

    /**
     * Constructor.
     *
     * @param string $role The role name
     */
    public function __construct($role, $attributes = array())
    {
        $this->role = (string) $role;
        $this->attributes = $attributes;
    }

    /**
     * {@inheritdoc}
     */
    public function getRole()
    {
        return $this->role;
    }

    /**
     * {@inheritdoc}
     */
    public function getAttributes()
    {
        return $this->attributes;
    }
}

刚刚登陆后,所有角色都ok了,users.roles和roles完全一样:

First page

但是当我转到另一个页面时,我得到了这个:

Second page

我的代码有什么问题? 为什么这适用于 PHP 5.3.3,但不适用于 PHP 5.4.40 或 PHP 5.5.28?

提前致谢,我完全被封锁了。

最佳答案

我认为您的问题的答案在那个链接的错误中,正如 GitHub 用户 Sharom 指出的那样 herehere .

所以看起来问题是你将 User::$roles 包含在 User 类本身的序列化/反序列化中,而你不必这样做.

附言我还认为您使用 json_*() 作为 Serializable 接口(interface)背后的机制很奇怪而且可能不合适。

关于php - Symfony2 - 安全角色 - 从 PHP 5.3 到 PHP >5.4 - 非对象上的 getRole(),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38456858/

相关文章:

php - 带有嵌入图表的 Excel.Application 复制表

java - 静态成员序列化

php - 使用/usr/bin/file判断文件类型?

php - SQL 错误 - 不正确的整数值

Symfony - 在 Controller 中使用参数生成 url

java - GWT + symfony2,我疯了吗?

django - 如何在 Django rest 框架中检索外键字段?

haskell - Cloud Haskell - 如何为闭包编写 "pure"?

php - codeigniter加载一个没有任何html标题的 View 进行打印

PHP: "Declaration of ... should be compatible with that of ..."