38
- 1 - STDIO.PL リファレンス STDIO.PL VERSION 9 by WEB POWER はじめに STDIO.PL(STandarD Input Output – Perl Library) は、 CGI 用の Perl ライブラリです。ブラウザから送信さ れたフォームデータの取得、クッキーのやり取りやメール送信などの、CGI におけるクライアント( ブラウザ) サーバーとの標準的な入出力を行うための関数を集めたライブラリです。 フォームデータの取得やクッキーのやり取りは、 CGI に必要不可欠な処理ですが、その処理方法はほとんど同 じようなものです。 stdio.pl は、このような CGI の定石といえるコードを集めて、ライブラリとして簡単に使え るようにしました。 例えば、CGI でメールを送信するコードを書く場合、sendmail へのパイプを開き、宛先や件名を含むヘッダ ーと本文を出力します。日本語を使用する場合は、電子メールの規格に基づいて、JIS に変換する必要がありま す。ヘッダー内の日本語や、添付ファイルは、 MIME エンコードする必要があります。これらを行うコードを普 通に書くと、数十行にもおよびますが、 stdio.pl を使えば、たった一行で書くことができます。このように、 stdio.pl CGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントは stdio.pl の関数リファレンスマニュアルです。 stdio.pl の全関数について、引数と戻り値の 書式・意味・使い方を、サンプルコードを交えて解説しています。 stdio.pl が、少しでもあなたの CGI プログラミングのお役に立てれば幸いです。 2003 8 1 WEB POWER ライブラリのソースコード、本ドキュメント、及びサンプルプログラムの著作権は WEB POWER に帰属します。使用条件の 範囲でご使用ください。STDIO.PL - Copyright©2004 WEB POWER. All Rights Reserved. 最新情報・最新版は、http://www.webpower.jp/ で提供してします。 記載の会社名及び製品名は各社の商標、もしくは登録商標です。文中では、特に TM ®マークは明記しておりません。

STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

  • Upload
    others

  • View
    2

  • Download
    0

Embed Size (px)

Citation preview

Page 1: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 1 -

SSTTDDIIOO..PPLL リリフファァレレンンスス

STDIO.PL VERSION 9 by WEB POWER

はじめに

STDIO.PL(STandarD Input Output – Perl Library)は、CGI用のPerlライブラリです。ブラウザから送信さ

れたフォームデータの取得、クッキーのやり取りやメール送信などの、CGI におけるクライアント(ブラウザ)とサーバーとの標準的な入出力を行うための関数を集めたライブラリです。 フォームデータの取得やクッキーのやり取りは、CGIに必要不可欠な処理ですが、その処理方法はほとんど同

じようなものです。stdio.plは、このようなCGIの定石といえるコードを集めて、ライブラリとして簡単に使え

るようにしました。 例えば、CGI でメールを送信するコードを書く場合、sendmail へのパイプを開き、宛先や件名を含むヘッダ

ーと本文を出力します。日本語を使用する場合は、電子メールの規格に基づいて、JIS に変換する必要がありま

す。ヘッダー内の日本語や、添付ファイルは、MIMEエンコードする必要があります。これらを行うコードを普

通に書くと、数十行にもおよびますが、stdio.plを使えば、たった一行で書くことができます。このように、stdio.plはCGI-Perlにおけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントは stdio.plの関数リファレンスマニュアルです。stdio.plの全関数について、引数と戻り値の

書式・意味・使い方を、サンプルコードを交えて解説しています。 stdio.plが、少しでもあなたのCGIプログラミングのお役に立てれば幸いです。

2003年8月1日 WEB POWER

ライブラリのソースコード、本ドキュメント、及びサンプルプログラムの著作権はWEB POWER に帰属します。使用条件の

範囲でご使用ください。STDIO.PL - Copyright©2004 WEB POWER. All Rights Reserved. 最新情報・最新版は、http://www.webpower.jp/ で提供してします。 記載の会社名及び製品名は各社の商標、もしくは登録商標です。文中では、特に TM、®マークは明記しておりません。

Page 2: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 2 -

CONTENTS はじめに ······························································································································1 コンテンツ ···························································································································2 ライブラリの使い方···············································································································3 関数リファレンス ●セッション・クッキー管理

setCookie (クッキーセット)······································································································6 getCookie (クッキー取得)·········································································································8 setSession (セッションセット) ·································································································9 getSession (セッション取得) ····································································································9

●フォームデータ処理 getFormData (フォームデータ取得)·························································································· 11 getUrlencodedFormData (URLエンコードフォームデータ取得) ················································· 11 getMultipartFormData (マルチパートフォームデータ取得)························································· 11 setQueryString (クエリー文字列設定)······················································································· 14 setHiddenForm (Hiddenフィールド設定) ················································································· 14

●時間処理 getTime (書式を指定して時間取得) ··························································································· 15 getSerialTime (年月日時分秒からUTCシリアル値を取得) ·························································· 17

●エンコード・デコード base64encode (Base64エンコード)··························································································· 18 base64decode (Base64デコード)······························································································ 18 urlencode (URLエンコード) ···································································································· 19 urldecode (URLデコード) ······································································································· 19

●文字列処理

trString (文字列を置換) ··········································································································· 20 searchString (マルチ文字列検索)······························································································ 21 getRandomString (ランダムな文字列を作成) ············································································· 24 setLink (文字列中のURIをリンク)··························································································· 25 setComma (数字に3桁毎にカンマ設定) ···················································································· 26

●ファイルロック lock (ファイルロック)·············································································································· 27 unlock (ファイルロック解除)···································································································· 27 lockCheck (ファイルロック中確認) ··························································································· 27

●ソケット通信 openSocket (ソケット確立・URIに接続)··················································································· 29 closeSocket (ソケット解放) ······································································································ 29

●その他 sendmail (sendmailコマンドによるメール送信)········································································· 31 shuffleArray (配列をシャッフル) ······························································································ 34 getImageSize (GIF/JPEG/PNGのピクセルサイズ取得) ······························································ 35 getMimeType (ファイル名からMIMEタイプ取得)····································································· 36

クイックリファレンス············································································································37

Page 3: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 3 -

STDIO.PLの使い方 このマニュアルは、stdio.pl に収録されている全関数を解説したリファレンスです。各関数を書式、機能とサ

ンプルコードを掲載して解説しています。 リファレンスの見方

リファレンスで使用されている関数の書式の意味は、下記の通りです。

[ ] で囲まれた引数は、省略可能です。

(参照)は変数へのリファレンス(Perl4では型グロブ)を表します。

偽は未定義値・空値・数字の0を、真はそれ以外のデータです。

使用上の注意

付属のライブラリ、サンプルプログラムやマニュアルは、すべてユーザーの自己責任で使用してください。

それらを使用したことによって生じた、いかなる直接的・間接的損害に対しても、作者は一切の責任を負い

ません。 付属のライブラリ、サンプルプログラムとマニュアルの著作権は作者に帰属します。使用条件は、それぞれ

に付属しているドキュメントを参照してください。 各関数やサンプルプログラムの完全な動作保証はありません。サーバーOS や設定によっては意図した通り

に動作しない場合があります。プロバイダの Web サーバーを使用している場合、プロバイダによって実行

環境が制限されている場合があります。動作環境については各プロバイダかサーバー管理者に問い合わせて

ください。

プログラミング上の注意

◆いきなりサーバー上で動作させない

作成したばかりのプログラムを、いきなりサーバー上で動作させるのは危険です。作成したばかりのプロ

グラムは、未知のバグやセキュリティーホールを含んでいる可能性が多々あります。まずは、自分のパソコ

ンに、サーバーソフトとPerlをインストールして、正しく動作するかを確認してください。問題がないこと

を確認してからサーバー上で動作させるようにしてください。

◆セキュリティー対策はプログラマの責任で stdio.pl では、引数などの汚染チェックは一切行っていません。ユーザー入力(フォームデータ、クッキー

などの HTTP ではじまる環境変数)を引数に使う場合は、必ず汚染チェックを行ってください。これを怠る

と、重大なセキュリティーホールに繋がります。

◆メールの送信テストは必ず実在するアドレス宛に 適当なアドレス宛に送信すると、エラーメールの発生によるサーバーへの負荷となったり、第三者に不要

メールとして届いたりすることになり、第三者に迷惑がかかります。メールの送信テストをする場合は、必

ず実在する有効なアドレス宛にしてください。 ライブラリのロード

stdio.plの関数を呼び出す前に、stdio.pl自体を require関数でロードします。

require "stdio.pl";

Page 4: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 4 -

関数の呼び出し

stdio.plの関数を呼び出す場合は、関数名をパッケージ名「stdio」で修飾します。 一部の関数では、文字コードの処理に jcode.pl を使っています。そのような関数を呼び出す場合は、事前に

jcode.plもロードしておく必要があります。

戻り値 = stdio::関数名(引数); (Perl4の場合はstdio’関数名となる) 例) getImageSize関数を呼び出す ($type, $width, $height) = stdio::getImageSize($file);

値渡しと参照渡し

関数を呼び出す際の引数の指定方法には、値渡しと参照渡しがあります。値渡しとは、変数の中身をコピーし

て関数に渡す方法です。参照渡しとは、変数への参照(ポインタ)を渡す方法です。 値渡しは、リファレンス以外が格納された変数、もしくは値をそのまま渡します。参照渡しは、変数へのリフ

ァレンス(Perl4の場合は型グロブ)を渡します。関数リファレンスで、「スカラー(参照)」、「配列(参照)」と「ハッ

シュ(参照)」とある引数は、参照渡しである必要があります。stdio.plの関数で、ハッシュ変数や配列変数を渡す

場合、そのほとんどが参照渡しとなっています。

▼例1. 値渡しの例 stdio::getImageSize("image.gif");

