PythonでAS400と通信しようとしています。目標はSQLAlchemyを使用することですが、それを機能させることができなかったときは、ibm_db_saの代わりにibm_dbだけを使用してより基本的なスクリプトに戻りました。
import ibm_db
dbConnection = ibm_db.pconnect("DATABASE=myLibrary;HOSTNAME=1.2.3.4;PORT=8471;PROTOCOL=TCPIP;UID=username;PWD=password", "", "") #this line is where it hangs
print ibm_db.conn_errormsg()
問題はポートにあるようです。すべての例にある50000を使用すると、エラーが発生します。 446を使用すると、エラーが発生します。困惑する部分はこれです:私が8471を使用する場合、これは IBMがそうするように言っています 、エラー、タイムアウト、応答はまったくありません。スクリプトを20分以上実行したままにしましたが、スクリプトはそのままで何もしません。コマンドPromptをまったく使用できないため、アクティブですが、いかなる種類のフィードバックも提供されません。
これと同じ400は、私が毎日働いている会社で、ロギング、電子メール、および(大量の)データベースの使用に使用されているので、機能することはわかっています。私たちが使用しているソフトウェアは、バックグラウンドでデータベースと通信しますが、私のマシンでは問題なく動作します。これは、私のドライバーが優れていること、ネットワーク設定が正しいことなどを示しています。ここから400にtelnetで接続することもできます。
私はSQLAlchemyとibm_dbのメーリングリストに参加しており、この問題について何日も連絡を取り合っています。私はまたそれをグーグルで検索したので、検索結果の未訪問のリンクが不足し始めています。接続が無期限にハングするという問題を抱えている人はいないようです。 Pythonで試すことができるものがあれば、試してみます。私は400を直接扱っていませんが、必要なものは何でもチェック/構成するように依頼することができます。ただし、前述したように、複数のワークステーションは問題なく400のデータベースと通信でき、アクセスしたいライブラリに対してクエリを実行すると、400自体から実行した場合でも正常に機能します。何か提案があれば、聞いていただければ幸いです。ありがとう!
README for _ibm_db_sa
_ は、「サポートされているデータベース」セクションにLinux/Unix/Windows用のDB2のみをリストしています。したがって、DB2 for iでは機能しない可能性が高く、少なくとも箱から出してすぐには機能しません。
IBM System i Access for Windowsを使用しているとおっしゃっていたので、付属のドライバーの1つ(@Charlesが述べたように、ODBC、OLEDB、またはADO.NET)を使用することを強くお勧めします。
個人的には、私は常にODBCを使用し、 pyodbc
または pypyodbc
のいずれかを使用します。どちらでも問題なく動作します。簡単な例:
_import pyodbc
connection = pyodbc.connect(
driver='{iSeries Access ODBC Driver}',
system='11.22.33.44',
uid='username',
pwd='password')
c1 = connection.cursor()
c1.execute('select * from qsys2.sysschemas')
for row in c1:
print row
_
さて、SQLAlchemyの接続方法の1つはpyodbc
なので、pyodbc
を直接使用して接続を確立できれば、SQLAlchemyを同じように構成できると思います。しかし、私自身はSQLAlchemyユーザーではないので、そのためのサンプルコードはありません。
[〜#〜]更新[〜#〜]
SQLAlchemyをIBMiに接続して、直接SQLクエリを実行することができました。つまり、PyODBCを直接使用するのとほぼ同じ機能を実現するためです。 他のSQLAlchemy機能はテストしていません。Windows 7マシンで接続をセットアップするために行ったこと:
_ibm_db_sa
_をSQLAlchemy方言としてインストールします
これにはpip
を使用できるかもしれませんが、私はそれをローテクな方法で行いました。
ibm_db_sa
_ をダウンロードします。ibm_db_sa-0.3.2.tar.gz
_)を解凍し、同封の_ibm_db_sa
_ディレクトリを_sqlalchemy\dialects
_ディレクトリにコピーします。_sqlalchemy\dialects\ibm_db_sa\pyodbc.py
_を変更します
initialize()
メソッドを_AS400Dialect_pyodbc
_クラスに追加しますDB2Dialect
_が継承する_AS400Dialect_pyodbc
_の同じ名前のメソッドをオーバーライドすることです。問題は、DB2Dialect.initialize()
が属性_dbms_ver
_と_dbms_name
_を設定しようとすることです。どちらも、PyODBCを使用してIBM iに接続するときに使用可能でも関連性もありません(私が知る限り)。dialect
を追加し、それを_AS400Dialect_pyodbc
_クラスに設定します上記の変更のコードはファイルの最後にあり、次のようになります。
_ def initialize(self, connection):
super(DB2Dialect, self).initialize(connection)
dialect = AS400Dialect_pyodbc
_
インデントに注意してください!initialize()
メソッドは_AS400Dialect_pyodbc
_クラスに属している必要があり、dialect
はグローバルである必要があることを忘れないでくださいモジュールに。
最後に、エンジン作成者に正しいURLを与える必要があります。
'ibm_db_sa + pyodbc:// username:password @ Host/* local'
(明らかに、username
、password
、およびHost
の代わりに有効な値を使用してください。)
それでおしまい。この時点で、エンジンを作成し、iに接続し、SQLAlchemyを介してプレーンSQLを実行できるはずです。この時点で多くのORMも機能するはずだと思いますが、これは検証していません。
これは、as400、sqlalchemy、およびpandasで動作する例です。この例では、多数のcsvファイルを取得し、pandas/sqlalchemyで挿入します。 Windowsでのみ機能し、Linuxではiシリーズのodbcドライバーのセグメンテーション違反(Centos7およびDebian9 x68_64)
クライアントはWindows10です。
私のas400バージョンは7.3です
Pythonは2.7.14です
pipでインストール:pandas、pyodbc、imb_db_sa、sqlalchemy
Windows用のiaccessをインストールする必要があります ftp://public.dhe.ibm.com/as400/products/clientaccess/win32/v7r1m0/servicepack/si66062/
さらに、pyodbc.py C:\ Python27\Lib\site-packages\sqlalchemy \方言\ ibm_db_sa\pyodbc.pyの@JohnYによる変更
pyodbc_driver_name = "IBM i Access ODBC Driver"
Odbcドライバーはその名前を変更しました。
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import pandas as pd
import numpy as np
from sqlalchemy import create_engine
import glob
csvfiles=(glob.glob("c:/Users/nahum/Documents/OUT/*.csv"))
df_csvfiles = pd.DataFrame(csvfiles)
for index, row in df_csvfiles.iterrows():
datastore2=pd.read_csv(str(row[0]), delimiter=',', header=[0],skipfooter=3)
engine = create_engine('ibm_db_sa+pyodbc://DB2_USER:PASSWORD@IP_SERVER/*local')
datastore2.to_sql('table', engine, schema='SCHEMA', chunksize=1000, if_exists='append', index=False)
それが役に立てば幸い。
必要なポートを見つける方法は、IBMiのサービステーブルエントリを調べることです。
IBM i担当者は、iNav GUIまたは緑色の画面の「サービス表項目の処理(WRKSRVTBLE)」コマンドを使用できます。
次のような画面が表示されます。
Service Port Protocol
as-admin-http 2001 tcp
as-admin-http 2001 udp
as-admin-https 2010 tcp
as-admin-https 2010 udp
as-central 8470 tcp
as-central-s 9470 tcp
as-database 8471 tcp
as-database-s 9471 tcp
drda 446 tcp
drda 446 udp
DBのデフォルトポートは確かに8471です。ただし、drdaは「分散データベース」操作に使用されます。
これに基づいて thread 、ibm_dbを使用してIBM i上のDB2に接続するには、IBMConnect製品が必要です。これは、支払いが必要な商用パッケージです。
この スレッド は、pyodbcモジュールを介してODBCを使用することを示唆しています。また、JT400ツールキットを介したJDBCも機能する可能性があることを示唆しています。
Pandas/SQLAlchemyが必要ない場合は、 John Yの回答 で提案されているようにpyodbcを使用してください。それ以外の場合は、以下で私のために働いたことをやってみることができます。 私自身の同様の質問 に対する私の答えから取られています。これは、がしないことの詳細を確認できます。動作します(動作させる前に、さまざまな方法で試して失敗しました)。
受け取ったこのメッセージを和らげるために、プロジェクトに空のファイルを作成しました。
'hashtable_class_helper.pxi'
を開くことができません:ファイルが見つかりません(file:///c:/git/dashboards/pandas/_libs/hashtable_class_helper.pxi
)。
(私のプロジェクトフォルダーはC:/Git/dashboards
なので、残りのパスを作成しました。)
そのファイルが存在するので、以下のコードが機能します。ちなみに、ibm_db_sa
モジュールが John Yの回答 で提案されているように変更されているかどうかに関係なく機能するようですので、そのモジュールはそのままにしておくことをお勧めします。直接インポートされませんが、次のモジュールをインストールする必要があることに注意してください:pyodbc
、ibm_db_sa
、場合によってはfuture
(Python = 2 ...必要かどうか忘れます)Python 3を使用している場合は、urllib
の代わりにurllib.parse
が必要です。 iコンピューターにインストールされている7.1ドライバーにアクセスします。
import urllib
import pandas as pd
from sqlalchemy import create_engine
CONNECTION_STRING = (
"driver={iSeries Access ODBC Driver};"
"system=ip_address;"
"database=database_name;"
"uid=username;"
"pwd=password;"
)
SQL= "SELECT..."
quoted = urllib.quote_plus(CONNECTION_STRING)
engine = create_engine('ibm_db_sa+pyodbc:///?odbc_connect={}'.format(quoted))
df = pd.read_sql_query(
SQL,
engine,
index_col='some column'
)
print df