【问题标题】:Doctrine - Database representationDoctrine - 数据库表示
【发布时间】:2018-04-19 10:31:42
【问题描述】:

我尝试了几乎所有方法来制作代表我的数据库架构的实体,但仍然出现整页错误。如果有人能给我一些启发,我将不胜感激。

基本上我们有 2 份注册表,一份用于品牌,一份用于影响者。在每个表单中,我们都要求提供用户信息以及具体信息,具体取决于您所在的表单页面。

数据库架构:

  • 角色(此表已经填充了他们的“类型”,管理员、品牌或影响者)

标识 | 名字

  • 用户(此表包含一个人的一般信息,电子邮件和密码将用于登录)

标识 | id_role FK| 姓名 | 电话 | 电子邮件 | 密码 | created_at | 状态

  • 品牌(此表包含使用品牌表格进行注册的品牌的具体信息)

标识 | user_id FK| name_brand | position_id | 电子邮件品牌 | nif_brand | name_firma | 手机品牌 |

  • 职位(此表已填入我们显示的要选择的职位,例如 CEO)

标识 | 名字

  • 地区(此表已填充了我们显示的要选择的地区,例如 NJ)

标识 | 名字

  • 影响者(此表包含使用品牌形式注册的影响者的具体信息)

标识 | user_id FK | 姓氏 | 出生日期 | 电子邮件品牌 | District_id FK | 性别

要点:

我已经尝试使用 Doctrine 注释,但仍然没有为我工作,不确定是因为我是新手,还是我没有正确构建数据库/实体,甚至没有管理一个实体及其与数据库的关联.

这个想法是一个用户/个人可以是品牌或影响者。这是通过链接到角色表的 role_id 来实现的。例如,如果我在品牌表单中并尝试添加我的信息,它将在用户表中添加个人信息并使用 role_id 2 链接到角色表。然后,将使用用户 PRIMARY KEY 链接两个表,将给出的特定品牌信息插入到表 BRAND 中。 (不确定这里是否有错误,也许用户应该通过角色表并从该表到特定表,这不是我现在正在做的)。在 BRAND 表中,我询问它的信息,并以我获取 FK position_id 并将其链接到表 POSITION 的形式来自 POSITION SELECT。

影响者发生了不同但相似的事情,它将选择他的地区,然后我使用该 District_id 来链接地区表。

问题始终是我需要在实体中定义的与学说和属性的外键关联。我已经没有声明外键,因为我知道教义使用对象在内部处理 FK 关系,但不能使它起作用..

非常感谢你们可以分享的所有帮助。 谢谢。

【问题讨论】:

  • 你看过继承吗?特别是 CTISTI Doctrine?
  • @rkeet 我实际上没有!最合适的方式似乎是CTI
  • 嗨鲁本,最近怎么样?我的回答对你有帮助吗?

标签: mysql sql zend-framework doctrine-orm zend-framework3


【解决方案1】:

我认为您正在尝试手动执行 Doctrine 可以通过继承提供的功能。

一个小的设置应该与您对您正在尝试做的事情的描述一致。

通用用户设置

/**
 * @ORM\Table(name="users")
 * @ORM\Entity
 *
 * @ORM\MappedSuperclass

 * @ORM\InheritanceType("JOINED")
 * @ORM\DiscriminatorColumn(name="discr", type="string")
 */
class User 
{
    /**
     * @var int
     * @ORM\Id
     * @ORM\Column(name="id", type="integer")
     * @ORM\GeneratedValue(strategy="IDENTITY")
     */
    protected $id;

    /**
     * @var string
     * @ORM\Column(name="name", type="string", length=255, nullable=false, unique=true)
     */
    protected $name;

    /**
     * @var Position
     * @ORM\OneToOne(...)
     */
    protected $position; // TODO

    // getters/setters & other properties
}

品牌用户

/**
 * @ORM\Table(name="brands")
 * @ORM\Entity
 */
class BrandUser extends User
{
    /**
     * @var string
     * @ORM\Column(name="specific_brand_property", type="string", length=255, nullable=false, unique=false)
     */
    protected $specificBrandProperty;

    // getters/setters & other properties
}

这个小设置应该已经为您提供了 2 个实体对象:UserBrandUser,后者扩展了第一个。

BrandUser 的主键是 User 的外键,User 的要求也是 BrandUser 的要求。

如果您使用 Fieldset 和 InputFilter 类,您可以让 BrandUserFieldset 扩展 Fieldset 以在您的表单中使用(下面的示例和 more info 在我关于此主题的一个回购中)

class UserFieldset
{
    public function init()
    {
        parent::init();

        $this->add([
            'name' => 'id',
            'required' => true,
            'type' => Hidden::class,
        ]);

        $this->add([
            'name' => 'name',
            'required' => true,
            'type' => Text::class,
            'options' => [
                'label' => 'Name',
            ],
        ]);

        $this->add([
            'name' => 'position',
            'required' => true,
            'type' => ObjectSelect::class,
            // other properties
        ]);
    }
}

扩展为BrandUser

class BrandUserFieldset extends UserFieldset
{
    public function init()
    {
        parent::init(); // <-- adds id, name, position

        $this->add([
            'name' => 'specificBrandProperty',
            'required' => true,
            'type' => Text::class,
            'options' => [
                'label' => 'Name',
            ],
        ]);
    }
}

想添加一些命令,他们可能会帮助你。我的设置要求我在命令前加上 ./vendor/bin/doctrine-module,将设置所需的内容添加到以下内容:

  • orm:validate-schema - 将检查您的 Doctrine Annotation 是否有错误。还将返回它发现的任何错误(语法和逻辑)
  • orm:schema-tool:update - 创建/更新数据库模式的命令
    • 标记-f - 将使:update 真正执行
    • 标记--dump-sql 将使:update 执行,但将 SQL 转储到终端中
    • 标志-f--dump-sql 可以组合
  • orm:mapping:describe “\Full\Namespace\To\Entity” - 显示 Doctrine 关于特定实体的所有信息 - 包括关系、关系映射、鉴别器、扩展(子)和父实体等

另外,有一个look at a solution 我前段时间遇到过类似的问题。

【讨论】:

  • 非常感谢您的时间和回答!我还有一个疑问,实际上在通用用户中我应该将数据库中使用的属性添加为 FK 吗?不确定我是否想错了,但我不能在通用用户上获得位置,因为当我创建类 InfluencerUser extends User 时,它将有一个位置,并且该位置是特定于品牌的。您的意思是 ROLE,因此每个用户都有特定的角色吗?
  • Primary Key 标识符是属性id。当像这样扩展一个类并使用鉴别器时,唯一的id 属性设置在最顶层的类上。在此示例中,主键 id 位于 users 表中(id 属性)。 BrandUser 使用的 idUser 实体的外键。
  • 我添加了positionspecificBrandProperty属性作为示例,供您填写自己的属性。如果您仅在 InfluencerUser 实体中而不在 BrandUser 中拥有自己的 position 属性,那么是的,您应该将我的示例属性移动到您的 InfluencerUser 实体中。使用继承时,“以上”属性应该对所有子类都可用(并且相关!)。如果它们不相关,则它们都处于错误的级别或错误的实体中。
  • 我会仔细看看一切,非常感谢!
猜你喜欢
  • 2013-10-27
  • 2015-04-22
  • 2014-06-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多