▼例2. 参照渡しの例 (変数名の前に"\"を付けるとその変数へのリファレンスを取得) stdio::sendmail(¥%header, $body);

▼例3. 参照渡しの例 ($headerには%headerへのリファレンスが格納されている) $header = ¥%header; stdio::sendmail($header, $body);

▼例4. 参照渡しの例 (無名ハッシュ変数へのリファレンスを渡す) stdio::sendmail({To=>'*',From=>'*',Subject=>'*'}, $body); ※ %hash = (key1=>val1, key2=>val2, ..)のように、配列(ハッシュ)要素をカンマで区切って括弧を付けると、通常の配列(ハッシュ)変数を取得する。上の例のように、括弧を中括弧にすると、無名配列(ハッシュ)変数へのリファレンスを取得する。

■値渡しと参照渡しの両方に対応した関数

関数によっては、値渡しと参照渡しの両方ができるものがあります。base64encode/base64decode 関数、

urlencode/urldecode 関数、trString 関数と setLink 関数がそれに該当します。値渡しで呼び出す場合は、例 6のように関数名の後にアンダースコアを付けます。 両者の違いですが、値渡しの場合、引数の値をコピーするため、参照渡しに比べてパフォーマンスが若干低下

します。参照渡しは変数への参照(ポインタ)を渡すため高速ですが、元に値が書き換えられます。元の値を保持

する場合や戻り値が必要な場合は値渡しを、それ以外は参照渡しといったように状況によって使い分けると良い

でしょう。

▼例5. 参照渡しの例 ($strの中身を書き換える) stdio::urlencode(¥$str);

▼例6. 値渡しの例 ($strの中身はそのまま。処理された値は戻り値で取得する。) $new_str = stdio::urlencode_($str);

Page 5: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 5 -

パッケージ変数 stdio.pl では以下のパッケージ内グローバル変数が定義されています。プログラム実行中に参照・変更する場

合は、stdio.plをロードした後に、パッケージ名「stdio」で変数名を修飾します。 ■version (stdio.plのバージョン情報)

stdio.plのバージョン情報が"stdio.pl/8.1x"の形式で入っています。 ■max_byte (最大受信バイト数)

getFormData/getMultipartFormData/getUrlencodedFormData関数で、受け取るデータの 大バイト数

を指定します。128K バイトを超える値を設定した場合、マルチパートフォームデータでアップロードされ

たファイルをサーバー側に保存する場合は、そこで指定した値まで受け取れますが、ハッシュ変数に格納さ

れる上限は128Kバイトになります。(サイズ上限の詳細はリファレンスのページを参照してください。)

$stdio::max_byte = 1048576;

■ses_byte (セッションファイルのレコードサイズ)

setSession/getSession関数で使用するセッションファイルのレコードサイズを指定します。セッションフ

ァイルはレコードサイズが固定長のランダムファイルです。

$stdio::ses_byte = 1024;

■tmp_dir (テンポラリファイルを格納するディレクトリのパス)

テンポラリファイルを格納するディレクトリのパスを指定します。このディレクトリには書き込み属性が

必要です。ここで指定されたディレクトリは、sendmail関数で添付ファイルのキャッシュ使用時に、キャッ

シュファイルが作成されます。また、setSession/getSession 関数、getFormData/getMultipartFormData関数と lock/unlock/lockCheck関数で、パスを指定する引数で、「///」で始まるパスを指定すると、「///」がこ

こで指定したディレクトリに置換されます。

$stdio::tmp_dir = '/tmp/';

■sendmail (sendmailコマンドのパス)

sendmailコマンドのパスを指定します。この変数は、sendmail関数を使う場合に必要です。

$stdio::sendmail = '/usr/lib/sendmail';

■inet (socket関数呼び出し時のドメイン)

socket関数の第2引数に指定するドメインです。初期値では1ですが、この値はサーバーによって異なる

場合があります。Socket.pm モジュールがロードされている場合は、PF_INET 関数の戻り値が指定される

ため、ここでの指定は無視されます。この変数は、openSocket関数を使う場合に必要です。

$stdio::inet = 2;

■stream (socket関数呼び出し時のタイプ)

socket関数に第3引数に指定するタイプです。初期値では1ですが、この値はサーバーによって異なる場

合があります。Socket.pmモジュールがロードされている場合は、SOCK_STREAM関数の戻り値が指定さ

れるため、ここでの指定は無視されます。この変数は、openSocket関数を使う場合に必要です。

$stdio::stream = 1;

Page 6: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 6 -

ssseeetttCCCooooookkkiiieee クライアントにクッキーを渡す

◎ = stdio::setCookie(☆[,★[,□[,■[,○[,●[,△]]]]]])

☆ : ハッシュ(参照) クッキーのデータを格納したハッシュ変数へのリファレンス(型グロブ) 配列(参照) クッキーのデータを格納した配列変数へのリファレンス(型グロブ) ★ : スカラー クッキーID(省略時はスクリプトのファイル名) □ : スカラー クッキーの有効期限(有効秒数/有効期限/-1:直ちに削除/偽:セッション内) ■ : スカラー クッキーの有効範囲(仮想パス) ○ : スカラー クッキーの有効範囲(ドメイン) ● : スカラー セキュア時のみクッキー発行(真:する/偽:しない) △ : スカラー クッキーの値を戻り値に返す(真:する/偽:しない) ◎ : スカラー クッキーの値(第7引数でクッキーの値を返すようにした場合)

setCookie 関数は、引数からHTTP クッキー(Cookie)を作成して、それを標準出力に出力、もしくはその値を

戻り値として返します。 クッキーとは、Webサーバーとブラウザとの間でテキスト情報をやり取りする仕組みです。サーバーから送信

されたクッキーは、ブラウザを経由して、クライアントのハードディスクに一定期間保存され、次に同じ Webサイトにアクセスした時に、保存されているクッキーをブラウザ経由でサーバーに渡します。クッキーは ID(名前)、値、有効期限と有効範囲を持ちます。 クッキーは多くのブラウザが標準サポートしているため、ユーザーを識別したり、セッションを保持したりす

るために、ポータルサイトを始めとする多くのサイトで使われています。 クッキーの有効期限

クッキーの有効期限は第3引数で指定します。日時(Fri, 31-Dec-1999 23:59:59 GMTの形式)で指定した場合は、

その日時が有効期限になります。整数で指定した場合は、クッキーの発行日時を基準とした有効秒数になります。

偽、もしくは省略した場合は、セッション内(ブラウザを終了するまで)が有効期限になります。-1 を指定した場

合は、過去の日時が指定され、クッキーは直ちに破棄されます。 クッキーの有効範囲

クッキーを返す有効範囲(ドメイン名と仮想パス)を第 4 引数と第 5 引数で指定します。第 4 引数では、クッキ

ーを返す仮想パスを指定します。ブラウザは、この仮想パスに一致するすべてのファイルに対してクッキーを返

します。共用ドメインのサーバーで、不用意に「/」とすると、同じドメイン名のすべての Web サイトにクッキ

ーを返してしまいますので、指定の際は注意が必要です。省略時は、クッキーを発行した仮想パスになります。 第5引数では、クッキーを返すドメイン名を指定します。ブラウザは、このドメインに対してのみクッキーを

返します。例えば、「hostname.ne.jp」を指定すると、hostname.ne.jp に対してのみクッキーを返します。

「.hostname.ne.jp」を指定すると、「aaa.hostname.ne.jp」や「bbb.hostname.ne.jp」のようにhostname.ne.jpのサブドメインに対してもクッキーを返します。省略時は、クッキーを発行したドメイン名になります。 クッキーのIDと値

クッキーの IDは、第2引数で指定します。省略した場合は、スクリプトのファイル名がクッキーIDになりま

す。クッキーの値は、第1引数で指定します。第1引数には、ハッシュ変数か配列変数へのリファレンス(型グロ

ブ)を指定します。ハッシュで渡したクッキーはハッシュで受け取り、配列で渡したクッキーは配列の形で受け取

Page 7: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 7 -

ります。 戻り値にクッキーの本体を返す

第 7 引数で真を指定した場合、クッキー本体が戻り値になります。偽を指定した(省略した)場合は、クッキー

は標準出力(STDOUT)に出力されます。HTMLの<meta http-equiv="Set-Cookie" content="~" />要素(②参照)でセットする場合や、JavaScript でセット(③参照)する場合は、第7 引数に真を指定し、戻り値でクッキーの本

体を取得して、HTMLの属性値やJavaScriptのパラメータにセットします。 記記 述述 例例

$cookie = stdio::setCookie(¥%cookie, $cookie_id, $expires, $path, $domain, $secure,

$return_value);

ササンンププルル

# ① Contentヘッダーでクッキーを設定 (7200秒=2時間後にクッキー削除) print "Content-Type: text/html¥n";

stdio::setCookie(¥%cookie, "MyCookie", 7200);

print "¥n";

# ② HTMLのMETAタグでクッキーを設定 (ブラウザを終了するとクッキー削除) $cookie = stdio::setCookie(¥%cookie, "MyCookie", "", "", "", "", 1);

print qq|<meta http-equiv="Set-Cookie" content="$cookie" />¥n|;

# ③ JavaScriptでクッキーを設定 (過去の日付を指定してクッキー削除) $cookie = stdio::setCookie(¥%cookie, "MyCookie", -1, "", "", "", 1);

print qq|<script type="text/javascript">¥n|;

print qq|<!--¥n|;

print qq| document.cookie = "$cookie"; ¥n|;

print qq|// -->¥n|;

print qq|</script>¥n|;

Tips 携帯電話でクッキーは?

残念ながら i-modeなどの携帯電話では、現時点でクッキーはサポートされていません。しかし、一部の旧端末を除いて、ユーザー

エージェントに utn という個体識別情報(ユニークなコード)を付加して送らせることができます。このコードを取得することで、

i-modeでもセッション管理ができます。i-modeでutnを送るようにするには、HTMLのa要素や form要素にutn属性を付け加え

ます。(プライバシー保護のため、その都度確認ダイアログが表示されます。) CGI側では、このutnをセッション IDとして、stdio.plのsetSession/getSession関数を使えばクッキーと同等の機能を実装できます。

参考⇒ http://www.nttdocomo.co.jp/p_s/imode/tag/utn.html

Page 8: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 8 -

gggeeetttCCCooooookkkiiieee クライアントからクッキーを取得

◎ = stdio::getCookie(☆[,★])

☆ : ハッシュ(参照) クッキーのデータを格納するハッシュ変数へのリファレンス(型グロブ) 配列(参照) クッキーのデータを格納する配列変数へのリファレンス(型グロブ) ★ : スカラー クッキーID(省略時はスクリプトのファイル名) ◎ : リスト キーのリスト(処理された順番通り)/取得できなかった場合は無し

getCookie 関数は、setCookie 関数でセットしたクッキーをブラウザから受け取ります。第 1 引数に、受け取

ったクッキーを格納するハッシュ変数、もしくは配列変数へのリファレンスを指定します。setCookie 関数で、

ハッシュで渡したクッキーはハッシュで受け取り、配列で渡したクッキーは配列で受け取る必要があります。 記記 述述 例例

@keys = stdio::getCookie(¥%COOKIE, $cookie_id);

ササンンププルル

# クッキーを格納するハッシュ変数を定義してクッキーを受け取る %COOKIE = ();

@keys = stdio::getCookie("MyCookie", ¥%COOKIE);

# 受け取ったクッキーを書き出す foreach (@keys) {

print "$_ : $COOKIE{$_}¥n";

}

Tips クッキーっておいしいの?

クッキーはユーザーの追跡や識別など色々使えて、とてもおいしい機能ですが、使用するにあたっては注意しなければいけな

いことがあります。プライバシーとセキュリティーの問題です。 IE6ではP3Pが採用され、クッキーの受け入れを細かく指定できるようになりました。デフォルトでは、サードパーティ(他のサイ

ト)のクッキーは原則拒否するようになっています。これは、ユーザーのプライバシーに対する意識の向上の結果でもあります。クッ

