Bezdepbonusu7Программирование: статьи и ответы

Вопрос

Mysqldb преобразует данные метки времени в None

Автор вопроса: ronakОтветов: 2

Я использую MySQLdb для общения с базой данных mysql, и я могу динамически извлекать все наборы результатов.

Моя проблема в том, что как только я получаю набор результатов, есть пара столбцов, которые объявлены как временные метки в mysql, но когда они извлекаются, они превращаются в None.

У меня есть два столбца, оба объявлены временными метками, но один возвращает правильные данные, а другой возвращает None. И utime, и enddate объявляются временными метками, но utime не возвращает правильный результат, а enddate возвращает.

['utime', 'userstr', 'vstr_client', 'enddate']

((None, '000102030ff43260gg0809000000000004', '7.7.0', '1970-01-01 12:00:00.000000'))

def parse_data_and_description(cursor, data):

    res = []
    cols = [d[0] for d in cursor.description]
    print cols
    print data

    for i in data:
        res.append(OrderedDict(zip(cols, i)))
    return res

def call_multi_rs(sp, args):

    rs_id=0;
    conn = connect()
    cursor = conn.cursor()
    try:
        conn.autocommit(True)
        cursor.execute ("CALL %s%s" % (sp, args))
        while True:
            rs_id+=1
            data = cursor.fetchone( )
            listout = parse_data_and_description(cursor, data)
            print listout
            if cursor.nextset( )==None:
            # This means no more recordsets available
            break

timestampdatetimetype-conversion

Ответы

Ответ 1 · рейтинг 8 · ronak

Наконец, после того, как никто не ответил или не попытался найти дополнительную информацию, я продолжил искать другие решения и обнаружил, что библиотека MySQLdb преобразует типы данных из sql в python, и есть ошибка, которая не преобразует метку времени.

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

Но вот модификация, которую нужно сделать при подключении к базе данных mysql. MySQLdb не может сериализовать объект даты и времени Python

try:
    import MySQLdb.converters
except ImportError:
    _connarg('conv')

def connect(host='abc.dev.local', user='abc', passwd='def', db='myabc', port=3306):

    try:
        orig_conv = MySQLdb.converters.conversions
        conv_iter = iter(orig_conv)
        convert = dict(zip(conv_iter, [str,] * len(orig_conv.keys())))
        print "Connecting host=%s user=%s db=%s port=%d" % (host, user, db, port)
        conn = MySQLdb.connect(host, user, passwd, db, port, conv=convert)
    except MySQLdb.Error, e:
        print "Error connecting %d: %s" % (e.args[0], e.args[1])
    return conn

Ответ 2 · рейтинг 3 · Fantilein1990

Я столкнулся с той же проблемой: получение данных типа DATETIME(1) возвращает None.

Некоторые исследования выявили ошибку MySQLdb №325. Согласно этому трекеру ошибок, проблема все еще открыта (уже более 2 лет), но комментарии предоставляют рабочее решение:

В файле times.py пакета MySQLdb вам нужно вставить несколько строк для обработки микросекунд следующим образом:

def DateTime_or_None(s):
    if ' ' in s:
       sep = ' '
    elif 'T' in s:
        sep = 'T'
    else:
        return Date_or_None(s)

    try:
        d, t = s.split(sep, 1)
        if '.' in t:
            t, ms = t.split('.',1)
            ms = ms.ljust(6, '0')
        else:
            ms = 0
        return datetime(*[ int(x) for x in d.split('-')+t.split(':')+[ms] ])
    except (SystemExit, KeyboardInterrupt):
        raise
    except:
        return Date_or_None(s)

def TimeDelta_or_None(s):
    try:
        h, m, s = s.split(':')
        if '.' in s:
            s, ms = s.split('.')
            ms = ms.ljust(6, '0')
        else:
            ms = 0
        h, m, s, ms = int(h), int(m), int(s), int(ms)
        td = timedelta(hours=abs(h), minutes=m, seconds=s,
                       microseconds=ms)
        if h < 0:
            return -td
        else:
            return td
    except ValueError:
        # unpacking or int/float conversion failed
        return None

def Time_or_None(s):
    try:
        h, m, s = s.split(':')
        if '.' in s:
            s, ms = s.split('.')
            ms = ms.ljust(6, '0')
        else:
            ms = 0
        h, m, s, ms = int(h), int(m), int(s), int(ms)
        return time(hour=h, minute=m, second=s, microsecond=ms)
    except ValueError:
        return None

Однако я не могу объяснить, что ваш исходный запрос работает с одним столбцом, а не с другим. Может быть, во втором нет микросекундной информации?

Перевод вопроса и ответов сообщества Stack Overflow, лицензия CC BY-SA. Оригинал на Stack Overflow.

Похожие материалы