COPY

Name

COPY  --  ファイルとテーブル間でデータのコピー

Synopsis

COPY [ BINARY ] table [ WITH OIDS ]
    FROM { 'filename' | stdin }
    [ [USING] DELIMITERS 'delimiter' ]
    [ WITH NULL AS 'null string' ]
COPY [ BINARY ] table [ WITH OIDS ]
    TO { 'filename' | stdout }
    [ [USING] DELIMITERS 'delimiter' ]
    [ WITH NULL AS 'null string' ]
  

入力

BINARY

フィールドのフォーマットを全てのデータをテキストではなく バイナリで読み書きするように設定します。バイナリーフォーマットでは、 DELIMITERSとWITH NULLのオプションは無意味となります。

table

存在するテーブルの名前です。

WITH OIDS

それぞれの行に対して内部的に一意のオブジェクトID(OID)をコピーすることを 特定します。

filename

入出力ファイルのUNIX絶対パス名です。

stdin

入力がクライアントアプリケーションからのものかを特定します。

stdout

出力がクライアントアプリケーションへのものかを特定します。

delimiter

ファイルの各行(ライン)のフィールドを区切る文字です。

null string

これは、NULLの値を表す文字列です。デフォルトでは "\N"(バックスラッシュN)です。 しかし、場合によっては、空の文字列の方が良いかも知れません。

Note: コピーをして読み込む際、この文字列と一致するデータ要素はNULL値として格納されます。 したがって、その時には、コピーを行った際に使用した同じ文字列を使用する必要があります。

出力

COPY

コピーは正常に終了しました。

ERROR: reason

エラーメッセージ内の理由によってコピーは失敗しました。

説明

COPYコマンドは、Postgres のテーブルと標準Unixファイル間でデータを移動します。 COPY TOコマンドはテーブルのすべての内容をファイルに コピーします。また、COPY FROMコマンドは ファイルからテーブルへとデータをコピーします。(この時、すでにテーブルにある データにコピー内容を追加します。)

COPYコマンドは、Postgresの バックエンドに対して直接ファイルへの読み書きをするように通告します。 ファイル名が指定された場合は、そのファイルは必ずバックエンドから 接続できる必要があり、またファイル指定はバックエンドの観点から指定される必要があります。 stdinstdoutが指定された場合、 データはクライアントのフロントエンドからバックエンドに流れます。

Tip: COPYpsql\copyとは異るものであることにご注意下さい。 \copyCOPY FROM stdinCOPY TO stdoutを呼び出し、 psqlクライアントから接続できるファイルに データを書き込み/読み込みを行います。したがって、\copy コマンドが使用された場合には、ファイルへの接続と接続権限は、 バックエンドではなく、クライアント側に依存しています。

注釈

キーワードBINARYは全てのデータをテキストではなく、バイナリオブジェクトとして 書き込まれたり読み込まれるようにします。普通のコピーコマンドより いく分か速度が速いですが、バイナリのコピーファイルは移植性がありません。

デフォルトではテキストコピーはフィールドの区別子としてタブ("\t")を使用しています。 フィールドの区別子はUSING DELIMITERSというキーワードを用いて、別の 任意の1文字に変更することができます。区別子にたまたま一致するデータフィールド中の 文字は引用符が付けられます。区別子は必ず1字であることにご注意下さい。 2字以上の文字が指定された場合には、最初の1字が区別子として使用されます。

COPYコマンドによって値が読み込まれたあらゆるテーブルは selectを実行する権限が必要となります。 また、COPYコマンドによって値が挿入されたテーブルには insertupdate権限が必要とあります。 それに加え、バックエンドはCOPYによって読み書きされるファイル に適切なUnixのパーミッションが与えられている必要があります。

COPY TOコマンドはルールを発行したり、列のデフォルトに 働きかけることは行いません。トリガやチェック制約を発行します。

COPYでは、最初のエラーで処理を終了させます。 これは、COPY FROMコマンドを実行している際には 何ら問題はないと思われますが、ターゲットリレーションは COPY TOの始めの行をすでに受け取っています。 これらの行は見えませんし、接続することもできませんが、ディスク領域を 使用します。大きなコピー処理の時に起こった場合には無駄なディスク領域が 増えてしまいます。この無駄な領域を有効にするために、VACUUMを 行う必要があります。

COPYコマンドのファイル名はクライアントではなく、バックエンドが直接 読み込み/書き込みを行います。したがって、それはデータベースのサーバマシンに存在する、 または、サーバから接続可能である必要があります。また、クライアントではなく、 Postgresユーザ(バックエンドが起動しているユーザID)で読み書きができる必要もあります。 COPYコマンドでのファイルを作成は、データベースの スーパーユーザのみが可能です。それは、バックエンドが書き込み可能な あらゆるファイルに対して書き込みを許可するためです。