キーの使用は必要 小限にとどめ、どのような目的でクッキーを使用するかをプライバシーポリシーとしてサイト内に掲載するよう

にしましょう。 ブラウザから渡されるクッキーはユーザーの自己申告にすぎません。ユーザーがクッキーの値を改変して、サーバーに渡すこ

とも可能です。そのため、クッキーの値をファイル処理系の関数などに渡す場合、必ず汚染チェックをしましょう。また、ネッ

ト上を流れるクッキー情報は第三者から盗まれる可能性もあります。 これらの問題により、サイト運営者から見れば、クッキーは以前ほどおいしくはなくなってきているようです。

Page 9: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 9 -

ssseeetttSSSeeessssssiiiooonnn /// gggeeetttSSSeeessssssiiiooonnn セッション管理

◎ = stdio::setSession(☆[,★[,□[,■]]])

◎ = stdio::getSession(☆,★[,□[,○]])

☆ : スカラー セッション管理ファイルのパス(このディレクトリには書き込み属性が必要) ※ パスの指定が「///」で始まる場合は、「///」は$stdio::tmp_dirで指定した値に置換。

★ : ハッシュ(参照) セッション情報を格納するハッシュ変数へのリファレンス(型グロブ) ※ setSession関数では、省略した場合や偽の場合はセッション情報削除。

□ : スカラー セッション ID(省略時は IPアドレス) ■ : スカラー 有効秒数(省略時は3600秒=1時間) ○ : スカラー 当該セッションを(-1:読み出し後セッション削除/1以上:有効秒数延長) ◎ : スカラー 1以上:成功(レコードサイズを返す) /空値:セッションファイル破損/ 0:失敗(ファイル入出力失敗・セッション IDが見つからない)

setSession/getSession関数は、セッション管理のためのハッシュ形式でのファイル入出力を行う関数です。ク

ッキーはクライアントのハードディスクに保存されますが、この関数ではサーバーにファイルとして保存します。

ただ保存するのではなく、クッキーと同じように、ID(識別名)と有効期限を付けて、ハッシュの形で保存して、

ハッシュの形で取り出すことができます。 セッションファイルのレコードサイズ

setSession/getSession関数の扱うセッション情報ファイルは、レコードサイズが固定長のランダムファイルで

す。バイナリファイルですので、FTPで送受信する場合、バイナリモードにする必要があります。また、テキス

トエディタなどで不用意に編集すると、破損させてしまう可能性があります。1 バイトでもレコードサイズが変

わってしまうと、読み書きできなくなりますので、直接編集は極力避けるようにしましょう。 ■レコードサイズ レコードサイズは固定長のため、1 つのセッション情報として保存できる 大バイト数には制限があります。

レコードサイズは stdio.pl のパッケージ変数$stdio::ses_byte で設定します。stdio.pl をロードした後に設定する

には、パッケージ名で修飾して、以下のようにします。 require 'stdio.pl'; $stdio::ses_size = 1024;

レコードサイズはセッションファイル毎に異なってもかまいませんが、一度作成したセッションファイルのレ

コードサイズは途中から変更できません。変更する場合は、セッションファイルをいったん削除する必要があり

ます。 1 つのレコードは、セッション ID、有効期限とセッション情報で構成され、これにセパレータが加わります。

また、セッション IDとセッション情報に含まれる半角英数字以外の文字列はURLエンコードされます。このレ

コードサイズが、$ses_byteで指定したサイズを超えた場合、超過分は強制的にカットされます。 レコードサイズは取り扱うセッション情報に応じて、弾力的に設定しましょう。セッション情報が小さい情報

の場合はレコードサイズを小さめに、逆に大きい情報の場合やそれが予想される場合は、レコードサイズは大き

めにしましょう。レコードサイズを設定する場合、想定されるセッション情報のサイズより、ある程度余裕を持

って設定しておくことをお勧めします。

Page 10: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 10 -

記記 述述 例例

$result = stdio::setSession($session_file, ¥%session, $session_id, $expires);

$result = stdio::getSession($session_file, ¥%session, $session_id, $expires);

ササンンププルル

# IPをセッションIDとしたセッション情報(ハッシュ変数)を読み出す %session = ();

stdio::getSession($ses_file, ¥%session);

# IPをセッションIDとしているセッション情報を解放する stdio::setSession($sef_file);

# IPをセッションIDとしてセッション情報を書き込む stdio::setSession($ses_file, ¥%session);

Page 11: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 11 -

gggeeetttFFFooorrrmmmDDDaaatttaaa /// gggeeetttUUUrrrllleeennncccooodddeeedddFFFooorrrmmmDDDaaatttaaa /// gggeeetttMMMuuullltttiiipppaaarrrtttFFFooorrrmmmDDDaaatttaaa 標準入力(クエリー文字列)からデータ(ファイル)取得

◎ = stdio::getFormData(☆[,★[,□[,■[,○]]]])

◎ = stdio::getUrlencodedFormData(☆[,★[,□[,■]]])

◎ = stdio::getMultipartFormData(☆[,★[,□[,■[,○]]]])

☆ : ハッシュ(参照) 標準入力データを格納するハッシュ変数へのリファレンス(型グロブ) ★ : スカラー タグ構成文字を実体参照(< > & " → &lt; &gt; &amp; &quot;)に置換

(1:する/2:する ※ 改行は<br />に置換/偽:しない) □ : スカラー 変換文字コード(sjis/jis/euc/SJIS/JIS/EUC) ※大文字の場合は半角カタカナを全角に置換

■ : スカラー 同一キーがあった場合の処理(真:それをセパレータとして追記/空値:上書き) ○ : スカラー アップロードされたファイルを格納するディレクトリのパス

※ ディレクトリには書き込み属性が必要。省略時はハッシュ変数にそのまま格納。 ※ パスの指定が「///」で始まる場合は、「///」は$stdio::tmp_dirで指定した値に置換。

◎ : リスト キーのリスト(処理された順番通り)/取得できなかった場合は無し

getFormData/getUrlencodedFormData/getMultipartFormData関数は、標準入力(クエリー文字列)からのデ

ータを取得し、デコード処理を行って、ハッシュ変数に格納します。ブラウザから送信されたフォームデータを

取得する関数で、CGIでは も基本となる処理を行います。 getFormData 関数は、通常のフォームデータ(URL エンコードされたフォームデータ)とマルチパートフォー

ムデータの両方を取得します。getMultipartFormData関数は、マルチパートフォームデータ(添付ファイル付き)のみを、getUrlencoded-FormData関数は、通常のフォームデータのみを取得します。 デコード処理以外に、文字コード変換(jcode.pl要)、タグ構成文字の実体参照への置換、半角カタカナの全角変

換も行います。 戻り値

この関数は、処理したキーを順番通りに格納したリスト(配列)を戻り値として返します。標準入力データはハ

ッシュ変数に格納されますが、ハッシュは配列と異なり、先頭や末尾といった順番がありません。each関数でハ

ッシュの値を1つずつ取り出しても、取り出される順番は、格納した順番通りにはなりません。順番通りの処理

が必要な場合は、サンプルコードのように戻り値のリスト(配列)を使います。 重複するキーの扱い

送信フォームの select要素にmultiple属性を指定している場合などで、同じ名前のキーが複数送信される場合

があります。このような場合に、後から送信されたキーの値で古い値を上書きするか、追記するかを第4引数で

指定します。省略した場合や、未定義値や空値の場合は上書きされ、それ以外の場合は、引数の値をセパレータ

として追記します。 例えば、次に示すデータがフォームから送信されて、それをハッシュ変数"%PARAM"に格納するとします。

name=Taro&name=Jiro&name=Saburo&[email protected]

通常は上書きされるため、$PARAM{'name'}には、"Saburo"が入ります。ただし、第4引数に真を指定してい

た場合、第4引数の文字をセパレータとして追記します。第4引数に"¥t"(タブ)を指定した場合、$PARAM{'name'}は、次のようになります。

Taro> Jiro> Saburo (※ >はタブを表します)

Page 12: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 12 -

マルチパートフォームデータ

マルチパートフォームデータ(ブラウザからアップロードされたファイル)は、通常はそのままハッシュ変数に

格納されます。ただし、第5引数に書き込み可能なディレクトリのパスを指定することで、アップロードされた

ファイルをそのディレクトリ内にファイルとして保存できます。アップロードされたファイルのサイズが小さく、

テキストとして処理したい場合は前者を、それ以外の場合は後者を使うとよいでしょう。なお、前者の場合は、

ハッシュ変数に格納できる 大容量はテキストと合わせて128Kバイトになります。(後述) アップロードされたファイルを保存する場合、ファイル名にはユニークな名前が付けられます。ハッシュ変数

の値には、サーバー側での保存されているパスが格納されます。このパスは配列変数(@stdio::file)にも格納され

ます。これ以外にも、ファイルに関する情報が格納され、それらはハッシュ変数のキーに"->***"を付けることで

取得できます。 ▼ハッシュ変数に同時に格納されるファイル情報

* サーバー側での保存されているパス (例 file/1058337893-1.tmp)

*->name クライアント側でのファイル名 (例 image.gif)

*->path クライアント側でのパス (例 C:¥Document and Settings¥User¥image.gif)

*->type ファイルのMIMEタイプ (例 image/gif)

*->size ファイルサイズ (例 38641)

送信データの上限

この関数が処理可能なデータサイズの上限は、128K(131,072)バイト、もしくは stdio.pl のパッケージ変数

$stdio::max_byteで指定した値の、どちらか小さい方です。これを超えると処理を中断して、戻り値には何も返

しません。ただし、マルチパートフォームデータでアップロードされたファイルをサーバーに保存する場合、そ

のファイルに対してのみ、128Kバイト制限はされず、$max_byteの値が上限になります。 $max_byteは stdio.plの冒頭で定義していますので、必要に応じて変更してください。メインプログラムの中

で変更したい場合は、stdio.plをロードした後に、パッケージ名で修飾して次のようにします。 require 'stdio.pl'; $stdio::max_byte = 1048576 * 10;

※この値がフォームデータで受け取る上限サイズです。128KBを超える値を設定した場合でも、通常のテキストデータ、アップロー

ドされたファイルであってもサーバーにファイル保存せずにハッシュ変数(メモリ)に格納する場合は、ハッシュ変数のサイズ128K

バイトが上限になります。

※マルチパートフォームデータでアップロードされたファイルをサーバーに保存する場合、$max_byte で指定したサイズ内であれば

制限ありません。非常に大きい値を指定した場合、サーバーの使用可能容量には十分注意してください。

その他

データのセパレータは"&"と";"が使えます。 タグ構成文字を実体参照に置換する場合は、第2引数に真を指定します。< > & " は、それぞれ &lt; &gt; &amp; &quot; に置換されます。第2引数に2を指定すると、実体参照への置換に加えて、改行を<br />に置換します。

文字コードの変換を行う場合、第 3 引数に変換する文字コード(sjis/euc/jis)を指定します。大文字

(SJIS/EUC/JIS)を指定した場合は、文字コードの変換に加えて、半角カタカナを全角に置換します。文字

コード変換、半角カタカナの全角変換は、jcode.plがロードされている必要があります。 記記 述述 例例

@keys = stdio::getFormData(¥%PARAM, 2, $jcode, $separator, $file_dir);

@keys = stdio::getMultipartFormData(¥%PARAM, 2, $jcode, $separator, $file_dir);

@keys = stdio::getUrlencodedFormData(¥%PARAM, 2, $jcode, $separator);

Page 13: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 13 -

ササンンププルル

#### サンプルプログラム① ####

#フォームデータを格納するハッシュ変数を定義してフォームデータを受け取る %PARAM = ();

@keys = stdio::getFormData(¥%PARAM);

# 順番通りに書き出す foreach (@keys) {

print "$_ = $PARAM{$_}¥n";

}

