【问题标题】:Doctrine with SQL Server DateTime typeSQL Server DateTime 类型的学说
【发布时间】:2019-02-23 17:01:20
【问题描述】:

我在 Laravel 上开发一个依赖于 Doctrine 的 Web 应用程序。数据库存储在 SQL Express 2017 上。

当我执行 SELECT 时,我遇到了 documentation 中提到的 DateTime 类型的问题。

无法将数据库值“2018-11-19 16:19:44.923”转换为 Doctrine 类型 datetimetz。预期格式:Y-m-d H:i:s.u P

为了解决这个问题,经过一些研究,我创建了自己的 DateTime 类型。

<?php

namespace App\Doctrine\Types;

use Doctrine\DBAL\Types\DateTimeType;
use Doctrine\DBAL\Platforms\AbstractPlatform;

class MsDateTime extends DateTimeType
{
    private $dateTimeFormatString = 'Y-m-d H:i:s.u';

    public function convertToDatabaseValue($value, AbstractPlatform $platform)
    {
        return ($value !== null) ? $value->format($this->dateTimeFormatString) : null;
    }

}

然后我覆盖默认类型:

Type::overrideType(Type::DATETIMETZ, 'App\Doctrine\Types\MsDateTime');

所以现在我可以显示数据但我不能插入新行: 使用参数 ["Test", "Test", 1, " 执行 'INSERT INTO table (row1, row2, active, date_created, timestamp) VALUES (?, ?, ?, ?, ?)' 时发生异常2018-11-20 16:12:11.349245", "2018-11-20 16:12:11.349250"]

我想知道为什么我不能存储新行。如果您对 SQLServer 的 Doctrine 有任何修复,我将不胜感激!

我们也使用 Python 和 SQL Alchemy 来查询同一个数据库,我们没有这种问题。

【问题讨论】:

  • 你能不能把日期字符串格式改成20181120 16:12:11.349245,也可能是DateTime的小数位太多了,你可能需要SQL中的DateTime2。 YYYYMMDD 是 SQL 的 ISO 日期格式,几乎总是适用于 SQL 字符串。
  • 我将SQL EXPRESS中的日期时间格式设置为Datetime2。但是我可以更新/插入但不能选择。我得到了预期的格式:Y-m-d H:i:s.u P.

标签: sql-server doctrine


【解决方案1】:

使用 Microsoft Sql Server Express 2017,您应该首先确认您在 Doctrine 配置/自动加载器中使用了SQLServer2012Platform

我通过以下方式指定它(在 Codeigniter 下):

$myPlatform = new \Doctrine\DBAL\Platforms\SQLServer2012Platform();
$connectionOptions = array(
    'driver' => 'pdo_sqlsrv',
    'user' => $db['default']['username'],
    'password' => $db['default']['password'],
    'host' => $db['default']['hostname'],
    'dbname' => $db['default']['database'],
    'platform' => $myPlatform
);

我将所有 SQL 字段从 DATETIME 切换到 DATETIME2 并且插入/更新运行良好。

我的 Doctrine 实体是使用 'datetime' 类型定义的,我可以使用原生 DateTime() 对象来提供它们。

/**
 * @var \DateTime
 *
 * @ORM\Column(type="datetime", nullable = true)
 */
protected $created;

/**
 * @var \DateTime
 *
 * @ORM\Column(type="datetime", nullable = true)
 */
protected $updated;

/**
 * @ORM\PrePersist
 * @ORM\PreUpdate
 */
public function updatedTimestamps(): void
{
    if ($this->created === null) {
        $this->created = new \DateTime();
    }
    $this->updated = new \DateTime();
}

希望这会有所帮助!

根据已知问题,我将放弃 datetimetz 类型。看 Doctrine - Known Vendor Issues - Microsoft SQL Server

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2020-07-31
    • 1970-01-01
    • 1970-01-01
    • 2020-02-02
    • 2015-02-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多