Можем ли мы всегда получать столбец даты в виде строки (varchar) с помощью knex и postgres? - PullRequest
0 голосов
/ 06 июня 2018

У меня есть столбец в базе данных postgres с типом date.Это столбец, похожий на день рождения, который является просто датой и не должен иметь часть времени.

При извлечении этого столбца с помощью knex результатом является объект Date в формате javascript.Предположительно он выполняет new Date(row.birthday), и это результат, который отправляется клиенту.

Проблема в том, что значение, которое получает клиент, находится в стандартном формате ISO 8601 с временной частью иZ.Когда клиент пытается создать новый объект Date из этой строки, клиент может иметь ошибочное значение даты в зависимости от того, где находится клиент.

Например:

Date: 2018-06-15
Date sent to client: 2018-06-15T00:00:00Z

Client in +5:00     | Client in -5:00
2018-06-16 05:00:00 | 2018-05-15 10:00:00

ЭтоХорошо, если сервер находится в UTC, мы могли бы просто добавить смещение часового пояса клиента и получить исходную дату, но это выглядит немного хрупким и ломается во время локальной разработки (чего нет в UTC).

ПростойРешение состоит в том, чтобы просто отправить часть даты в виде строки клиентам.Но это потребовало бы сохранения даты как varchar на сервере, что мы не хотим делать.Мы потеряли бы ограничение на форматирование даты и усложнили бы вычисления на основе даты с помощью SQL.

Мы могли бы привести столбец к типу varchar при выборе столбца, но нам нужно иметь в виду наличие умаэто каждый раз, когда эта таблица выбирается.Это также означает, что нам нужно обойти ORM (Книжную полку) для работы с этой таблицей.

Существует ли простой способ указать, либо в knex, либо на книжной полке, либо непосредственно в postgres, что столбец должен хранитьсякак date со всеми сопутствующими ограничениями, но всегда выбирается как varchar?

Ответы [ 4 ]

0 голосов
/ 30 июня 2019

Для меня это не сработало самое голосуемое решение.Для меня это сработало с использованием момента.

    import * as moment from 'moment';
    types.setTypeParser(1114, str => moment.utc(str).format());
    return knex({
        client: 'pg',
        connection: {
          host : 'localhost',
          user : 'postgres',
          password : '',
          database : 'localDB',
        }
    })

Кредиты Oleksii Rudenko https://60devs.com/working-with-postgresql-timestamp-without-timezone-in-node.html

0 голосов
/ 06 июня 2018

Установка typeParser для pg, вероятно, является лучшим ответом, но вы также можете использовать Плагин процессора Книжной полки , чтобы изменить то, как выглядит этот конкретный атрибут date:

bookshelf.plugin('processor')
var MyModel = bookshelf.Model.extend({
  tableName: 'stuff',
  processors: {
    date: function(value) {
      /* you can use any other method for getting the date part */
      return value.toLocaleDateString()
    }
  }
})
0 голосов
/ 13 ноября 2018

Чтобы получить время в соответствии с местным часовым поясом в строковом формате, мы можем использовать.

  var date =function(value) {
      /* you can use any other method for getting the date part */
        return value.toLocaleDateString()
  }

date ('1990-12-30T18: 30: 00.000Z');дата (значение)

0 голосов
/ 06 июня 2018

Драйвер node-postgres - это часть, которая фактически создает объекты Date () из данных, отправляемых из столбцов даты (https://node -postgres.com / features / types # date-timestamp-timestamptz )

С помощью postgres вы можете изменять синтаксические анализаторы типа node-pg, как описано здесь https://github.com/brianc/node-pg-types

oid типа даты типа 1082 можно получить с помощью следующего запроса

select typname, oid, typarray from pg_type where typname = 'date' order by oid;

Итакчтобы переопределить тип даты для передачи в виде строки, достаточно сделать это перед настройкой соединения с БД (я полагаю, это можно сделать, например, в knexfile.js):

var types = require('pg').types;
// override parsing date column to Date()
types.setTypeParser(1082, val => val); 
...