#### サンプルプログラム② ####

# フォームデータを格納するハッシュ変数を定義してフォームデータを受け取る %PARAM = ();

@keys = stdio::getMultipartFormData(¥%PARAM, 2, "EUC", "", $file_dir);

# 順番通りに書き出す foreach (@keys) {

# 添付ファイルの場合 ($PARAM{$_}には添付ファイルのパスが格納されている) if ($PARAM{"$_->name"}) {

print qq|$key = 添付ファイル($PARAM{"$_->path"} $PARAM{"$_->size"}バイト)¥n|;

# 通常のファイルの場合 } else {

print "$key = $PARAM{$key}¥n";

}

}

▼ ①の実行結果 (引数:name=%C2%C0%CF%BA&[email protected]&uri=http%3A%2F%2Fwww.hostname.co.jp%2F)

name = 太郎 mail = [email protected]

uri = http://www.hostname.co.jp/

▼ ②の実行結果

name = 次郎 mail = [email protected]

file = 添付ファイル(C:¥Document and Settings¥User¥image.gif 342バイト)

Page 14: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 14 -

ssseeetttQQQuuueeerrryyySSStttrrriiinnnggg /// ssseeetttHHHiiiddddddeeennnFFFooorrrmmm ハッシュからクエリー文字列・HIDDENフィールドを作成

◎ = stdio::setQueryString(☆[,★[,□[,■]]])

◎ = stdio::setHiddenForm(☆[,★[,□[,■]]])

☆ : ハッシュ(参照) ハッシュ変数へのリファレンス(型グロブ) ★ : 配列(参照) (順番を指定のための)配列変数へのリファレンス(型グロブ) □ : スカラー 各項のセパレータ(省略時: setQueryString関数は";"、setHiddenFormは"¥n") ■ : スカラー 値が空の場合は項目自体をカット(1:する/0:しない) ◎ : スカラー 作成されたクエリー文字列・HIDDENフィールド

setQueryString関数は、ハッシュ変数からクエリー文字列を作成します。setHiddenForm関数は、ハッシュ

変数からフォームの隠しフィールド(<input type="hidden" … />)を作成します。 記記 述述 例例

$query_string = stdio::setQueryString(¥%hash, ¥@array, $separator, $cut_novalue_key);

$hidden = stdio::setHiddenForm(¥%hash, ¥@array, $separator, $cut_novalue_key);

ササンンププルル

# クエリー文字列を格納するハッシュ変数を定義 %PARAM = (

'keyword' => 'CGI プログラム', 'max' => '20'

);

# ① クエリー文字列を作成・表示 $query_string = stdio::setQueryString(¥%PARAM);

print qq|<a href="search.cgi?$query_string">検索</a>¥n|;

# ② 隠しフィールドを作成・表示 $hidden = stdio::setHiddenForm(¥%PARAM);

print $hidden;

▼ ①の実行結果

<a href="search.cgi?keyword=CGI+%a5%d7%a5%ed%a5%b0%a5%e9%a5%e0;max=20">検索</a>

▼ ②の実行結果

<input type="hidden" name="keyword" value="CGI プログラム" /> <input type="hidden" name="max" value="20" />

Page 15: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 15 -

gggeeetttTTTiiimmmeee フォーマットを指定して時間を取得

◎ = stdio::getTime([☆[,★[,□]]])

☆ : スカラー 書式(省略時はgmtime関数をスカラー評価した時と同じ書式) ★ : スカラー GMT(グリニッジ標準時=英国ロンドン)との秒差 (日本は3600*9) □ : スカラー 基準ミリ秒(省略時は現在時間=time関数の戻り値) ◎ : スカラー 整形済み時間

getTime関数は、時間を取得する関数です。第1引数で書式を指定することで、日付の書式(英語表記、和暦表

記など)を自由に指定できます。第 2 引数では、時差(グリニッジ標準時=英国ロンドン)を秒単位で指定します。

日本の場合は、+9 時間なので、「3600*9」と指定します。第 3 引数では、取得する時間の UTC(国際協定時刻)のシリアル値を指定します。省略した場合は、現在時間(time関数の戻り値)を使用します。 日付書式に使える記号と意味

書式指定記号には以下のものが使えます。記号の前には、「%」を付ける必要があります。「%」自体を表示さ

せる場合は、「%%」とします。

記号 意味 例 記号 意味 例

yyyy 西暦4桁 2002 ap 午前/午後 午前

yyy 和暦 (平成のみ) 14 ap1 AM/PM AM yy 西暦2桁 (1桁の場合 2桁目は0) 02 ap2 am/pm am y 西暦1桁 2 hh 24時間制2桁 (1桁の場合 2桁目は0) 19 mm 月2桁 (1桁の場合 2桁目は0) 12 h 24時間制1桁 19 m 月1桁 12 HH 12時間制2桁 (1桁の場合 2桁目は0) 07 MM 月英語略表記 Jan H 12時間制1桁 7 MM2 月英語表記 January nn 分2桁 (1桁の場合 2桁目は0) 12 dd 日2桁 (1桁の場合 2桁目は0) 05 n 分1桁 12 d 日1桁 5 ss 秒2桁 (1桁の場合 2桁目は0) 05 ww 曜日日本語表記 日 s 秒1桁 5 ww2 曜日英語略表記 Sun ww3 曜日英語表記 Sunday

日付書式指定の例

%yyyy/%mm/%dd %hh:%nn:%ss : 2002/03/13 12:34:21 平成%yyy年%m月%d日 : 平成14年3月13日 %ap%HH時%nn分%ss秒 : 午後12時34分21秒 %ww3 %MM %d, %yyyy : Thursday Jun 6, 2002 %yyyy%mm%dd%hh%nn%cc : 20020313123421 %H:%nn%ap2, %ww2 %MM d : 3:52pm, Thu Jul 6

記記 述述 例例

$time_now = stdio::getTime($time_format, $time_difference, $base_time);

Page 16: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 16 -

ササンンププルル

# ① 現在時間を日本時間で表示 print stdio::getTime("%yyyy/%mm/%dd (%ww) %hh:%nn", 3600*9);

# ② $filenameの 終アクセス時をGMT時間で表示 $atime = (stat($filename))[9];

print stdio::getTime("%ww2, %mm3 d, yyyy HH:nn ap3", 0, $atime);

▼ ①の実行結果(以下の形式で現在時間を表示)

2002/06/07 (金) 02:14

▼ ②の実行結果(以下の形式で$filenameのUTCでの最終アクセス時間を表示)

Friday, June 7, 2002 02:14 pm

▼ ③の実行結果(以下の形式でUTCでの現在時間を表示)

20020810141039

Tips 正午は午前12時、それとも午後12時?

正午は午前12時、それとも午後12時?getTime関数のコーディングの際に疑問に思ったので調べてみました。調べた結果は、 文科省の国立天文台のサイトでは、「正午は午前12時か午後0時とした方が良い、法律的(明治5年の古い法律)には午前12時が正し

い(といっても曖昧に記されている)。正午を1秒でも過ぎると午後になる。」とありました。しかしデジタル時計は、国内外を問わず

ほとんどが12時間制を採用し、正午を午後12時としています。 どちらにするか悩んだあげく、getTime関数では、正午は午後12時、正子(夜の12時)は午前12時としました。理由ですが、手元

にあるデジタル時計、Windows のタスクトレイに表示される時計、世界 大のポータルサイトである米 Yahoo!のトップページに表

示される時間がこの表記であり世界で定着している(と思われる)こと、午前/午後0時という表現は12時間制であるアナログ時計で0という数字が無いため違和感がある、といったことにあります。

Page 17: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 17 -

gggeeetttSSSeeerrriiiaaalllTTTiiimmmeee 時間からUTCシリアル値を取得

◎ = stdio::getSerialTime(☆,★[,□[,■[,○[,●[,△]]]]])

☆ : スカラー GMT(グリニッジ標準時=英国ロンドン)との秒差 (日本は3600*9) ★ : スカラー 年(西暦4桁) □ : スカラー 月(省略時は1月) ■ : スカラー 日(省略時は1日) ○ : スカラー 時(省略時は0時) ● : スカラー 分(省略時は0分) △ : スカラー 秒(省略時は0秒) ◎ : スカラー UTCシリアル値

getSerialTime 関数は、引数として指定した時間(年・月・日・時・分・秒)からUTC のシリアル値(1970 年 1月 1 日 0 時 0 分 0 秒からの経過秒数)を取得します。時間をシリアル値に変換することによって、時間計算が容

易にできるようになります。 記記 述述 例例

$utc_serial = stdio::getSerialTime($time_difference, $year, $mon, $day, $hour, $min, $sec);

ササンンププルル

# 2020年10月31日14時15分32秒のUTCシリアル値を求める $utc_serial = stdio::getSerialTime(9*3600, 2020, 10, 31, 14, 15, 32);

print "2020/10/31 14:15:32のUTCシリアル値 : $serial_time¥n"; $time = scalar(localtime $serial_time);

print "上記シリアル値を時間へ変換 : $time¥n";

# 1999年7月10日から2002年6月7日までの日数を求める $day1 = stdio::getSerialTime(9*3600, 1999, 7, 10);

$day2 = stdio::getSerialTime(9*3600, 2002, 6, 7);

$days = int(($day2 - $day1) / 86400);

print "1999/7/10から2002/6/7までの日数 : $days日¥n";

▼ 実行結果

2020/10/31 14:15:32のUTCシリアル値 : 1604121332

上記シリアル値を時間へ変換 : Sat Oct 31 14:15:32 2020

1999/7/10から2002/6/7までの日数 : 1063日

Page 18: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 18 -

bbbaaassseee666444eeennncccooodddeee /// bbbaaassseee666444dddeeecccooodddeee base64エンコード・デコード

stdio::base64encode(☆[,★]) , ◎ = base64encode_(■[,★])

stdio::base64decode(□) , ◎ = stdio::base64decode_(○)

