我正在尝试在迁移中运行自定义SQL。这就是它的样子:
from django.db import migrations
class Migration(migrations.Migration):
dependencies = [
]
operations = [
migrations.RunSQL(
"SET timezone TO 'UTC'",
),
]
当我用
运行它时./ manage.py migrate helper
我可以在日志中看到运行SQL命令:
[17/Feb/2017 20:37:37] DEBUG [django.db.backends.schema:103] SET timezone TO 'UTC'; (params None)
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.000) SET timezone TO 'UTC';
但是当我在数据库中检查它时,仍然说时区是本地时间:
gdp=# show timezone;
TimeZone
-----------
localtime
(1 row)
如果我手动运行相同的命令,它可以正常工作:
gdp=# SET timezone TO 'UTC';
SET
gdp=#
gdp=# show timezone;
TimeZone
----------
UTC
(1 row)
Django版本:1.10.5
PostgreSQL版本:9.5.5
完整日志:
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.591) CREATE EXTENSION IF NOT EXISTS postgis; args=None
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.002)
SELECT c.relname, c.relkind
FROM pg_catalog.pg_class c
LEFT JOIN pg_catalog.pg_namespace n ON n.oid = c.relnamespace
WHERE c.relkind IN ('r', 'v')
AND n.nspname NOT IN ('pg_catalog', 'pg_toast')
AND pg_catalog.pg_table_is_visible(c.oid); args=None
[17/Feb/2017 20:37:37] DEBUG [django.db.backends.schema:103] CREATE TABLE "django_migrations" ("id" serial NOT NULL PRIMARY KEY, "app" varchar(255) NOT NULL, "name" varchar(255) NOT NULL, "applied" timestamp with time zone NOT NULL); (params None)
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.014) CREATE TABLE "django_migrations" ("id" serial NOT NULL PRIMARY KEY, "app" varchar(255) NOT NULL, "name" varchar(255) NOT NULL, "applied" timestamp with time zone NOT NULL); args=None
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.000) SELECT "django_migrations"."app", "django_migrations"."name" FROM "django_migrations"; args=()
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.001)
SELECT c.relname, c.relkind
FROM pg_catalog.pg_class c
LEFT JOIN pg_catalog.pg_namespace n ON n.oid = c.relnamespace
WHERE c.relkind IN ('r', 'v')
AND n.nspname NOT IN ('pg_catalog', 'pg_toast')
AND pg_catalog.pg_table_is_visible(c.oid); args=None
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.000) SELECT "django_migrations"."app", "django_migrations"."name" FROM "django_migrations"; args=()
[17/Feb/2017 20:37:37] DEBUG [django.db.backends.schema:103] SET timezone TO 'UTC'; (params None)
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.000) SET timezone TO 'UTC'; args=None
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.000)
SELECT c.relname, c.relkind
FROM pg_catalog.pg_class c
LEFT JOIN pg_catalog.pg_namespace n ON n.oid = c.relnamespace
WHERE c.relkind IN ('r', 'v')
AND n.nspname NOT IN ('pg_catalog', 'pg_toast')
AND pg_catalog.pg_table_is_visible(c.oid); args=None
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.000) INSERT INTO "django_migrations" ("app", "name", "applied") VALUES ('helper', '0001_initial', '2017-02-17T20:37:37.272476+00:00'::timestamptz) RETURNING "django_migrations"."id"; args=(u'helper', u'0001_initial', datetime.datetime(2017, 2, 17, 20, 37, 37, 272476, tzinfo=<UTC>))
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.001)
SELECT c.relname, c.relkind
FROM pg_catalog.pg_class c
LEFT JOIN pg_catalog.pg_namespace n ON n.oid = c.relnamespace
WHERE c.relkind IN ('r', 'v')
AND n.nspname NOT IN ('pg_catalog', 'pg_toast')
AND pg_catalog.pg_table_is_visible(c.oid); args=None
[17/Feb/2017 20:37:37] DEBUG [django.db.backends:90] (0.000) SELECT "django_migrations"."app", "django_migrations"."name" FROM "django_migrations"; args=()
编辑:
我有这些设置:
USE_TZ = True
TIME_ZONE = 'UTC'
但是这个Django使用我当地的时区将日期时间保存到Postgres,就像这个'2016-09-12T08:06:45-04:00'。当我通过Django查询数据库时它确实将它转换回UTC但我想在Postgres中使用'clean'datetime,就像这样'2016-09-12T12:06:45 + 00'。
答案 0 :(得分:1)
我在PostgreSQL文档8.5.3. Time Zones中找到了我的问题的答案:
SQL命令SET TIME ZONE设置会话的时区。
我能够通过在 postgresql.conf 中设置时区来解决这个问题(对我而言,它位于 /etc/postgresql/9.5/main 中)。
答案 1 :(得分:0)
当您使用DateTimeField时,Django会设置自己的时区。在您的settings.py中,您应该找到以下设置:
TIME_ZONE='UTC'
您可以将此设置为None
来禁用djangos timezone-usage。但是,我相信这只会将所有DateTimeField值转换为没有时区的值。 (没试过)
我建议在任何情况下都使用djangos TIME_ZONE
设置,因为它可以确保所有数据库的一致性。