web-dev-qa-db-ja.com

pythonおよびpsycopg2を使用してS3からAWSredshiftにデータをコピーする

コピーコマンドを実行してS3からAmazonのRedshiftにPythonからデータをロードする際に問題が発生します。
次のコピーコマンドがあります:

copy moves from 's3://<my_bucket_name>/moves_data/2013-03-24/18/moves'
credentials 'aws_access_key_id=<key_id>;aws_secret_access_key=<key_secret>'
removequotes
delimiter ',';

SQL Workbench/jを使用してこのコマンドを実行すると、すべてが期待どおりに機能しますが、pythonおよびpsycopg2を使用してこれを実行しようとすると、コマンドはOKを渡しますが、データはロードされず、エラーはスローされません。
次の2つのオプションを試しました(psycopg2接続はOKであるため、OKであると想定します)。

cursor.execute(copy_command)  
cursor.copy_expert(copy_command, sys.stdout)

両方とも警告なしで合格しますが、データはロードされていません

アイデア?

ありがとう

15
Yaniv Golan

この正確なセットアップ(psycopg2 + redshift + COPY)を正常に使用しました。その後コミットしましたか? SQL Workbenchはデフォルトで自動コミットし、psycopg2はデフォルトでトランザクションを開くため、接続でcommit()を呼び出すまでデータは表示されません。

完全なワークフローは次のとおりです。

conn = psycopg2.connect(...)
cur = conn.cursor()
cur.execute("COPY...")
conn.commit()

Copy_expert()またはcursor.copy_ *コマンドのいずれかがRedshiftで機能するとは思わない。

26
Voket

まず、トランザクションがコミット済みであることを確認します。

conn = psycopg2.connect(conn_string)
cur = conn.cursor()
cur.execute(copy_cmd_str)
conn.commit()

次の方法でもトランザクションコミットを保証できます(リソースの解放を保証します)。

with psycopg2.connect(conn_string) as conn:
    with conn.cursor() as curs:
        curs.execute(copy_cmd_str)

接続がwithブロックを終了するときに、ブロックによって例外が発生していない場合、トランザクションはcommittedです。例外の場合、トランザクションはロールバックされます。

次に、commitを実行しても、ロードするデータに時間がかかり、connect_timeoutを超える(そしてコミットできない)場合は役に立ちません。したがって、明示的なコミットが役に立たない場合は、タイムアウトを増やしてみてください。

14
str

sqlalchemyを使用している場合、copyコマンドはそれ自体では自動コミットされません。これは私のために働いた:

from sqlalchemy import create_engine
eng = create_engine(...)
command = """
copy command here
"""
conn = eng.connect()
result = conn.execution_options(autocommit=True).execute(command)
result.close()
2
jerrytim