☆ : スカラー(参照) Base64エンコードするスカラー変数へのリファレンス(型グロブ) ★ : スカラー 1行あたりのバイト数(省略時は改行なし) □ : スカラー(参照) Base64デコードするスカラー変数へのリファレンス(型グロブ) ※ 関数名がstdio::base64encode_()とstdio::base64decode_()の場合は値渡しになります

■ : スカラー Base64エンコードするスカラー変数(値渡しの場合) ○ : スカラー Base64デコードするスカラー変数(値渡しの場合) ◎ : スカラー Base64エンコード(デコード)されたスカラー変数(値渡しの場合のみ)

base64encode/base64decode関数は、引数で指定したデータを、Base64エンコード/デコードします。 Base64エンコードとは?

Base64 エンコードは、インターネットでよく使われるエンコード形式の1つです。3バイト(24 ビット)を6

ビットずつに区切り、それを 1 バイト(8 ビット)で表現します。(6ビットで表現できるパターンは、26で 64 通

りあります。アルファベット大文字小文字52文字、数字10文字、「+」と「/」の2つの記号の計64字を、それ

ぞれのパターンに割り当て、英数字と記号2字で表現します。) これによって、画像などのバイナリデータやマ

ルチバイト文字を問わずに、あらゆるデータを半角英数字で表現できます。デコードは、エンコードとは反対に、

元のデータに戻します。 ササンンププルル

$str = 'Base64エンコードする文字列。';

print "元の文字列 : $str¥n";

# Base64エンコードしてそれを表示 stdio::base64encode(¥$str);

print "base64encode : $str¥n";

# Base64デコード(復元)してそれを表示 stdio::base64decode(¥$str);

print "base64decode : $str¥n";

▼ 実行結果

元の文字列 : Base64エンコードする文字列。 Base64encode : QmFzZTY0g0eDk4NSgVuDaIK3gumVto6al/GBQg==

Base64decode : Base64エンコードする文字列。

Page 19: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 19 -

uuurrrllleeennncccooodddeee /// uuurrrllldddeeecccooodddeee URLエンコード・デコード

stdio::urlencode(☆) , ◎ = stdio::urlencode_(□)

stdio::urldecode(★) , ◎ = stdio::urldecode_(■)

☆ : スカラー(参照) URLエンコードするスカラー変数へのリファレンス(型グロブ) ★ : スカラー(参照) URLデコードするスカラー変数へのリファレンス(型グロブ) ※ 関数名がstdio::urlencode_()とstdio::urldecode_()の場合は値渡しになります

□ : スカラー URLエンコードするスカラー変数(値渡しの場合) ■ : スカラー URLデコードするスカラー変数(値渡しの場合) ◎ : スカラー URLエンコード(デコード)されたスカラー変数(値渡しの場合のみ)

urlencode/urldecode関数は、引数で指定したデータを、URLエンコード/デコードします。 URLエンコードとは?

URL(URI)に使用可能な文字にエンコードした形式です。半角英数字はそのまま、半角スペースは「+」に、

それ以外の文字は、1バイトを 16 進数による2バイト(00~ff)に変換します。変換後の 16 進数の前に「%」を

付けます。 ササンンププルル

# ① クエリー文字列をURLデコードしてハッシュ変数に格納 (フォームでコード処理の定石) foreach (split /&/, $ENV{'QUERY_STRING'}) {

my($key, $val) = split /=/, $_, 2;

stdio::urldecode(¥$val);

$QUERY_STRING{$key} = $val;

}

# ② $strをURLエンコード(文字コードはシフトJIS)

$str = 'URLエンコード テスト Test';

print "元の文字列 : $str¥n"; stdio::urlencode(¥$str);

print "URLエンコード : $str¥n";

▼ ②の実行結果

元の文字列 : URLエンコード テスト Test

URLエンコード : URL%83G%83%93%83R%81%5B%83h+%83e%83X%83g+Test

Page 20: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 20 -

tttrrrSSStttrrriiinnnggg 文字列を置換する

stdio::trString(☆[,★[,□[,■[,○[,●]]]]])

◎ = stdio::trString_(△[,★[,□[,■[,○[,●]]]]])

☆ : スカラー(参照) 置換する文字列を格納したスカラー変数へのリファレンス(型グロブ) ★ : スカラー 1:HTML構成文字を実体参照に置換/2:実体参照をHTML構成文字に置換

□ : スカラー 1:大文字を小文字に置換/2:小文字を大文字に置換

■ : スカラー 1:全角英数字と記号を半角に置換/2:半角英数字と記号を全角に置換

○ : スカラー 1:全角カタカナをひらがなに置換/2:ひらがなを全角カタカナに置換

● : スカラー 削除する文字 ※ 関数名がstdio::trString_()の場合は値渡しになります

△ : スカラー 置換する文字列のスカラー変数(値渡しの場合) ◎ : スカラー 置換された文字列のスカラー変数(値渡しの場合のみ)

trString 関数は、文字列を指定した条件の通りに置換します。タグ構成文字を実体参照に置換、大文字を小文

字に置換、全角カタカナをひらがなに置換したり、指定した文字を削除したりすることができます。第4引数以

降を使う場合、呼び出す前に文字コード変換ライブラリ jcode.plをロードしておく必要があります。 記記 述述 例例

stdio::trString(¥$string, $conv_tags, $lc, $z2h, $k2h, $rmstr);

ササンンププルル

# ① 全角英数字を半角英数字小文字に置換

$str = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; stdio::trString(¥$str, 0, 1, 1);

print $str;

# ② 記号類を削除する

$str = "インターフェイス・TCP/IP";

stdio::trString(¥$str, 0, 0, 0, "ー・/"); print $str;

▼ ①の実行結果

abcdefghijklmnopqrstuvwxyz

▼ ②の実行結果

インタフェイスTCPIP

Page 21: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 21 -

ssseeeaaarrrccchhhSSStttrrriiinnnggg マルチ文字列検索

◎ = stdio::searchString(☆,★[,□])

☆ : スカラー 検索対象の文字列(検索対象となる文字列) ★ : スカラー 検索する文字列(キーワード) □ : スカラー 検索条件(省略時はAND) ◎ : スカラー 1:検索条件にマッチする/0:しない/空値:検索式が不正

searchString関数は、複数のキーワードによる文字列検索を行います。AND、ORとBOOLEAN(検索演算子

による検索式)が使用できます。 キーワードの指定とワイルドカード

第 1 引数に検索対象の文字列を、第 2 引数に検索する文字列(キーワード)を指定します。キーワードに正規表

現は使えませんが、ワイルドカードを使うことができます。ワイルドカードは、半角アスタリスク「*」で、0~32バイトの任意の文字列にマッチします。「*」自体を検索したい場合は、「**」とします。

◆例. 今日*です。

…「今日です」「今日は晴れです」「今日は試験です」「今日からです」にマッチ

検索条件の指定

第3引数で検索条件を指定します。指定可能な検索条件は、以下の通りです。省略した場合は、1=AND を指

定したことになります。検索条件を指定する際の大文字小文字は区別されません。

▼指定可能な検索条件

0 = AND : 論理積 すべての検索文字列を含む

1 = OR : 論理和 1つ以上の検索文字列を含む

2 = BOOLEAN = BLN : 論理式 ユーザー検索式使用

■AND検索とOR検索の使い方

AND と OR 検索で複数のキーワードを指定する場合は、半角スペースで区切ります。また、各キーワードの

頭に半角エクスクラメーション(感嘆符"!")か半角ハイフン"-"を付けると、そのキーワードのみ NOT 検索になり

ます。 ■検索式の使い方

第3引数に"BOOLEAN"を指定した場合、検索式の使用が可能になります。検索式を使用することで、より柔

軟な検索ができるようになります。検索式に使用可能な検索演算子は、以下の通りです。検索演算子の大文字小

文字は区別されません。

▼使用可能な検索演算子

AND & : 両端の語の両方を含む

OR | : 両端の語のいずれかを含む

NOT ! : 直後の語を含まない (括弧の前に指定した場合は、括弧内の検索結果を反転)

( ) : 括弧内の検索式を優先する

Page 22: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 22 -

AND、ORとNOTの検索演算子の前後には、半角スペースをあける必要があります。それ以外の半角スペー

スは無視されます。「AND NOT」は単に「NOT」とだけ書くこともできます。

◆例1. Java AND NOT JavaScript (「AND NOT」は「NOT」だけでも良い)

…Javaを含むが、JavaScriptは含まない

◆例2. ( フリーソフト or フリーウェア ) and ( 日本 or 国内 )

…日本(国内)にあるフリーソフト(フリーウェア)

◆例3. ( 本屋 | 書店 ) & ( !古本 & !古書 )

…本屋(書店)を含むが、古本(古書)は含まない

記記 述述 例例

$result = stdio::searchString($string, $keyword, $match_mode);

ササンンププルル

# レコードを定義 @record = (

'1. 旅の恥はかき捨て',

'2. 旅の犬が尾をすぼめる',

'3. 旅は道連れ',

'4. 二兎を追う者は一兎をも得ず',

'5. 旅は道連れ世は情け',

'6. 犬も歩けば棒に当たる',

'7. 明日は明日の風が吹く' );

# ① "旅は道連れ"と"世は情け"を含むレコードを抽出 foreach (@record) {

if (stdio::searchString($_, "旅は道連れ 世は情け")) { print "$_¥n";

}

}

# ② "旅"を含み、"犬"を含まないレコードを抽出 foreach (@record) {

if (stdio::searchString($_, "旅 -犬")) { print "$_¥n";

}

}

# ③ "旅"か"犬"を含み、"尾"を含まないレコードを抽出 (検索演算子を使用) foreach (@record) {

if (stdio::searchString($_, "( 旅 OR 犬 ) AND NOT 尾", "Boolean")) { print "$_¥n";

}

}

Page 23: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 23 -

# ④ "旅"と"犬"を含まないレコードを抽出 (検索演算子を使用) foreach (@record) {

if (stdio::searchString($_, "NOT 旅 AND NOT 犬", "Boolean")) { print "$_¥n";

}

}

▼ ①の実行結果

5. 旅は道連れ世は情け

▼ ②の実行結果

1. 旅の恥はかき捨て

2. 旅の犬が尾をすぼめる

3. 旅は道連れ

5. 旅は道連れ世は情け

▼ ③の実行結果

1. 旅の恥はかき捨て

3. 旅は道連れ

5. 旅は道連れ世は情け

6. 犬も歩けば棒に当たる

▼ ④の実行結果

4. 二兎を追う者は一兎をも得ず

7. 明日は明日の風が吹く

Page 24: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 24 -

gggeeetttRRRaaannndddooommmSSStttrrriiinnnggg ランダムな文字列を作成・取得

◎ = stdio::getRandomString([☆[,★]])

☆ : スカラー 作成する文字列のバイト数(省略時は8バイト) ★ : スカラー 作成に使用する文字(省略時は英数字62文字) ※半角文字列のみ ◎ : スカラー 作成された文字列

getRandomString 関数は、引数で指定した文字種とバイト数からランダムな文字列を作成し、それを戻り値

