Python: установить параметр для столбцов и значений pypyodbc - executemany

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

СТОЛБЦЫ = [['ИМЯ','ФАМИЛИЯ','ВОЗРАСТ'],['ФАМИЛИЯ','ИМЯ','ВОЗРАСТ']]
ЗНАЧЕНИЯ = [['Джон','Доу',56],[ 'Доу','Джон',56]]
TABLE = 'люди'

Вот как я хотел бы пройти, но это не работает:

db = DB_CONN.MSSQL() #method for connecting to MS SQL or ORACLE etc.
cursor = db.cursor()
sql = "insert into %s (?) VALUES(?)" % TABLE 
cursor.executemany([sql,[COLUMNS[0],VALUES[0]],[COLUMNS[1],VALUES[1]]])
db.commit()

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

db = DB_CONN.MSSQL() #method for connecting to MS SQL or ORACLE etc.
cursor = db.cursor()
sql = 'insert into %s (NAME,SURNAME,AGE) VALUES (?,?,?)'
cursor.executemany(sql,[['John','Doe',56],['Doe','John',56]])
db.commit()

Надеюсь, я объяснил это достаточно ясно. Пс. СТОЛБЦЫ и ЗНАЧЕНИЯ извлекаются из словаря json

[{'ИМЯ':'Джон','ФАМИЛИЯ':'Доу','ВОЗРАСТ':56...},{'ФАМИЛИЯ':'Доу','ИМЯ':'Джон','ВОЗРАСТ':77 ...}]

если это поможет.

РЕШЕНИЕ:

class INSERT(object):

    def __init__(self):
        self.BASE_COL = ''

    def call(self):
        GATHER_DATA =  [{'NAME':'John','SURNAME':'Doe','AGE':56},{'SURNAME':'Doe','NAME':'John','AGE':77}]
        self.BASE_COL = ''
        TABLE = 'person'

        #check dictionary keys
        for DATA_EVAL in GATHER_DATA:

            if self.BASE_COL == '': self.BASE_COL = DATA_EVAL.keys()
            else:
                if self.BASE_COL != DATA_EVAL.keys():
                    print ("columns in DATA_EVAL.keys() have different columns")
                    #send mail or insert to log  or remove dict from list
                    exit(403)

        #if everything goes well make an insert
        columns = ','.join(self.BASE_COL)
        sql = 'insert into %s (%s) VALUES (?,?,?)' % (TABLE, columns)
        db = DB_CONN.MSSQL()
        cursor = db.cursor()
        cursor.executemany(sql, [DATA_EVAL.values() for DATA_EVAL in GATHER_DATA])
        db.commit()


if __name__ == "__main__":
    ins = INSERT()
    ins.call()

person Dragon.M    schedule 06.07.2017    source источник
comment
Если вы не можете обеспечить порядок значений, вы можете использовать dict. См. ответы на этот вопрос stackoverflow.com/questions/9336270/ для некоторых идей   -  person Oluwafemi Sule    schedule 06.07.2017
comment
хм, я не уверен, потому что на первый взгляд это вряд ли применимо к executemany, но я проверю.   -  person Dragon.M    schedule 06.07.2017


Ответы (1)


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

columns = ','.join(records[0].keys())
sql = 'insert into %s (%s) VALUES (?,?,?)' % (TABLE, columns)
cursor.executemany(sql,[record.values() for record in records])

Использованная литература:

person Oluwafemi Sule    schedule 06.07.2017
comment
Ага, понятно... Так что, в принципе, даже если ключи словаря находятся в другом порядке в списке... В тот момент, когда мы делаем цикл по словарям, они будут отсортированы одинаково. Спасибо, я поделился своим кодом с другими, чтобы они могли извлечь пользу из этого ответа. - person Dragon.M; 06.07.2017