Tip: psql\copyは クライアントの権限で、クライアントのマシンにて読み書きを行います。 したがって、スーパーユーザの権限は必要ありません。

COPYで指定されるファイル名は絶対パスで記述されることを 推薦しています。COPY TOコマンドの場合ではバックエンドによって 強制的にそうなりますが、COPY FROMコマンドでは 相対パスによって指定されたファイルを読み込むことも可能となっています。 そのパスは、クライアントの作業環境ではなく、バックエンドの作業環境 ($PGDATAの下のどこか)と連携して解釈されます。

ファイル形式

テキスト形式

COPY TOがBINARYオプション無しで使用されると、 生成されたファイルは、それぞれの列(属性)が区別子文字で区切られた 一行ごとの行(インスタンス)から成ります。組み込まれた区別子文字は バックスラッシュ("\")が付きます。属性値そのものはそれぞれの属性 の型に対応した出力関数 によって生成された文字列です。型の出力関数は バックスラッシュ文字の生成に関与してはなりません。COPY 自身がこれを取り扱います。

それぞれのインスタンスの実際の形式は下記のようになります。

<attr1><separator><attr2><separator>...<separator><attrn><newline>
    
すべての行の終りにはUnix形式の改行文字("\n")であることにご注意下さい。 COPY FROMでは、DOSやMac形式の改行が含まれている ファイルに対しては、希望に沿う動作を行いません。

WITH OIDSが指定された場合、OIDが行の先頭に付きます。

COPY TOが出力をファイルではなく、標準出力に出す場合、 最後の行の後の改行のすぐ後にバックスラッシュ("\")とピリオド(".")を送出します。 同様に、COPY FROMが標準入力からデータを読み込む場合は、 ファイルの終了(end-of-file)を規定する行の始めの3文字として、改行と それに引き続くバックスラッシュ("\")とピリオド(".")があることを前提とします。 しかし、この特殊なファイル終了の様式が検出される前に、入力接続が閉ざされた場合、 正常に終了されます(バックエンドも引き続いて終了します。)

バックスラッシュには別の特別な意味があります。リテラルのバックスラッシュは 二つの連続したバックスラッシュ("\\")で表現されます。リテラルのタブ文字は バックスラッシュとタブで表現されます。(区別子としてタブを使用していない場合は、 データを含めるためにその区別子にバックスラッシュを付けて下さい)リテラルの改行は バックスラッシュと改行で表現されます。Postgresで生成されていない テキストデータを読み込む時は、正常に読み込みを行うためにバックスラッシュ文字("\")を 二つのバックスラッシュ("\\")に変換する必要があります。

バイナリ形式

COPY BINARYで使用されるファイル形式は Postgres v7.1で、変更されました。新しい形式はファイルヘッダー、0以上のタプル、 ファイルトレーラーで構成されています。

ファイルヘッダ

ファイルヘッダは24バイトの固定フィールドで構成され、その後に 可変長の拡張ヘッダがあります。修正されたフィールドは下記の通りです。

シグネチャー(Signature)

12バイトのシーケンス"PGBCOPY\n\377\r\n\0" -- NULLはシグネチャーで 必ず必要であることにご注意下さい。(シグネチャーは8ビットではない変換で行われた 際に識別を容易にするためのものです。このシグネチャーは改行変換のフィルターで 変更され、NULLを削除し、大きいビットや、部分修正も削除します。)

整数レイアウトフィールド(Integer layout field)

ソースのバイト順にあるint32の定数0x01020304。正しくないバイト順が感知された場合、 潜在的に読手はその後のフィールドバイト変換と従事できます。

フラグフィールド(Flags field)

重要なファイル形式を示すint32ビットマスク。ビットは0 (LSB)から31 (MSB) まで番号が付けられます。このフィールドがソースのエンディアネスに格納され、 またすべては後続の整数のフィールドです。ビットの16-31は重要なファイル形式に 関連することを示すために予約されています。読手はこの範囲に予期していない ビットの列を発見した際には、そのファイルを破棄する必要があります。 ビットの0-15は順序の両立性のあるファイル形式であるかの合図を行うために 予約されています。読手はこの範囲に予期していないビットの列を発見した際には、 無視して下さい。現在では、1つのフラグビットのみが定義されて、他はすべて ゼロとなります。

Bit 16

もし1ならば、OIDはダンプに含まれます。0の時には含まれません。

拡張ヘッダー領域(Header extension area length)

それ自身を含まない、int32のヘッダの残り。初期のバージョンでは、これは0で、 そのすぐ後に最初のタプルが続きます。今後の形式の変更では、ヘッダに表示させる 情報の追加があるかもしれません。読手は、どのような対処を行えばいいのかが 分からないヘッダに関しては、ヘッダを飛ばす必要があります。

拡張ヘッダ領域は 自己確認のチャンクのシーケンスを保持するために把握されています。 フラグフィールドは読手に拡張領域の内容を知らせるものではありません。特定の 拡張ヘッダ内容のデザインは後のリリースのために残してあります。

このデザインは、順序の両立性のあるヘッダの追加(拡張ヘッダチャンク、 または順序の低いフラグビット)と両立性のない変更(変更を合図するために 順序の高いフラグビットを設定し、必要に応じて拡張領域にサポート情報を追加する) に有効です。

タプル

ゼロ(Zero)

フィールドがNULLで、後続するデータがない

> 0

フィールドは固定長のデータ型で、typlenの後に 丁度Nバイトのデータがある

-1

フィールドはvarlenaデータ型で、次の4バイトはそれ自身も含めた varlenaヘッダーの合計長さ

< -1

後のために保存

NULLではないフィールドに対して、読手は目的列のtyplenが期待された typlenと一致することを確認することができます。これはを簡単ですが、 有益なデータ確認を提供しています。

フィールド間ではアラインパディングや、その他の追加的データはありません。 また、形式でデータ型が参照パスであるか値パスであるかの判断を行わない ことにもご注意下さい。これら両方の規定は故意のもので、ファイルの 移植性を向上させる働きがあるかもしれません(しかし、エンディアネス と浮動少数形式のことなどから、マシン間のファイルの移動はまだ問題があります)。

OIDがダンプに含まれている場合は、OIDのフィールドはフィールドカウント単語の 直後に位置します。これは、他のフィールドとなんら違いはありませんが、フィールド カウントにはカウントされません。typlenを持ち、これで4バイトと8バイトのOIDに 対して処理を行います。また、今後の実装でOIDがオプションとなった場合、OIDを NULLとして表示させます。

ファイル追跡

ファイル追跡は、-1を含んだ、int16の単語から成っています。これは タプルのフィールドカウント単語を使用することによって容易に 見分けることができます。

読手はフィールドカウント単語が-1、または予期されていた列数とは 異なる場合にはその報告を行って下さい。これは、データと共にsync からどうにかして抜けることに対しての追加確認を提供します。

使用方法

下記の例では、フィールドの区別子として縦棒 ("|") を使用し、テーブルを標準出力に出します。

COPY country TO stdout USING DELIMITERS '|';
  

下記のコマンドは、Unixファイルからデータをテーブル "country" にコピーします。

COPY country FROM '/usr1/proj/bray/sql/country_data';
  

下記の例はstdinからテーブルにコピーする時の 有効なデータを示しています。(したがって、最終行に終端を表す並びがあります。)

AF      AFGHANISTAN
AL      ALBANIA
DZ      ALGERIA
ZM      ZAMBIA
ZW      ZIMBABWE
\.
  

各行の空白は実際にはタブであることにご注意下さい。

Linux/i586マシンでのバイナリ形式による同じデータの出力です。 Unixのユーティリティod -cコマンドでフィルタを 行った後にデータが表示されます。テーブルには3つのフィールドがあります。 1つ目は char(2)型、2つ目はtext型、 3つ目はintegerです。すべての行は3つ目のフィールドに NULL値を持っています。

0000000   P   G   B   C   O   P   Y  \n 377  \r  \n  \0 004 003 002 001
0000020  \0  \0  \0  \0  \0  \0  \0  \0 003  \0 377 377 006  \0  \0  \0
0000040   A   F 377 377 017  \0  \0  \0   A   F   G   H   A   N   I   S
0000060   T   A   N  \0  \0 003  \0 377 377 006  \0  \0  \0   A   L 377
0000100 377  \v  \0  \0  \0   A   L   B   A   N   I   A  \0  \0 003  \0
0000120 377 377 006  \0  \0  \0   D   Z 377 377  \v  \0  \0  \0   A   L
0000140   G   E   R   I   A  \0  \0 003  \0 377 377 006  \0  \0  \0   Z
0000160   M 377 377  \n  \0  \0  \0   Z   A   M   B   I   A  \0  \0 003
0000200  \0 377 377 006  \0  \0  \0   Z   W 377 377  \f  \0  \0  \0   Z
0000220   I   M   B   A   B   W   E  \0  \0 377 377
  

互換性

SQL92

SQL92にはCOPY文はありません。