升级Ubuntu至22.04后Laravel中SQL Server日期字段格式异常
Ubuntu 22.04 Docker容器中Laravel读取SQL Server date字段格式异常问题
我在基于Ubuntu的Docker容器中运行Laravel应用,将基础镜像从Ubuntu 20.04升级到22.04后,SQL Server的date类型字段返回格式发生了变化。
迁移代码
Schema::create('my_table', function (Blueprint $table) { $table->bigIncrements('id'); $table->date('due_date'); });
查询代码
$dueDate = DB::table('my_table')->find(1)->due_date;
在Ubuntu 20.04环境下,$dueDate 的值为 '2020-01-31';升级到Ubuntu 22.04后,$dueDate 的值变为 'Jan 31 2020 12:00:00:AM'。除了升级Ubuntu镜像外,未做任何其他更改。
Dockerfile内容
FROM ubuntu:22.04 #Switched from ubuntu:20.04 RUN apt-get update && apt-get install -y software-properties-common RUN add-apt-repository ppa:ondrej/php RUN apt-get update && apt-get install -y \ gnupg2 \ nginx \ php8.1 \ php8.1-bcmath \ php8.1-curl \ php8.1-fpm \ php8.1-gd \ php8.1-intl \ php8.1-mbstring \ php8.1-memcached \ php8.1-redis \ php8.1-sybase \ php8.1-xdebug \ php8.1-xml \ php8.1-zip \ && rm -rf /var/lib/apt/lists/* COPY . /var/www/html WORKDIR /var/www/html CMD tail -f /var/log/nginx/*.log
环境版本信息
- PHP版本:8.1.13
- Laravel版本:9.43.0
- SQL Server版本:2017
问题原因及解决方法
该问题根源是Ubuntu 22.04默认系统区域设置(locale)与20.04不同,导致PHP依赖的freetds(通过php8.1-sybase)返回的日期格式改变。以下是三种可行解决方式:
方式1:在Dockerfile中配置区域设置
在Dockerfile中添加locale配置命令,指定支持ISO日期格式的区域:
# 安装locale工具并生成指定区域 RUN apt-get install -y locales && \ locale-gen en_US.UTF-8 && \ update-locale LC_ALL=en_US.UTF-8 LANG=en_US.UTF-8 # 设置环境变量生效 ENV LANG=en_US.UTF-8 ENV LC_ALL=en_US.UTF-8
方式2:Laravel层面强制日期格式
- 若使用Eloquent模型,可在模型中定义日期字段格式:
class MyTable extends Model { protected $dates = ['due_date']; protected $dateFormat = 'Y-m-d'; }
- 直接在查询时转换格式(利用SQL Server内置函数):
$dueDate = DB::table('my_table') ->selectRaw("CONVERT(varchar, due_date, 23) as due_date") ->find(1)->due_date;
(注:SQL Server中23对应YYYY-MM-DD格式)
方式3:修改freetds配置
在容器中配置freetds的日期格式为ISO:
# 写入freetds配置 RUN echo -e "[global]\ntds version = 7.4\ndate format = iso" > /etc/freetds/freetds.conf
内容的提问来源于stack exchange,提问作者Yaakov
相关产品推荐
相关产品推荐