に返します。パスワードを作成したり、crypt関数の暗号化の種を作成したりするのに使います。 記記 述述 例例

$random_string = stdio::getRandomString($byte, $string);

ササンンププルル

# 変数$passwordに6バイトのランダム文字列をセット $password = stdio::getRandomString(6);

# crypt関数で$passwordを暗号化 $crypted_password = crypt($password, stdio::getRandomString(2));

print "¥$password = $password (getRandomString関数で作成したランダム文字列)¥n";

print "¥$crypted_password = $crypted_password (crypt関数で暗号化したもの)¥n";

# crypt関数で暗号化したパスワードと元のパスワードが一致の確認 if (crypt($password, $crypted_password)) {

print "パスワードが一致しました。¥n"; }

▼ 実行結果 (結果は毎回異なる)

$password = mN7ZsY (getRandomString関数で作成したランダム文字列)

$crypted_password = PR4VmYTEpEzCQ (crypt関数で暗号化したもの)

パスワードが一致しました。

Page 25: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 25 -

ssseeetttLLLiiinnnkkk クリッカブルURI(URL)を設定する

stdio::setLink(☆[,★[,□[,■]]])

◎ = stdio::setLink_(○[,★[,□[,■]]])

☆ : スカラー(参照) クリッカブルURIの対象となる文字列へのリファレンス(型グロブ) ★ : スカラー target属性(メールリンクには無効) □ : スカラー a要素の要素内容に設定する文字列(URIリンク時) ■ : スカラー a要素の要素内容に設定する文字列(メールアドレスリンク時) ※ 関数名がstdio::setLink_()の場合は値渡しになります

○ : スカラー クリッカブルURIの対象となる文字列のスカラー変数(値渡しの場合) ◎ : スカラー クリッカブルURIが適用された文字列のスカラー変数(値渡しの場合のみ)

文字列中に含まれるURIとメールアドレスにa要素によるマーク付けをします。対応しているURIのスキー

ムは http、https、ftp、telnet、wais、gopher、news、nntp、rstp と mailto です。URI の直前が「;」と引用

符の場合はリンクされません。メールアドレスリンクは、"mailto:"スキームがついている場合に有効です。 記記 述述 例例

stdio::setLink(¥$string, $target_attribute, $link_string, $mail_string);

ササンンププルル

# $str変数にURIを設定する $str = <<'_EOF_';

http://www.google.com/

mailto:[email protected]

ftp://www.webpower.jp/

<a href="http://www.yahoo.co.jp/">http://www.yahoo.co.jp/</a>

_EOF_

# $str変数のURIをリンクする (メールアドレスのリンク文字列は[E-MAIL]) stdio::setLink(¥$string, 'target="_top"', undef, '[E-MAIL]');

print $str;

▼ 実行結果

<a href="http://www.google.com/" target="_top">http://www.google.com/</a>

<a href="mailto:[email protected]">[E-MAIL]</a>

<a href="ftp://www.webpower.jp/" target="_top">ftp://www.webpower.jp/</a>

<a href="http://www.yahoo.co.jp/">http://www.yahoo.co.jp/</a>

Page 26: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 26 -

ssseeetttCCCooommmmmmaaa 3桁毎にカンマを打つ

◎ = stdio::setComma(☆)

☆ : スカラー カンマ打ちする数字

◎ : スカラー カンマ打ちされた数字

setComma関数は、引数として指定した数字に3桁毎にカンマを打ち、それを戻り値として返します。 記記 述述 例例

$digit = stdio::setComma($digit);

ササンンププルル

# 3桁毎にカンマ打ち print stdio::setComma(5629800), "¥n";

print stdio::setComma(9800), "¥n";

print stdio::setComma(345), "¥n";

print stdio::setComma("12A0F"), "¥n"; # 16進数も対応

▼ 実行結果

5,629,800

9,800

345

12,A0F

Tips ヒアドキュメントの中で関数呼び出し

ヒアドキュメントの中で関数を呼び出したり、コマンドを実行したりしたい場合があります。通常は、ヒアドキュメントを開始す

る前に実行して、結果を変数にあらかじめ格納しておくか、ヒアドキュメントを一度終了させて、実行後に再度ヒアドキュメントを

開始するといった方法をとります。しかし、この方法の場合、コードが複雑になったりしかねません。そこで、次のようにすること

で、ヒアドキュメントの中でも関数を呼び出したり、コマンドを実行したりすることができます。 @{[stdio::setComma(1200)]}

この方法では戻り値は、リストとして評価されるため、スカラー評価したい場合は、scalar関数を使って次のようにします。 @{[scalar locatime]}

Page 27: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 27 -

llloooccckkk /// uuunnnllloooccckkk /// llloooccckkkCCChhheeeccckkk 排他制御

◎ = stdio::lock(☆[,★[,□]])

◎ = stdio::unlock(☆)

◎ = stdio::lockCheck(☆[,★[,□]])

☆ : スカラー ロックフラグ用ディレクトリのパス ※ パスの指定が「///」で始まる場合は、「///」は$stdio::tmp_dirで指定した値に置換。 ★ : スカラー ロック中の場合の再試行回数 (省略時は3) □ : スカラー 次の試行までの待機秒数[整数] (省略時は1) ◎ : スカラー 1:非ロック中/0:ロック中

lock/unlock 関数は、ファイルのロック/アンロックをします。lockCheck 関数は、ロックされているかどうかをチェックします。(チェックするだけでロックはしません。) lock、unlock関数を用いないファイル操作はロックの対象となりません。この関数では、ロックフラグにディレクトリを使っています。 記記 述述 例例

$result = stdio::lockCheck($lock_dir);

$result = stdio::lock($lock_dir);

stdio::unlock($lock_dir);

ササンンププルル

# ロック if (!stdio::lock($lockdir)) {

print "Busy!¥n";

exit;

}

# ファイル入出力 open IO, "+<count.txt" || die "Can't open file.";

my($count) = <IO>;

$count ++;

seek IO, 0, 0;

print IO $count;

# アンロック stdio::unlock($lockdir);

Page 28: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 28 -

ココ ララ ムム

●●フファァイイルルロロッッククがが必必要要なな理理由由

ファイル操作を行うCGIでは、複数のプロセスによる同じファイルへの同時書き込みが発生する場合がありま

す。同時に書き込みがされると、ファイルが壊れる場合があります。ファイルロックは、それを防止するために、

あるプロセスがファイルに書き込んでいる間、他のプロセスは待機させる処理です。 次のコードは、掲示板で書き込む場合のファイル入出力処理の一例です。 1 open IN, "data.txt"; # ファイルを読み込みモードで開く

2 @record = <IN>; # ファイルからレコードを配列に読み込む

3 close IN; # ファイルを閉じる

4 unshift @record, $record; # レコードの先頭に新しいレコードを足す

5 open OUT, ">data.txt"; # ファイルを上書きモードで開く (この時点でファイルは空になる)

6 print OUT @record; # ファイルにレコードを書き込む (バッファリングされる)

7 close OUT; # ファイルを閉じる (バッファが解放されファイルに書き込まれる) ※ 行番号は説明のためにつけているもので、実際は必要ありません。

5行目のopen関数で、ファイルを上書きモードで開いた時点で、data.txtの中身は削除されます。6行目でレ

コードをファイルに出力していますが、通常はバッファリングされるため、この時点ではまだ書き込まれていま

せん。ファイルを閉じる7行目の時点でバッファがフラッシュされ、実際にファイルに書き込まれます。 上のコードには実装方法に問題があります。あるプロセスAが5行目から7行目までの3ステップを実行中に、

別のプロセスB が 2 行目を実行すればどうなるでしょう。プロセスA が 5 行目を実行した時点でファイルは空

になるため、プロセスB は、1 行目で空のファイルを開き、2 行目で空のレコードを読み込んでしまうことにな

ります。空のレコードに、新しいレコードを足してファイルに書き込むと、以前のレコードはすべて失われてし

まいます。これが、書き込みの衝突によってファイルが壊れるメカニズムです。 これを防止する機構が排他制御(ロック)です。ファイルロックの実装方法にはいくつかありますが、stdio.plで

はmkdir関数を使ったフラグチェックで実現させています。 ファイルを開く前にフラグ(旗)を立てます。ファイルを閉じたらフラグも降ろします。他のプロセスは、フラ

グが立っている場合は、フラグが降りるまで待機します。ここでいうフラグには空のディレクトリを使います。

フラグにディレクトリを使うのは、アトミック(分割不可能=フラグの確認と確立がワンステップで可能)であり、

Windows系OSでも実装可能であるからです。

① ロックフラグにファイルを使う

