繁体   English   中英

如何通过 python ibm_db 驱动程序使用 DB2 LOAD 实用程序

[英]How to use the DB2 LOAD utility using the python ibm_db driver

LOAD 是一个 DB2 实用程序,我想用它来将数据从 CSV 文件插入到表中。 如何使用ibm_db驱动程序在 Python 中执行此操作? 我在此处的文档中没有看到任何内容

CMD: LOAD FROM xyz OF del INSERT INTO FOOBAR

将其作为标准 SQL 运行会按预期失败: Transaction couldn't be completed: [IBM][CLI Driver][DB2/LINUXX8664] SQL0104N An unexpected token "LOAD FROM xyz OF del" was found following "BEGIN-OF-STATEMENT". Expected tokens may include: "<space>". SQLSTATE=42601 SQLCODE=-104 Transaction couldn't be completed: [IBM][CLI Driver][DB2/LINUXX8664] SQL0104N An unexpected token "LOAD FROM xyz OF del" was found following "BEGIN-OF-STATEMENT". Expected tokens may include: "<space>". SQLSTATE=42601 SQLCODE=-104

直接使用 db2 CLP(即os.system('db2 -f /path/to/script.file') )不是一个选项,因为 DB2 位于我没有 SSH 访问权限的另一台机器上。

EDIT:
使用ADMIN_CMD实用程序也不起作用,因为由于防火墙,正在加载的文件无法放在数据库服务器上。 现在,我已经切换到使用INSERT

LOAD是 IBM 命令行处理器命令,而不是 SQL 命令。 是这样,它不能通过ibm_db模块使用。

执行此操作的最典型方法是将 CSV 数据加载到 Python(所有行或批处理,如果内存太大),然后使用批量插入将多行一次插入到数据库中。

要执行批量插入,您可以使用execute_many方法

您可以CALL ADMIN_CMD过程。 ADMIN_CMD支持LOADIMPORT 请注意,这两个命令都要求加载/导入的文件位于数据库服务器上。

该示例取自DB2 知识中心

CALL SYSPROC.ADMIN_CMD('load from staff.del of del replace
 keepdictionary into SAMPLE.STAFF statistics use profile
 data buffer 8')

使用 Python 将 CSV 转换为 DB2

简而言之:一种解决方案是使用SQLAlchemy适配器Db2 的 External Tables

SQLAlchemy:

引擎是任何 SQLAlchemy 应用程序的起点。 它是实际数据库及其 DBAPI 的“大本营”,通过连接池和Dialect传递给 SQLAlchemy 应用程序,它描述了如何与特定类型的数据库/DBAPI 组合进行对话。

在此处输入图片说明

在上面的地方,一个Engine引用了一个Dialect和一个Pool ,它们一起解释了 DBAPI 的模块功能以及数据库的行为。

创建引擎只是发出一个调用create_engine() 的问题

dialect+driver://username:password@host:port/database

其中 dialect 是数据库名称,例如 mysql、oracle、postgresql 等,driver 是 DBAPI 的名称,例如 psycopg2、pyodbc、cx_oracle 等。

使用临时外部表加载数据:

瞬态外部表 (TET) 提供了一种定义仅在单个查询期间存在的外部表的方法。

TET 具有与普通外部表相同的功能和限制。 TET 的一个特殊功能是,当您使用 TET 将数据加载到表中或创建 TET 作为 SELECT 语句的目标时,您不需要定义表架构。

以下是 TET 的语法:

INSERT INTO <table> SELECT <column_list | *>
FROM EXTERNAL 'filename' [(table_schema_definition)]
[USING (external_table_options)];

CREATE EXTERNAL TABLE 'filename' [USING (external_table_options)]
AS select_statement;

SELECT <column_list | *> FROM EXTERNAL 'filename' (table_schema_definition)
[USING (external_table_options)];

有关可以为external_table_options变量指定的值的信息,请参阅外部表选项

一般示例

  • 通过发出以下命令,将临时外部表中的数据插入到 Db2 服务器上的数据库表中:
INSERT INTO EMPLOYEE SELECT * FROM external '/tmp/employee.dat' USING (delimiter ',' MAXERRORS 10 SOCKETBUFSIZE 30000 REMOTESOURCE 'JDBC' LOGDIR '/logs' )

要求

pip install ibm-db
pip install SQLAlchemy

派顿代码

下面的一个例子展示了它是如何协同工作的。

from sqlalchemy import create_engine


usr = "enter_username"
pwd = "enter_password"
hst = "enter_host"
prt = "enter_port"
db = "enter_db_name"

#SQL Alchemy URL
conn_params = "db2+ibm_db://{0}:{1}@{2}:{3}/{4}".format(usr, pwd, hst, prt, db)

shema = "enter_name_restore_shema"
table = "enter_name_restore_table"
destination = "/path/to/csv/file_name.csv"

try:
    print("Connecting to DB...")
    engine = create_engine(conn_params)
    engine.connect()  # optional, output: DB2/linux...
    print("Successfully Connected!")
except Exception as e:
    print("Unable to connect to the server.")
    print(str(e))

external = """INSERT INTO {0}.{1} SELECT * FROM EXTERNAL '{2}' USING (CCSID 1208 DELIMITER ',' REMOTESOURCE LZ4 NOLOG TRUE )""".format(
    shema, table, destination
)

try:
    print("Restoring data to the server...")
    engine.execute(external)
    print("Data restored successfully.")
except Exception as e:
    print("Unable to restore.")
    print(str(e))

结论

  • 恢复大文件的一个很好的解决方案,特别是 600m 工作没有任何问题。
  • 它对于将数据从一个表/数据库复制到另一个表也很有用。 以便备份作为 csv 的导出完成,然后使用给定的示例将该 csv 导出到 DB2。
  • SQLAlchemy- Engine可以与其他数据库结合,例如:sqlite、mysql、postgresql、oracle、mssql 等。

在此处输入图片说明

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM