标识符中的 Doctrine 2 ORM DateTime 字段 [英] Doctrine 2 ORM DateTime field in identifier
问题描述
在我们的数据库表中,我们的 refID
和 date
列是一个复合主键,标识符的一个字段被映射为一个 datetime
:
In our DB tables, we columns refID
and date
are a composite primary key, with one field of the identifier being mapped as a datetime
:
class corpWalletJournal
{
/**
* @ORMColumn(name="refID", type="bigint", nullable=false)
* @ORMId
* @ORMGeneratedValue(strategy="NONE")
*/
private $refID;
/**
* @ORMColumn(name="date", type="datetime", nullable=false)
* @ORMId
* @ORMGeneratedValue(strategy="NONE")
*/
private $date;
public function setRefID($refID)
{
$this->refID = $refID;
}
public function setDate(DateTime $date)
{
$this->date = $date;
}
}
如果我们在实体中将它们描述为@ORMId,此代码将返回异常无法将日期时间转换为字符串"...
If we describe them in entity as @ORMId this code will return exception "cannot convert datetime to string"...
$filter = array(
'date' => $this->stringToDate($loopData['date']),
'refID' => $loopData['refID']
));
$oCorpWJ = $this->em->getRepository('EveDataBundle:corpWalletJournal')->findOneBy($filter);
// ...
$oCorpWJ->setDate($this->stringToDate($loopData['date']));
// ...
如果我们将 corpWalletJournal#date
描述为一个简单的列,代码工作正常.为什么?
If we describe corpWalletJournal#date
as a simple column, code works fine. Why?
我们该如何处理?我们需要在主键中同时具有 date
和 refID
.
How can we deal with it? We need to have both date
and refID
in the primary key.
添加:
所以我创建了一个新类
use DateTime;
class DateTimeEx extends DateTime
{
public function __toString()
{
return $this->format('Y-m-d h:i:s');
}
}
和它的新类型
use DoctrineDBALTypesType;
use DoctrineDBALPlatformsAbstractPlatform;
use EveDataBundleEntityTypeDateTimeEx;
class DateTimeEx extends Type
{
const DateTimeEx = 'datetime_ex';
public function getSQLDeclaration(array $fieldDeclaration, AbstractPlatform $platform)
{
return 'my_datetime_ex';
}
public function convertToPHPValue($value, AbstractPlatform $platform)
{
return new DateTimeEx($value);
}
public function convertToDatabaseValue($value, AbstractPlatform $platform)
{
return $value->format('Y-m-d h:i:s');
}
public function getName()
{
return self::DateTimeEx;
}
public function canRequireSQLConversion()
{
return true;
}
}
如何在实体中使用它们?
How can i use them in entity?
我的(编辑过的)类型类
My (edited) Type Class
use DoctrineDBALTypesType;
use DoctrineDBALPlatformsAbstractPlatform;
class DateTimeEx extends Type
{
const DateTimeEx = 'datetime_ex';
public function getSQLDeclaration(array $fieldDeclaration, AbstractPlatform $platform)
{
return 'my_datetime_ex';
}
public function convertToPHPValue($value, AbstractPlatform $platform)
{
return $value;
}
public function convertToDatabaseValue($value, AbstractPlatform $platform)
{
return $value;
}
public function getName()
{
return self::DateTimeEx;
}
}
推荐答案
Doctrine 2 ORM 需要将 UnitOfWork
.这是让 EntityManager
能够跟踪对象更改所必需的.
Doctrine 2 ORM needs to convert identifier fields to strings in the UnitOfWork
. This is required to have the EntityManager
being able to track changes to your objects.
因为 DateTime
类型的对象本身不实现方法 __toString
,将它们转换为字符串并不像将它们转换为字符串那么简单.
Since objects of type DateTime
don't natively implement method __toString
, converting them to strings is not as simple as casting them to strings.
因此,默认的date
、datetime
和time
类型不支持作为标识符的一部分.
Therefore, the default date
, datetime
and time
types are not supported as part of the identifier.
要处理它,您应该定义自己的自定义字段类型 mydatetime
映射到您自己的 MyDateTime
类,该类实现了 __toString
.这样,ORM 也可以处理包含对象的标识符.
To deal with it, you should define your own custom field type mydatetime
mapped to your own MyDateTime
class which implements __toString
. That way, the ORM can handle identifiers also if they contain objects.
以下是该类的示例:
class MyDateTime extends DateTime
{
public function __toString()
{
return $this->format('U');
}
}
这是自定义 DBAL 类型的示例:
And here's an example of how the custom DBAL type would look like:
use DoctrineDBALTypesDateTimeType;
use DoctrineDBALPlatformsAbstractPlatform;
class MyDateTimeType extends DateTimeType
{
public function convertToPHPValue($value, AbstractPlatform $platform)
{
$dateTime = parent::convertToPHPValue($value, $platform);
if ( ! $dateTime) {
return $dateTime;
}
return new MyDateTime('@' . $dateTime->format('U'));
}
public function requiresSQLCommentHint(AbstractPlatform $platform)
{
return true;
}
public function getName()
{
return 'mydatetime';
}
}
然后你在引导过程中用你的 ORM 配置注册它(取决于你使用的框架).在 symfony 中,它记录在 symfony 准则文档中.
Then you register it with your ORM configuration during bootstrap (depends on the framework you are using). In symfony, it is documented on the symfony doctrine documentation.
之后,您可以在实体中使用它:
After that, you can use it in your entities:
class corpWalletJournal
{
// ...
/**
* @ORMColumn(name="date", type="mydatetime", nullable=false)
* @ORMId
* @ORMGeneratedValue(strategy="NONE")
*/
private $date;
这篇关于标识符中的 Doctrine 2 ORM DateTime 字段的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!