if (!-f $lock_file) {

open OUT, ">$lock_file" || die "Can’t open lock file."

ロックファイルが存在しないことを確認して、ロックファイルを作成する。2ステップあるため、ロックファイルの

存在確認からロックファイルを作成するまでの間に、他のプロセスが1ステップ目を実行する可能性がある。可能性と

しては低いが、ロック自体が衝突する場合がある。

② ロックフラグにディレクトリを使う

if (mkdir $lock_dir) {

ロックディレクトリの存在確認と、ロックディレクトリの作成がワンステップでできる。 ファイルロックをすれば、書き込みの衝突によってファイルが破損する可能性は格段に低くなります。しかし、

万全ではなく、サーバーダウン、ディスククラッシュ、クラッキングや操作ミスなどのその他の要因によってデ

ータを失う可能性は常にあります。大切なデータは日頃からバックアップを心がけておくことが大切です。

Page 29: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 29 -

ooopppeeennnSSSoooccckkkeeettt /// ccclllooossseeeSSSoooccckkkeeettt ソケット確立・解放

◎ = stdio::oepnSocket(☆,★[,□[,■[,○]]])

◎ = stdio::closeSocket(☆)

☆ : スカラー ソケットと結びつけるファイルハンドル

★ : スカラー 接続先ホスト(プロトコルがhttpで始まるURIの場合のみ以下の3引数が有効) □ : スカラー リクエストメソッド(省略時はGET) ■ : ハッシュ(参照) リクエストヘッダー

○ : スカラー リクエスト時の標準入力(GETメソッドでは無効)

◎ : スカラー 1:成功/0:失敗

openSocket/closeSocket関数は、ネットワーク通信のためのソケットの確立/解放を行います。第2引数の接続

先ホストに http で始まるURI を指定した場合は、Web サーバーに HTTP 接続を行い、レスポンスを受け取り

ます。この場合のリクエストメソッドやリクエストヘッダーなどは第3引数以降で指定できます。http以外のプ

ロトコルを指定した場合は、ソケットの確立のみを行いますので、SMTP サーバーや FTP サーバーに接続して

通信を行うことができます。 ドメインとタイプ

ソケット通信(socket 関数の引数)に必要なドメインとタイプは stdio.pl のパッケージ変数$stdio::inet と

$stdio::stream で定義されています。この値は OS 等によって異なる場合がありますので、必要に応じて変更し

てください。Socket.pmモジュールがロードされている場合、PF_INET関数とSOCK_STREAM関数から取得

します。 WebサーバーにHTTP接続する

第2引数に接続先のURIをhttpから指定します。ポート番号も指定可能です(省略時は80になります。)。こ

れだけで、ブラウザが Web サイトにアクセスするのと同様に、CGI が Web サイトにアクセスします。Web サ

ーバーからのレスポンスは、ソケットと結びつけたファイルハンドルから取得します。 また、以下の形式でプロクシサーバーを経由することができます。

openSocket(SOCK, "http://プロクシホスト:ポート番号(省略時は80) 接続先URI");

例えば、プロクシサーバー proxy.hostname.jp:80 を経由して http://www.google.co.jp/ に接続する場合、 openSocket(SOCK, "http://proxy.hostname.jp:80 http://www.google.co.jp");

のようにします。 リクエストメソッドとヘッダーを指定する

HTTP接続の場合、第3引数でリクエストメソッドを、第4引数でリクエストヘッダーを指定できます。リク

エストメソッドは省略すると"GET"になります。リクエストヘッダーはハッシュの形で定義し、第4引数に、そ

のハッシュ変数へのリファレンスを渡します。ユーザーエージェントやReferer(参照元)などは、サンプルのよう

に、このリクエストヘッダーに指定します。

Page 30: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 30 -

標準入力とContent-Type/Content-Length

HTTP 接続の場合で POST メソッドによるリクエストを行う場合、第 5 引数に標準入力として与えるデータ

を指定します。この場合の、リクエストヘッダーのContent-Typeには「application/x-www-form-urlencoded」が、Content-Length は標準入力のサイズが自動的に指定されます。ただし、第 4 引数のリクエストヘッダー指

定でこれらを指定していた場合は、自動的には指定されません。また、マルチパートフォームデータを標準入力

で与える場合は、第4引数のリクエストヘッダーのContent-Typeで指定します。 記記 述述 例例

$result = stdio::oepnSocket(SOCK, $uri, $method, ¥%header, $stdin);

$result = stdio::closeSocket(SOCK);

ササンンププルル

# リクエストヘッダーを定義 %header = (

"User-Agent" => "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1)",

"Referer" => "http://www.hostname.jp/dir/file.html"

);

# アラーム(タイムアウト)発生時に呼び出す関数 $SIG{'ARM'} = ¥&TimeoutError;

# アラーム(タイムアウト)を30秒に設定 alarm 30;

# URI(http://www.hostname.jp/)に接続 if (stdio::openSocket(SOCK, "http://www.hostname.jp/", "GET", ¥%header)) {

print while(<SOCK>);

stdio::closeSocket(SOCK);

}

# アラームを解除する alarm 0;

# タイムアウト時に呼び出す関数を定義 sub TimeoutError

{

print "処理がタイムアウトになりました。¥n"; exit;

}

Page 31: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 31 -

ssseeennndddmmmaaaiiilll sendmailを使用してメール送信

◎ = stdio::sendmail(☆,★[,□[,■[,○]]])

☆ : ハッシュ(参照) 送信メールに付与するヘッダーを定義したハッシュ変数へのリファレンス(型グロブ) ★ : スカラー メール本文

□ : スカラー HTMLメール本文 (HTMLメール本文があればメール本文は空でもよい) ■ : スカラー 添付ファイルのエンコード形式(base64encode/uuencode) 省略時はbase64 ○ : リスト 添付ファイル(パス [; MIMEタイプ [; 名前 [; エンコード形式]]]) ◎ : スカラー 1:送信成功/0:送信失敗

sendmail関数は、電子メール送信プログラム sendmailを使って電子メールを送信します。この関数を実行す

るには、サーバーで sendmail(sendmail と互換性があるものを含む)が使用可能であり、文字コード変換ライブ

ラリ jcode.plがロードされている必要があります。 sendmail のパスは、stdio.pl のパッケージ変数$stdio::sendmail で指定します。初期状態では、

「/usr/lib/sendmail」になっています。 メールヘッダー

宛先や件名などのメールヘッダーは、サンプルのようにハッシュ変数で定義します。これによって任意のヘッ

ダーを付けたメールを送信できます。日本語を含むメールヘッダーは関数側でBase64エンコードされます。 関数へは、第1引数でヘッダーを定義したハッシュ変数のリファレンスを渡します。 メール本文

メール本文は第2引数と第3引数で指定します。第2引数で渡した内容はテキストとして扱われ、第3引数で

渡した内容はHTMLとして扱われます。 第2引数にのみ内容がある場合は、本文は通常のテキストメールになります。第2引数と第3引数の両方に内

容がある場合は、本文はテキストと HTML のマルチパートメッセージになります。第 3 引数にのみ内容がある

場合は、本文はHTMLメールになります。 HTMLメールは受信側のメーラーが対応している必要があります。

ファイル添付

ファイルを添付するには、第5引数以降に添付するファイルのパスを指定します。メールにファイルを添付す

る場合、テキスト形式にエンコードする必要があります。エンコード方式には、Base64encode、Uuencode と

BinHex があり、この関数ではBase64encodeとUUencodeをサポートしています。Base64encode は多くのメ

ーラーが対応しているため、通常はBase64encodeで送信します。エンコード形式は第4引数で指定します。

Tips 巨大ファイルの添付は御法度

添付可能なファイルサイズやファイルの種類に制限はありませんが、添付ファイルはテキスト形式にエンコード(エンコードによっ

てサイズが1.5倍近くになる)する必要があるため、巨大なファイルの添付はサイズに応じて処理時間がかかり、サーバーへの負荷も

大きくなります。受信側の環境も考慮して、合計で 1M バイトを超えるようなファイルの添付は避けるようにしましょう。大きいフ

ァイルのやりとりは、オンラインストレージサービスやP2Pが便利です。

Page 32: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 32 -

ファイルを添付する際の詳細設定

ファイルを添付するには第 5 引数以降に添付するファイルのパスを指定しますが、添付ファイル毎に MIMEタイプ、ファイル名とエンコード形式を指定することができます。それらを指定するには以下のようにします。

ファイルパス [; MIMEタイプ [; 名前 [; エンコード形式 ]]] * [ ] は省略可能

MIMEタイプ : "image/gif"や"audio/midi"といったMIMEタイプを指定します。省略した場合は、 "application/octet-stream"になります。 名前 : ファイルの名前を指定します。省略時は、添付ファイルのファイル名が使われます。 エンコード形式 : エンコード形式を"base64encode"か"uuencode"で指定します。省略した場合は、第4 引数で指定したエンコード形式が使われます。

添付ファイルのキャッシュオプション

ファイルを添付する際、エンコードしたデータをキャッシュしておくことで、同じファイルを添付する場合の

2回目以降のパフォーマンスを向上させることができます。キャッシュするには、第4引数か[ファイルを添付す

る際の詳細設定]のエンコード形式の後に「 cache」と指定します。キャッシュオプションは、キャッシュファイ

ルが存在しない場合は、通常と同様にエンコードして送信すると同時に、エンコードしたデータをキャッシュフ

ァイルとして保存します。キャッシュファイルが存在する場合は、エンコードをせずにキャッシュファイルから

読み込んだデータをそのまま送信します。このようにすることで、ファイル添付処理でオーバーヘッドの大きい

エンコード処理をスキップすることが可能となり、パフォーマンスの向上が実現できます。 ■どのような場合に有効?

キャッシュオプションは、容量の大きいファイルを添付する sendmail 関数を複数回、あるいは頻繁に実行す

る場合に効力を発揮します。ベンチマーキングの結果、1.3MBのファイルを2つのアドレスに送信する場合、キ

ャッシュ機能を使わない場合は約16秒、キャッシュ機能を使う場合は約8秒で実行できました。(サーバー環境

によって変動しますのであくまでも参考にしてください。) キャッシュ無効 16 wallclock secs (15.59 usr 0.09 sys + 0.12 cusr 0.06 csys = 15.86 CPU) キャッシュ有効 9 wallclock secs ( 8.02 usr 0.03 sys + 0.06 cusr 0.10 csys = 8.21 CPU)

逆に容量が小さいファイルや、1回だけしか添付しないファイルの場合は、それほど効力はありません。 ■キャッシュファイルはどこに作られる?

キャッシュファイルは$stdio::tmp_dirで指定した値のディレクトリに、ファイル名をbase64エンコード(「+」と「/」は、「-」と「_」に置換)したうえで、拡張子「.b64(uu).cache」を付けて保存されます。 ■キャッシュファイルを削除するには?

不要になったキャッシュファイルを削除するには、stdio::removeCacheFiles関数を使います。キャッシュファ

イルの自動削除は行われませんので、不要になったキャッシュファイルは速やかに削除しましょう。 stdio::removeCacheFiles(@files); # @filesは削除するキャッシュファイルのリスト

■関数側でエンコードせずに添付するには?

キャッシュオプションを使わずに、エンコード済みのファイルを、関数側でエンコードせずにメール送信する

には、「 cache」の代わりに「 encoded」とします。添付するファイルが既にエンコード済みの場合は、このオ

プションを使うとよいでしょう。 記記 述述 例例

$result = stdio::sendmail($sendmail, ¥%header, $body, $html_body, $encode, @attachments);

Page 33: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 33 -

ササンンププルル

# 宛先を含むメールヘッダーをハッシュ変数で定義 (ハッシュ変数へのリファレンスでもよい) %header = (

'To' => '[email protected]',

'Cc' => '[email protected]',

'From' => '太郎 <[email protected]>',

'Subject' => 'メールの件名' );

# 添付ファイルを配列変数で定義 @attachments = (

'imagefile.gif; image/gif',

'zipfile.zip; application/zip; archive.zip; uuencode cache'

);

# メール本文 (テキスト) $body = <<'_EOF_';

久しぶり~、元気?

今度また遊びに行こうよ。 _EOF_

# メール本文 (HTML) $html_body = <<'_EOF_';

<html>

<head>

</head>

<body>

<p>久しぶり~、元気?<br>

今度またどこかに遊びに行こうよ。</p> </body>

</html>

_EOF_

# 添付ファイル付きメールを送信 $result = stdio::sendmail(¥%header, $body, $html_body, "base64", @attachments);

# 戻り値が偽であれば送信失敗 if (!$result) {

print "メールの送信に失敗しました。¥n"; exit;

}

Page 34: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 34 -

ssshhhuuuffffffllleeeAAArrrrrraaayyy 配列をシャッフルする

◎ = stdio::shuffleArray(☆)

☆ : リスト シャッフルする配列

◎ : リスト シャッフルされた配列

shuffleArray 関数は、引数として指定した配列をシャッフル(ランダムに並び替える)して、それを戻り値とし

て返します。 記記 述述 例例

@array = stdio::shuffleArray(@array);

ササンンププルル

# 配列をシャッフルする @array = ('A'..'Z','a'..'z','0'..'9');

