Doctrine2默认时间戳与“0000-00-00 00:00:00”格式?

时间:2015-05-14 14:11:13

标签: php mysql datetime doctrine-orm timestamp

我正在使用Doctrine2 ORM。我有一张order表。

Name                | Type       | Attributes                  | Null | Default
--------------------------------------------------------------------------------
order_id            | int        |                             | No   | None
date_created        | timestamp  |                             | No   | CURRENT_TIMESTAMP
date_edited         | timestamp  | on update CURRENT_TIMESTAMP | No   | CURRENT_TIMESTAMP
date_sent           | timestamp  |                             | No   | 0000-00-00 00:00:00
date_cancelled      | timestamp  |                             | No   | 0000-00-00 00:00:00
requested_ship_date | timestamp  |                             | No   | 0000-00-00 00:00:00

我添加了Timestampable Doctrine Extension以用于date_createddate_edited字段,如下所示:

/**
 * @var \DateTime 
 *
 * @Gedmo\Timestampable(on="create")
 * @ORM\Column(type="datetime")
 */
private $date_created;

/**
 * @var \DateTime 
 *
 * @Gedmo\Timestampable(on="update")
 * @ORM\Column(type="datetime")
 */
private $date_edited;

但是,我不确定如何处理date_sentdate_cancelled。我希望它们都默认为0000-00-00 00:00:00而不是当前时间。我看到this workaround在没有插件的情况下在Doctrine2中使用时间戳,但我不希望默认值是这些时间戳的当前时间戳。原因是,用户可以“保存”订单,但不能“发送”给某人。另外,我显然不希望date_cancelled成为当前时间戳。

注意:我不想在数据库中存储空值,所以请不要建议。

提前致谢。

更新

我目前在订单实体的其余三个字段中都有这个。

/**
 * @var \DateTime 
 *
 * @ORM\Column(type="datetime", options={"default":"0000-00-00 00:00:00"})
 * @ORM\Version
 */
private $date_sent;

/**
 * @var \DateTime 
 *
 * @ORM\Column(type="datetime", options={"default":"0000-00-00 00:00:00"})
 * @ORM\Version
 */
private $date_cancelled;

/**
 * @var \DateTime 
 *
 * @ORM\Column(type="datetime", options={"default":"0000-00-00 00:00:00"})
 * @ORM\Version
 */
private $requested_ship_date;

出于某种原因,当我尝试更新requested_ship_date字段时,它最终成为“0000-00-00 00:00:00”。我将date_sentdate_cancelled字段保留为空,并将其更新为我的本地时间,而不是UTC时间。但是,date_createddate_edited字段将更新为UTC时间的当前时间(我希望如何)。

基本上,当我保存订单时,它看起来像第一行,但我希望它看起来像第二行(假设用户请求发货日期为2015-06-08)。

order_id | date_created        | date_edited         | date_sent           | date_cancelled      | requested_ship_date
-----------------------------------------------------------------------------------------------------------------------
1        | 2015-06-05 12:00:00 | 2015-06-05 12:00:00 | 2015-06-05 07:00:00 | 2015-06-05 07:00:00 | 0000-00-00 00:00:00  
1        | 2015-06-05 12:00:00 | 2015-06-05 12:00:00 | 0000-00-00 00:00:00 | 0000-00-00 00:00:00 | 2015-06-08 00:00:00  

我在index.php文件中设置了时区,如date_default_timezone_set('Zulu');。我不会在其他任何地方重置时区。

1 个答案:

答案 0 :(得分:0)

好的,我找到了一个疯狂的解决方法,但老实说,我找不到更好的解决方案。所以,对于那些陷入同样困境的人,我很欢迎你。

首先,规则:

  • date_created =仅在创作时更新

  • date_edited =每次更新时都会更新

  • date_sent =当用户点击“提交”而不是“保存”时更新

  • date_cancelled =在用户决定取消订单时更新

  • requested_ship_date =创建新订单时需要,这是客户希望订单发货的日期。

我的订单实体中的一些代码。

/**
 * @var \DateTime 
 *
 * @ORM\Column(type="datetime")
 * @Gedmo\Timestampable(on="create")
 */
private $date_created;

/**
 * @var \DateTime 
 *
 * @ORM\Column(type="datetime")
 * @Gedmo\Timestampable(on="update")
 */
private $date_edited;

/**
 * @var \DateTime 
 *
 * @ORM\Column(type="datetime", options={"default":"0000-00-00 00:00:00"})
 */
private $date_sent;

/**
 * @var \DateTime 
 *
 * @ORM\Column(type="datetime", options={"default":"0000-00-00 00:00:00"})
 */
private $date_cancelled;

/**
 * @var \DateTime 
 *
 * @ORM\Column(type="datetime")
 * @Gedmo\Timestampable(on="change", field="requested_ship_date")
 */
private $requested_ship_date;


/*
 * Constructor
 */
public function __construct()
{
    if (!$this->date_sent) $this->date_sent = new DateTime("0000-00-00 00:00:00", new DateTimeZone("Zulu"));
    if (!$this->date_cancelled) $this->date_cancelled = new DateTime("0000-00-00 00:00:00", new DateTimeZone("Zulu"));
}

/**
 * Updates time sent 
 *
 * @return Order
 */
public function send()
{
    $this->date_sent = new DateTime("now");

    return $this;
}

/**
 * Updates time cancelled
 *
 * @return Order
 */
public function cancel()
{
    $this->date_cancelled = new DateTime("now");

    return $this;
}

说明:

我没有更改我在订单表中设置数据库列的方法。我尝试在@Gedmo\Timestampabledate_sent字段中使用date_cancelled插件,但无法使其正常工作。我注意到时区已关闭,出于一些奇怪的原因,所以我在构造函数中手动设置它们。重要的是不要自动设置它,否则您将覆盖先前设置的值。由于某些我不知道的原因,我无法在不使用requested_ship_date插件的情况下使@Gedmo\Timestampable字段正常工作。如果我把它拿出来,我尝试使用Doctrines type="datetime"的每个设置只会导致列等于0000-00-00 00:00:00

如果有人有任何疑问,请与我联系。在我弄明白之前,我必须基本上捅东西一段时间。 date_sentdate_cancelled字段正常运行,并且在我更新它们时位于正确的时区。