我正在使用Symfony 2.2与Doctrine构建一个表单生成器。
我的实体如下:
- WidgetText
- WidgetSelect
我所有的小部件都扩展了下面的类:
/**
* Widget
*
* @ORMMappedSuperclass
*/
abstract class Widget
{
/**
* @var integer
*
* @ORMColumn(name="id", type="integer")
* @ORMId
* @ORMGeneratedValue(strategy="AUTO")
*/
private $id;
/**
* @ORMManyToOne(targetEntity="Form", inversedBy="widgets")
*/
private $form;
/**
* @var string
*
* @ORMColumn(name="type", type="string", length=255)
*/
private $type;
/**
* @var integer
*
* @ORMOneToOne(targetEntity="Question")
*/
private $question;
// getters and setters
}
我的表单实体是这样的:
/**
* Form
*
* @ORMTable(name="form")
* @ORMEntity(repositoryClass="IneatFormGeneratorBundleEntityFormRepository")
* @UniqueEntity("name")
* @UniqueEntity("slug")
*/
class Form
{
/**
* @var integer
*
* @ORMColumn(name="id", type="integer")
* @ORMId
* @ORMGeneratedValue(strategy="AUTO")
*/
private $id;
/**
* @var string
*
* @ORMColumn(name="name", type="string", length=255)
*/
private $name;
/**
* @var string
*
* @ORMColumn(name="slug", type="string", length=255)
*/
private $slug;
/**
* @var ArrayCollection
*
* @ORMOneToMany(targetEntity="Widget", mappedBy="form")
*/
private $widgets;
public function __construct()
{
$this->widgets = new ArrayCollection();
}
// getters and setters
}
和一个Widget实体:
/**
* Widget
*
* @ORMTable(name="widget_choices")
* @ORMEntity
*/
class WidgetChoices extends Widget
{
/**
* @var array
*
* @ORMColumn(type="array")
*/
private $choices;
// getters and setters
}
每当我尝试显示我的表单,我有以下错误:
属性"WidgetText"、方法"getWidgetText()"和方法"isWidgetText()"都不存在于类"IneatFormGeneratorBundleEntityForm"
看起来就像如果我的Widget没有扩展Widget一样。我需要一种方法来将我的小部件转换为Widget,或者一种方法来告诉doctrine我的ArrayCollection可以包含扩展Widget的所有内容。
有可能吗?
Widget
是一个MappedSuperclass(没有表),Form
有一个1-n的键。由于Widget
的每个子类都存在于它自己的表中,所以这不是一个有效的关系。或者换句话说,MappedSuperclass可能没有n-1关系(更像一个装饰器)。
您可以使用通用外键范例来完成您想要的操作,或者对widget
使用单表继承,这更适合您的情况(参考http://docs.doctrine-project.org/en/latest/reference/inheritance-mapping.html#single-table-inheritance)。
table Widget(id, type)
table WidgetXY(id, X, Y)
table WidgetQR(id, Q, R)
一个新的WidgetXY
实体将产生Widget(id=7, type=1)
行和WidgetXY(id=7, X, Y)
行。控制器(原则)将通过使用鉴别器映射来识别引用WidgetXY
的type=1
行,在数据库级别上,您只需针对正确的表pkeys 1-1进行连接。
原则上,你必须将继承类型设置为join,并在注释中定义你的判别符映射(见上面的链接)
hth