print stdio::shuffleArray(@array);

▼ 実行結果(結果は毎回異なる)

3f5GAmba8ruBCHQvOFoEV4kPNJw76Yld1RcexDLqS2KjTtpZiIs9UWXhgzMyn0

Page 35: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 35 -

gggeeetttIIImmmaaagggeeeSSSiiizzzeee GIF/JPEG/PING画像のピクセルサイズを取得

(□, ■, △) = stdio::getImageSize(☆)

☆ : スカラー 取得する画像のファイルパス

□ : スカラー 成功時:画像の種類(GIF/JPG/PNG) 失敗時:(0:GIF/JPEG/PNG以外のファイル/無し:ファイル読込不可) ■ : スカラー 画像の幅[width] (失敗時は0) △ : スカラー 画像の高さ[height] (失敗時は無し)

getImageSize 関数は、GIF、JPEG と PING 画像のピクセルサイズを、各画像のヘッダーから取得します。

ブラウザからアップロードされた画像のピクセルサイズをチェックする場合や、HTML で表示する際に img 要

素のwidth/height属性を設定する時などに使います。 記記 述述 例例

($type, $width, $height) = stdio::getImageSize($file_name);

ササンンププルル

# image.gifのピクセルサイズ取得 ($type, $width, $height) = stdio::getImageSize("image.gif");

# 画像の種類、横幅と高さを表示 if ($type eq "GIF" || $type eq "JPG" || $type eq "PNG") {

print "種類 : $type¥n";

print "横幅 : $width¥n";

print "高さ : $height¥n"; } else {

print "ファイルが存在しないか、認識できないファイルです。¥n"; }

# img要素のwidth属性とheight属性を設定する if ($type eq "GIF" || $type eq "JPG" || $type eq "PNG") {

print qq|<img src="image.gif" width="$width" height="$height" alt="画像" />¥n|; }

Page 36: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 36 -

gggeeetttMMMiiimmmeeeTTTyyypppeee ファイル名から適切なMIMEタイプを取得する

◎ = stdio::getMimeType(☆)

☆ : スカラー ファイル名、ファイルパスまたは拡張子

◎ : スカラー MIMEタイプ (該当するMIMEタイプが無い場合は" application/octet-stream") getMimeType関数は、引数として与えたファイル名、ファイルパス、もしくは拡張子から適切なMIMEタイ

プを取得し、それを戻り値に返します。CGI 経由でファイルを出力する際、Content-Type ヘッダーに出力する

MIME タイプを取得する場合に使います。対応する MIME タイプがない場合は、「application/octet-stream」

を返します。 記記 述述 例例

$mime_type = stdio::getMimeType($file_extention);

ササンンププルル

# $fileのMIMEタイプを取得 $mime_type = stdio::getMimeType($file);

# Content-TypeヘッダーにMIMEタイプを付与して出力 print "Content-Type: $mime_type¥n";

print "¥n";

open IN, $file || die "Can't open file.";

print while (read IN, $_, 1024);

close IN;

Page 37: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 37 -

STDIO.PL QUICK REFERENCE I STDIO.PLクイックリファレンス

(表記の記号の意味) %:ハッシュ/@:リスト/?:真か偽で指定/なし:スカラー変数/イタリックは参照(リファレンス) /[ ]は省略可能

(引数の色分け) 黒:第1引数/赤:第2引数/青:第3引数/緑:第4引数/紫:第5引数/茶:第6引数/紺:第7引数

※ 各関数の詳細は詳細リファレンスを参照してください。

動作 HTTPクッキーを作成する 引数 %@クッキー本体 [, クッキーID [, 有効期限 [, 有効パス [, 有効ドメイン [, ?セキュア時のみクッキ

ー発行 [, ?クッキー本体を戻り値に返す]]]]]] setCookie

戻値 クッキーの値(第7引数にクッキー本体を戻り値に返すようにした場合) 動作 ブラウザからHTTPクッキーを取得する 引数 %@クッキー本体を格納するハッシュ(配列) [, クッキーID] getCookie 戻値 取得したクッキーのキーのリスト(処理順)(取得できなかった場合は無し) 動作 セッション管理(ハッシュに有効期限と IDを付けて保存) 引数 ファイルのパス, %@セッション情報 [, セッション ID [, 有効秒数(省略時は3600秒)]] setSession

戻値 1:成功 0:失敗(ファイル読み書き不可) 動作 セッション管理(setSession関数で保存したセッション情報を読み出す) 引数 ファイルのパス, %@セッション情報を格納するハッシュ(配列) [, セッション ID] getSession

戻値 1:成功 0:失敗(ファイル読み書き不可かセッション IDが存在しない) 動作 フォームデータ(クエリー文字列か標準入力)を取得する。getUrlencodeFormData は URL エンコー

ドフォームデータのみ、getMultipartFormDataはマルチパートフォームデータのみを取得する 引数 %フォームデータを格納するハッシュ [, ?HTML構成文字を変換(※2を指定した場合改行は<br />にする)

[, 変換文字コード(euc/sjis/jis/EUC/JIS/SJIS ※大文字の場合は半角カタカナを全角置換) [, 重複キーのセ

パレータ(未定義の場合は上書き) [, 添付ファイルを格納するディレクトリのパス(省略時はハッシュ

に格納)]]]]

getFormData

getUrlencodedFormData

getMultipartFormData

戻値 取得したフォームデータのキーのリスト(処理順)(取得できなかった場合は無し) 意味 ハッシュからクエリー文字列を作成する 引数 %ハッシュ [, @配列(順番を指定する場合) [, セパレータ(省略時は”;”) [, ?値が空の場合はキー情報を

省略する]]] setQueryString

戻値 作成された文字列 動作 ハッシュからフォームの隠しフィールドを作成する 引数 %ハッシュ [, @配列(順番を指定する場合) [, セパレータ(省略時は"¥n") [, ?値が空の場合はキー情報

を省略する]]] setHiddenForm

戻値 作成された文字列 動作 書式を指定して時間を取得する 引数 [書式 [, GMTとの秒差(日本は3600*9) [, 基準時間(UTCシリアル値。省略時は現在時間)]]] getTime

戻値 整形済み時間 動作 時間からUTCシリアル値を取得する 引数 GMTとの秒差(日本は3600*9), 年(西暦4桁) [, 月 [, 日 [, 時 [, 分 [, 秒]]]]] getSerialTime

戻値 UTCシリアル値 動作 引数で指定したデータをBase64エンコード・デコードする 引数 エンコード(デコード)するデータ [, 1行あたりのバイト数(エンコード時のみ)]

base64encode

base64decode 戻値 なし (値渡しの場合はエンコード(デコード)されたデータ) 動作 引数で指定したデータをURLエンコード・デコードする 引数 エンコード(デコード)するデータ

urlencode

urldecode 戻値 なし (値渡しの場合はエンコード(デコード)されたデータ)

Page 38: STDIO.PLリファレンスwinofsql.jp/perl/stdio/stdio.pdfはCGI-Perl におけるコーディングの省力化と生産性の向上に貢献します。 このドキュメントはstdio.pl

- 37 -

STDIO.PL QUICK REFERENCE I STDIO.PLクイックリファレンス

(表記の記号の意味) %:ハッシュ/@:リスト/?:真か偽で指定/なし:スカラー変数/イタリックは参照(リファレンス) /[ ]は省略可能

(引数の色分け) 黒:第1引数/赤:第2引数/青:第3引数/緑:第4引数/紫:第5引数/茶:第6引数/紺:第7引数

※ 各関数の詳細は詳細リファレンスを参照してください。

動作 HTTPクッキーを作成する 引数 %@クッキー本体 [, クッキーID [, 有効期限 [, 有効パス [, 有効ドメイン [, ?セキュア時のみクッキ

ー発行 [, ?クッキー本体を戻り値に返す]]]]]] setCookie

戻値 クッキーの値(第7引数にクッキー本体を戻り値に返すようにした場合) 動作 ブラウザからHTTPクッキーを取得する 引数 %@クッキー本体を格納するハッシュ(配列) [, クッキーID] getCookie 戻値 取得したクッキーのキーのリスト(処理順)(取得できなかった場合は無し) 動作 セッション管理(ハッシュに有効期限と IDを付けて保存) 引数 ファイルのパス, %@セッション情報 [, セッション ID [, 有効秒数(省略時は3600秒)]] setSession

戻値 1:成功 0:失敗(ファイル読み書き不可) 動作 セッション管理(setSession関数で保存したセッション情報を読み出す) 引数 ファイルのパス, %@セッション情報を格納するハッシュ(配列) [, セッション ID] getSession

戻値 1:成功 0:失敗(ファイル読み書き不可かセッション IDが存在しない) 動作 フォームデータ(クエリー文字列か標準入力)を取得する。getUrlencodeFormDataはURLエンコー

ドフォームデータのみ、getMultipartFormDataはマルチパートフォームデータのみを取得する 引数 %フォームデータを格納するハッシュ [, ?HTML構成文字を変換(※2を指定した場合改行は<br />にする)

[, 変換文字コード(euc/sjis/jis/EUC/JIS/SJIS ※大文字の場合は半角カタカナを全角置換) [, 重複キーのセパレータ(未定義の場合は上書き) [, 添付ファイルを格納するディレクトリのパス(省略時はハッシュに格納)]]]]

getFormData

getUrlencodedFormData

getMultipartFormData

戻値 取得したフォームデータのキーのリスト(処理順)(取得できなかった場合は無し) 意味 ハッシュからクエリー文字列を作成する 引数 %ハッシュ [, @配列(順番を指定する場合) [, セパレータ(省略時は”;”) [, ?値が空の場合はキー情報を

省略する]]] setQueryString

戻値 作成された文字列 動作 ハッシュからフォームの隠しフィールドを作成する 引数 %ハッシュ [, @配列(順番を指定する場合) [, セパレータ(省略時は"¥n") [, ?値が空の場合はキー情報

を省略する]]] setHiddenForm

戻値 作成された文字列 動作 書式を指定して時間を取得する 引数 [書式 [, GMTとの秒差(日本は3600*9) [, 基準時間(UTCシリアル値。省略時は現在時間)]]] getTime

戻値 整形済み時間 動作 時間からUTCシリアル値を取得する 引数 GMTとの秒差(日本は3600*9), 年(西暦4桁) [, 月 [, 日 [, 時 [, 分 [, 秒]]]]] getSerialTime

戻値 UTCシリアル値 動作 引数で指定したデータをBase64エンコード・デコードする 引数 エンコード(デコード)するデータ [, 1行あたりのバイト数(エンコード時のみ)]

base64encode

base64decode 戻値 なし (値渡しの場合はエンコード(デコード)されたデータ) 動作 引数で指定したデータをURLエンコード・デコードする 引数 エンコード(デコード)するデータ

urlencode

urldecode 戻値 なし (値渡しの場合はエンコード(デコード)されたデータ)