Вставлення об’єкта Python datetime.datetime в MySQL


120

У таблиці MySQL у мене стовпець дати. Я хочу вставити datetime.datetime()об’єкт у цю колонку. Що я повинен використовувати в операторі Execute?

Я намагався:

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))
— Sheshnath

Відповіді:


198

Для часового поля використовуйте:

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

Я думаю, що стрипінг також стосується дати.


4
Також переконайтесь, що назва стовпця не є зарезервованим словом . У мене було 30 хвилин, щоб зрозуміти, що назва "current_date" спричиняло проблеми ... Тьфу!
— Пакман

2
Що timeв цьому прикладі?
— Джеймс Макмахон

1
J McMahon: час - модуль Python.
— дстромберг

Що робити, якщо хтось хоче отримати єдиний рік, місяць, день?
— Пуджа Хатрі

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')

Сподіваюся, це допомагає.


8
Ви не можете мати лапки %sв pymsql.
— Мартін Тома

1
Цитати навколо третього% s викликають помилку, коли я намагаюся це зробити.
— realjin

13

Спробуйте скористатися, now.date()щоб отримати Dateоб’єкт, а не a 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))

Чи не потрібно додавати лапки навколо параметрів рядка, тобто "... VALUES ('% 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 у таких форматах:

Як рядок у форматі "YYYY-MM-DD HH: MM: SS" або "YY-MM-DD HH: MM: SS" . Тут дозволений і розслаблений синтаксис: Будь-який розділовий символ може використовуватися як роздільник між частинами дати або частинами часу. Наприклад, "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" еквівалентні.

Як рядок без обмежувачів у форматі "YYYYMMDDHHMMSS" або "YYMMDDHHMMSS", за умови, що рядок має сенс як дата. Наприклад, "20070523091528" та "070523091528" інтерпретуються як "2007-05-23 09:15:28", але "071122129015" є незаконним (у ньому є безглузда хвилинна частина) і стає "0000-00-00 00: 00:00 '.

Як число у форматі YYYYMMDDHHMMSS або YYMMDDHHMMSS, за умови, що число має сенс як дата. Наприклад, 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.
— франкстер

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:
    ...

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)
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.