2026, Jan 05 03:01
Как загрузить файлы Feather в PostgreSQL с помощью pandas
Как без ручного DDL загрузить файлы Feather в PostgreSQL: pandas DataFrame.to_sql создаёт таблицы и сразу вставляет данные. Простой и надёжный конвейер.
Когда у вас каталог, набитый файлами Feather с десятками столбцов и сотнями тысяч строк, вручную писать CREATE TABLE для каждого файла — долго и легко ошибиться. Цель очевидна: сгенерировать таблицы и загрузить данные, не прописывая снова и снова каждый столбец и его тип.
Как выглядит первоначальный подход
Ниже — компактный пример, который перебирает папку, читает каждый .feather в DataFrame, сопоставляет типы PostgreSQL с dtypes pandas и собирает оператор CREATE TABLE. Это отражает привычное стремление сгенерировать DDL программно, а потом придумать, как массово загрузить данные.
import os
import glob
import pandas as pd
base_dir = "E:\\file_path"
feather_items = glob.glob(os.path.join(base_dir, '*.feather'))
for asset_path in feather_items:
print(f"File: {asset_path}")
frame = pd.read_feather(asset_path)
rel_name = {asset_path}
type_map = frame.dtypes.to_dict()
sql_parts = []
def pd_kind_to_pg(kind):
if pd.api.types.is_integer_dtype(kind):
return "INTEGER"
elif pd.api.types.is_float_dtype(kind):
return "FLOAT"
elif pd.api.types.is_bool_dtype(kind):
return "BOOLEAN"
elif pd.api.types.is_datetime64_any_dtype(kind):
return "TIMESTAMP"
else:
return "TEXT"
for col_name, kind in type_map.items():
pg_kind = pd_kind_to_pg(kind)
sql_parts.append(f'"{col_name}" {pg_kind}')
ddl_stmt = f"CREATE TABLE {rel_name} ( {' '.join(sql_parts)} );"
Почему это становится препятствием
Даже с успешно сгенерированным DDL всё упирается в надёжный способ загрузить строки в базу с той же схемой. Вставлять по столбцам — значит быстро получить громоздкую процедуру вставки. На этом многие конвейеры и буксуют: определение таблицы есть, а массовой загрузки — нет.
Простой путь: поручите pandas создать таблицу и загрузить данные
В pandas есть встроенный метод для сохранения DataFrame в SQL‑базе. На практике это избавляет от самописного DDL и отдельной логики вставки для каждого файла. Один вызов: DataFrame задаёт схему и сразу же загружает данные.
from sqlalchemy import create_engine
import pandas as pd
import os
import glob
root_dir = "E:\\file_path"
feathers = glob.glob(os.path.join(root_dir, '*.feather'))
for asset in feathers:
print(f"File: {asset}")
frame = pd.read_feather(asset)
dest_name = asset
engine_obj = create_engine("postgresql+psycopg2://user:pass@localhost/database")
frame.to_sql(name=dest_name, con=engine_obj)
Здесь используется подключение к базе через SQLAlchemy, а каждый DataFrame записывается прямо в таблицу. Имя таблицы берётся из пути к файлу — в соответствии с предложенным подходом.
Почему это важно
Замена ручной генерации DDL и вставок «на коленке» одним вызовом упрощает поддержку и уменьшает риск несоответствий схемы. Когда вы обрабатываете множество файлов с большим числом столбцов, отказ от кастомного SQL — практичное преимущество: процесс от обнаружения файлов до загрузки данных остаётся единообразным.
Итоги
Если вы уже читаете Feather через pandas, используйте DataFrame.to_sql для одновременного создания схемы и вставки данных. По сравнению с ручными CREATE TABLE и отдельной логикой вставки для каждого файла это экономит время и держит конвейер сосредоточенным на данных, а не на шаблонном SQL.