Вставка объекта Python datetime.datetime в MySQL

120

У меня есть столбец даты в таблице MySQL. Я хочу вставитьdatetime.datetime() объект в этот столбец. Что мне следует использовать в операторе выполнения?

Я пытался:

now = datetime.datetime(2009,5,5)

cursor.execute("INSERT INTO table
(name, id, datecolumn) VALUES (%s, %s
, %s)",("name", 4,now))

Я получаю сообщение об ошибке: "TypeError: not all arguments converted during string formatting" Что мне использовать вместо %s?

Питер Мортенсен
источник
вы пропустили цитаты вокруг%s cursor.execute("INSERT INTO table (name, id, datecolumn) VALUES (%s, %s , '%s')",("name", 4,now))
Шешнатх

Ответы:

198

Для поля времени используйте:

import time    
time.strftime('%Y-%m-%d %H:%M:%S')

Я думаю, что strftime также относится к datetime.

g33kz0r
источник
4
Также убедитесь, что имя вашего столбца не является зарезервированным словом . Мне потребовалось 30 минут, чтобы понять, что имя "current_date" вызывает проблемы ... тьфу!
Pakman
2
Что timeв этом примере?
Джеймс МакМахон
1
Дж. МакМахон: время - это модуль Python.
dstromberg 01
Что делать, если кто-то хочет получить только год, месяц, день?
Пуджа Хатри,
42

Скорее всего, вы получаете ошибку TypeError, потому что вам нужны кавычки вокруг значения столбца даты.

Пытаться:

now = datetime.datetime(2009, 5, 5)

cursor.execute("INSERT INTO table (name, id, datecolumn) VALUES (%s, %s, '%s')",
               ("name", 4, now))

Что касается формата, я успешно выполнил указанную выше команду (которая включает миллисекунды) и:

now.strftime('%Y-%m-%d %H:%M:%S')

Надеюсь это поможет.

Edvinas
источник
8
Вы не можете иметь кавычки %sв pymsql.
Мартин Тома,
1
Цитаты около третьего% s вызывают ошибку, когда я пытаюсь это сделать.
realjin
13

Попробуйте использовать, now.date()чтобы получить Dateобъект, а не DateTime.

Если это не сработает, тогда преобразование в строку должно работать:

now = datetime.datetime(2009,5,5)
str_now = now.date().isoformat()
cursor.execute('INSERT INTO table (name, id, datecolumn) VALUES (%s,%s,%s)', ('name',4,str_now))
Воган
источник
Разве вам не нужно заключать строковые параметры в кавычки, например: «... ЗНАЧЕНИЯ ('% s', '% s', '% s')»
Гарет Симпсон
5

Используйте метод Python datetime.strftime(format), где format = '%Y-%m-%d %H:%M:%S'.

import datetime

now = datetime.datetime.utcnow()

cursor.execute("INSERT INTO table (name, id, datecolumn) VALUES (%s, %s, %s)",
               ("name", 4, now.strftime('%Y-%m-%d %H:%M:%S')))

Часовые пояса

Если часовые пояса вызывают беспокойство, часовой пояс MySQL можно установить для UTC следующим образом:

cursor.execute("SET time_zone = '+00:00'")

А часовой пояс можно установить в Python:

now = datetime.datetime.utcnow().replace(tzinfo=datetime.timezone.utc)

Документация MySQL

MySQL распознает значения DATETIME и TIMESTAMP в следующих форматах:

В виде строки в формате «ГГГГ-ММ-ДД ЧЧ: ММ: СС» или «ГГ-ММ-ДД ЧЧ: ММ: СС» . Здесь также разрешен «смягченный» синтаксис: любой символ пунктуации может использоваться в качестве разделителя между частями даты или времени. Например, '2012-12-31 11:30:45', '2012 ^ 12 ^ 31 11 + 30 + 45', '2012/12/31 11 * 30 * 45' и '2012 @ 12 @ 31 11 ^ 30 ^ 45 'эквивалентны.

Единственный разделитель, распознаваемый между частью даты, времени и дробной частью секунд, - это десятичная точка.

Части даты и времени можно разделять буквой T, а не пробелом. Например, «2012-12-31 11:30:45», «2012-12-31T11: 30: 45» эквивалентны.

В виде строки без разделителей в формате «ГГГГММДДЧЧММСС» или «ГГММДДЧЧММСС» при условии, что строка имеет смысл как дата. Например, «20070523091528» и «070523091528» интерпретируются как «2007-05-23 09:15:28», но «071122129015» является недопустимым (оно содержит бессмысленную минутную часть) и становится «0000-00-00 00: 00:00' .

В виде числа в формате ГГГГММДДЧЧММСС или ГГММДДЧЧММСС, при условии, что число имеет смысл в качестве даты. Например, 19830905132800 и 830905132800 интерпретируются как «1983-09-05 13:28:00».

Кристофер Пейсер
источник
3

К какой базе данных вы подключаетесь? Я знаю, что Oracle может быть разборчивой в форматах даты и любит формат ISO 8601 .

** Примечание. Ой, я только что прочитал, что вы используете MySQL. Просто отформатируйте дату и попробуйте ее как отдельный прямой вызов SQL для проверки.

В Python вы можете получить дату ISO, например

now.isoformat()

Например, Oracle любит такие даты, как

insert into x values(99, '31-may-09');

В зависимости от вашей базы данных, если это Oracle, вам может потребоваться TO_DATE:

insert into x
values(99, to_date('2009/05/31:12:00:00AM', 'yyyy/mm/dd:hh:mi:ssam'));

Общее использование TO_DATE:

TO_DATE(<string>, '<format>')

Если вы используете другую базу данных (я увидел курсор и подумал о Oracle; я мог ошибаться), проверьте их инструменты формата даты. Для MySQL это DATE_FORMAT (), а для SQL Server - CONVERT.

Также использование такого инструмента, как SQLAlchemy , устранит подобные различия и упростит вашу жизнь.

Райан Кристенсен
источник
Я не рекомендую использовать datetime.isoformat (), потому что, если вы используете объект, поддерживающий часовой пояс, сгенерированная строка включает данные о часовом поясе и больше не соответствует требуемому формату mysql.
Frankster
0

Если вы просто используете python datetime.date (а не полный datetime.datetime), просто укажите дату в виде строки. Это очень просто и работает для меня (mysql, python 2.7, Ubuntu). Столбец published_date- это поле даты MySQL, переменная python publish_date- datetime.date.

# make the record for the passed link info
sql_stmt = "INSERT INTO snippet_links (" + \
    "link_headline, link_url, published_date, author, source, coco_id, link_id)" + \
    "VALUES(%s, %s, %s, %s, %s, %s, %s) ;"

sql_data = ( title, link, str(publish_date), \
             author, posted_by, \
             str(coco_id), str(link_id) )

try:
    dbc.execute(sql_stmt, sql_data )
except Exception, e:
    ...
jbartas
источник
0

при переходе в t-sql

это не удается:

select CONVERT(datetime,'2019-09-13 09:04:35.823312',21)

это работает:

select CONVERT(datetime,'2019-09-13 09:04:35.823',21)

Простой способ:

regexp = re.compile(r'\.(\d{6})')
def to_splunk_iso(dt):
    """Converts the datetime object to Splunk isoformat string."""
    # 6-digits string.
    microseconds = regexp.search(dt).group(1)
    return regexp.sub('.%d' % round(float(microseconds) / 1000), dt)
Кшиштоф Древич
источник