著者: Armel Fauveau
元のアドレス: http://www.phpbuilder.net/columns/armel20010427.php3
PHP はリモートまたはローカル サーバーのソケットを開くことができます。以下は、ソケットを使用した簡単な例です。Usenet ニュース サーバーに接続し、サーバーと通信し、正確なニュース グループからいくつかの記事をダウンロードします。
PHP を使用してソケットを開く
fsockopen() を使用してソケットを開きます。この関数は PHP3 と PHP4 の両方に存在します。関数のプロトタイプは次のとおりです。
intfsockopen
(string hostname,
int port [,
int errno [,
string errstr [,
double timeout]]])
?>ネットワーク ホスト、ホスト名のポートへの TCP ソケット接続が確立されます。ホスト名にはドメイン名または IP アドレスを使用できます。 UDP 接続の場合は、プロトコル udp://hostname を指定する必要があります。 UNIX ホストの場合、ホスト名はソケットへのパスで使用され、この例ではポートを 0 に設定する必要があります。オプションのタイムアウトを使用して、接続タイムアウトの秒数を設定できます。
fsockopen() の詳細については、http://www.php.net/manual/function.fsockopen.php を参照してください。
ネットワーク ニュース転送プロトコル (NNTP)
usenet ニュース サーバーにアクセスするには、特別なプロトコルが必要です。 NNTP、ネットワーク ニュース転送プロトコル標準と呼ばれます。このプロトコルの詳細は RFC977 に記載されており、http://www.w3.org/Protocols/rfc977/rfc977.html で参照できます。このドキュメントでは、さまざまなコマンドを使用して NNTP サーバーに接続し、通信する方法について詳しく説明します。
サーバーに接続する
NNTP サーバーに接続するには、サーバーのホスト名 (または IP アドレス) とサーバーがリッスンするポートを知っている必要があります。接続が失敗したときにプログラムが「フリーズ」しないように、タイムアウトを追加することもお勧めします。
$cfgServer = "your.news.host";
$cfgPort = 119;
$cfgTimeOut = 10;
// タイムアウトなしで asocket を開きます
$usenet_handle = fsockopen($cfgServer, $cfgPort);
else
// タイムアウトあり
$usenet_handle = fsockopen($cfgServer, $cfgPort, &$errno, &$errstr, $cfgTimeOut);
if(!$usenet_handle) {
echo "Connexionfailedn";
exit();
else {
$tmp = fgets($usenet_handle, 1024);
サーバーと通信します
サーバーと接続し、以前に開いたソケット接続を通じてサーバーと対話できます。サーバーに対して「特定のニュース グループから最新の 10 件の記事を取得したい」と言いましょう。 RFC977 は、正しいニュース グループを選択する方法に関するコマンドを次のように定義しています。
GROUPggg
必須パラメータ ggg は、選択するニュース グループの名前 (net.news など) です。 list コマンドを使用すると、有効なニュース リストを取得できます。選択応答が成功すると、グループ内の最初と最後の 2 つのニュース記事のニュース番号と、アーカイブされたニュース番号の推定値が返されます。
例:
chrome:~$ telnetmy.news.host 119
aa.bb.cc.dd を試行中...
tomy.news.host に接続しました。
エスケープ文字は '^]' です。 hostInterNetNews NNRP サーバー INN 2.2.2 13-Dec-1999 が準備完了 (投稿OK)
GROUP alt.test
211 232 222996 223235alt.test
quit
205
コマンド「GROUP alt.test」を受信した後、ニュース サーバーは「211232 222996 223235 alt.test」を返しました。211 は RFC 識別コードです (コマンドが正常に実行されたことを示す簡単な説明です。詳細については RFC を確認してください)。返された情報は、記事が 232 件あり、その中で最も古いニュースのインデックス番号が 222996 であることを示しています。最新のニュースインデックス番号は 223235 です。ここで計算してみましょう: 222996+232 は 232235 に等しくありません。見つからない記事はサーバーから削除されたか、作成者によってキャンセルされたか (はい、それは可能で簡単です)、または削除されました。
注意してください。もちろん、これはサーバーがパブリックかプライベートかによって異なります。通常、誰でもニュースを入手できますが、ニュースを発行するには認証が必要です。
//$cfgUser = "xxxxxx";
//$cfgPasswd = "yyyyyy";
$cfgNewsGroup = "alt.php";
// プライベートサーバーでは識別が必要です
if($cfgUser) {
fputs($usenet_handle, "AUTHINFO USER".$cfgUser."n");
$tmp = fgets($usenet_handle, 1024);
fputs($usenet_handle, "AUTHINFO PASS ".$cfgPasswd."); = $ TMP = fgets ニュースグループの選択
fputs($usenet_handle, "GROUP ".$cfgNewsGroup."n");
$tmp = fgets($usenet_handle, 1024); 480 コマンドには認証が必要です") {
echo "$ tmpn";
exit();
}
$info = split(" ", $tmp);
$first = $info[2];
$last = $info[3];
print "First : $firstn";
print "Last : $lastn";>
いくつかの記事を取得する
これで、最新の 10 件の記事を簡単に取得できます。 RFC977 には、ARTICLE コマンドを記事のインデックス番号またはメッセージ ID とともに使用できると記載されています。注意のため、ここでは記事のインデックス番号とメッセージ ID が異なります。ニュース サーバーごとに定義が異なるため、同じ記事でも異なるニュース サーバーではインデックス番号が異なりますが、メッセージ ID は同じである必要があります。 (記事のヘッダーに含まれます)
$cfgLimit = 10;
// 最後の記事をアップロード
$boucle=$last-$cfgLimit;
set_time_limit (0);
fputs($usenet_handle, "ARTICLE$bouclen");
$tmp = fgets($usenet_handle, 4096); != "220") {c Echo "+----------------------------------------------------- -+n"; --------------------+n"
}
else {
while($tmp!=".rn") {
$tmp = fgets($usenet_handle .
?>
このサーバー上のこのグループから得られた最新ニュースは 10 件のみです。 HEAD コマンドを使用して記事のヘッダー情報を取得したり、BODY コマンドを使用してニュースの本文を取得したりすることもできます。
接続を閉じる
fclose() 関数を使用して、NNTP サーバーとのセッションを終了します。 もちろん、次のように新しいファイルを作成することもできます:
// close connexion
fclose($usenet_handle) ;
?>
fclose() の詳細については、http://www.php.net/manual/function.fclose.php を参照してください。
結論
この記事では、特定の状況における状況のみを説明します。ソケット接続のオープン、使用、およびクローズの方法: NNTP サーバーに接続し、ニュース グループからいくつかの記事を取得します。 POST コマンドを使用して NNTP サーバーに記事を公開することは、それほど複雑ではありません。
次のステップは、記事を簡単に保存し、検索エンジン (htgid、http://www.htdig.org/ など) の記事を使用してインデックスを作成できるニュース クライアントを作成することです (そして Netscape の一部を削除します)。ニュースグループの下でキーワード検索ができるWEBアプリケーションです。以下に例を示します。http://www.phpindex.com/ng/ にアクセスしてダウンロードできます。