Я пишу скрипт, в котором я извлекаю данные из MongoDB и выгружаю их в PostgreSQL. Все работает нормально, но когда я пытаюсь вставить ObjectId MongoDBs _id
, выдает следующую ошибку.
(psycopg2.errors.SyntaxError) завершающий мусор после числового литерала в или рядом с "63711d"
Я хочу вставить _id
в базу данных PostgreSQL в качестве первичного ключа, чтобы не было повторяющихся строк.
Запрос, сгенерированный psycopg2, выглядит следующим образом
[SQL: INSERT INTO employees (_id, candidate_last_name, candidate_first_name, candidate_state, candidate_experience, candidate_relocation, candidate_skills, candidate_specialty)VALUES (6375364d1ad809ab6108a544, NULL, NULL, NULL, NULL, NULL, NULL, NULL), (6375364d1ad809ab6108a545, NULL, NULL, NULL, NULL, NULL, NULL, NULL)]
Поле _id
в PostgreSQL — это VARCHAR.
Код, который я использую, выглядит следующим образом:
def insert_psql(db, table_name: str, fields: dict, data: list):
new_fields = {}
for field in fields:
new_fields[field.replace('.', '_')] = fields[field]
insert_query = f'INSERT INTO {table_name} ('
insert_query += ', '.join(new_fields.keys()) + ')'
insert_query += 'VALUES '
for i, row in enumerate(data):
insert_query += '('
for j, field in enumerate(fields):
if not row.get(field):
insert_query += 'NULL'
else:
insert_query += f'{str(row.get(field))}'
if not j == len(fields) - 1:
insert_query += ', '
insert_query += ')'
if not i == len(data) - 1:
insert_query += ', '
# print(insert_query)
try:
db.execute(insert_query)
db.commit()
except Exception as e:
print(e)
Поля dict — это словарь, содержащий имена столбцов и их типы данных в качестве значения. Список данных список записей для вставки
Не могли бы вы добавить код, который генерирует этот запрос, в свой пост?
Я динамически генерирую запрос на вставку. Я добавил код для этого в сообщение.
@MarkRotteveel есть идеи, как решить эту ошибку?
Вы не должны создавать операторы посредством конкатенации. Используйте подготовленные операторы с параметрами. Ваш текущий код чрезвычайно уязвим для SQL-инъекций.
Ваш код ошибки: trailing junk after numeric literal at or near "63711d"
В частности, это предупреждение о неожиданных символах после числовых литералов. В напечатанном тексте мы видим пять цифр (63711
), за которыми следует символ a
. Похоже, что код пытается проанализировать этот набор символов как число и не может этого сделать, как только находит первый альфа-символ.
Действительно, когда мы смотрим на сгенерированный оператор SQL, мы видим это:
VALUES (6375364d1ad809ab6108a544,
Если вы пытаетесь вставить строку (VARCHAR
), то @Mark Rotteveel сказал, что вам нужно сделать в самом первом комментарии к этому вопросу:
Если это VARCHAR в PostgreSQL, то значение должно быть заключено в кавычки в сгенерированном операторе.
Вместо этого ваше утверждение INSERT
должно иметь что-то вроде этого:
VALUES ('6375364d1ad809ab6108a544',
Отредактировано для использования одинарных кавычек вместо двойных. Кроме того, Марк поднимает еще одно важное предупреждение об этом подходе в целом здесь.
Он должен выглядеть как VALUES ('6375364d1ad809ab6108a544',
(одинарные, а не двойные кавычки).
Упс, исправлено! Также указал на ваше предупреждение о подходе в целом в комментариях.
Как вы генерируете оператор вставки? Если это VARCHAR в PostgreSQL, то значение должно быть заключено в кавычки в сгенерированном операторе.