web-dev-qa-db-ja.com

サーバーに到達できない場合、PHPのPDOはMySQLのATTR_TIMEOUTオプションを無視します

接続を試みるランダムなIPを入力しても、mysqlサーバーに到達できないシナリオをテストしています。 PDO::ATTR_TIMEOUT => 1を使用して、1秒後にタイムアウトするようにPDOのオプションを設定しました。ただし、例外をスローするのに30秒かかります。このタイムアウトは、実際のmysql接続時間にのみ適用され、mysqlが実行されているサーバーには適用されないと思います。

Mysqlサーバーへの接続をタイムアウトするためにどのPHPオプションを変更する必要がありますか?

18
timetofly

置くだけ

ini_set("default_socket_timeout", 2);

pDO()接続文字列の前。

(Windowsでテスト済みですが、Linuxでも問題ないはずです。)


どうして?

マニュアルを通してこれを追いかける:

Mysqlndドライバーは、基になる接続にソケットを使用します。タイムアウトを設定するには、ソケット(ストリーム)タイムアウト関数を使用する必要があります。 (参照: http://php.net/manual/en/mysqlnd.notes.php

Mysqlndを使用するということは、基礎となる接続にPHPストリームを使用することを意味します。mysqlndの場合、PHPストリームのドキュメント(ストリーム)は、タイムアウト設定などの詳細について参照する必要があります。 MySQLクライアントライブラリのドキュメント。


より詳細な制御が必要な場合は、実際のソケットをより具体的に制御できる可能性があります。これはUNIXのみであるため、テストしていません。 mysqlndが使用するソケットを設定するには、ini設定を使用してソケットを指定できます(参照: http://php.net/manual/en/ref.pdo-mysql.connection.php

PDO_MYSQLがmysqlndに対してコンパイルされている場合、デフォルトのソケットはpdo_mysql.default_socket設定を介して設定できます。

その設定については http://php.net/manual/en/ref.pdo-mysql.php#ini.pdo-mysql.default-socket を参照してください。

その後、 http://php.net/manual/en/function.stream-set-timeout.php を使用してタイムアウトを設定できる場合があります。

しかし、おそらくデフォルトを設定し、完了したらリセットする方が簡単です...

11
Robbie

php.iniこの構成変数を更新できます。

mysql.connect_timeout = 1
5
Akram Fares

オプションをPDOコンストラクターに渡します。

https://github.com/phalcon/cphalcon/blob/2.0.0/phalcon/db/adapter/pdo.zep#L135-L149

2
Alpesh Rathod
 
 $ Host = '192.168.1.36'; 
 $ dbname = 'test'; 
 $ username = 'test'; 
 $ password = ''; 
 
 $ start = time(); 
 try {
 $ db = new PDO(
 "mysql:Host = $ Host; dbname = $ dbname "、
 $ username、
 $ password、
 array(
 PDO :: ATTR_TIMEOUT => 1、
 PDO :: ATTR_ERRMODE => PDO :: ERRMODE_EXCEPTION 
)
); 
} catch(Exception $ e){
 echo time()-$ start; 
 echo "\ n"; 
 echo $ e-> getMessage(); 
} 
 

このコードスニペットは問題を解決するはずです。

mysqli、mysqlnd、pdo-mysqlの違い:

  • (非推奨)mysqlndは、関数が手続き型であるmsyqlネイティブドライバーを意味します
  • mysqldiriverのmysqliオブジェクト形式
  • pdo-mysqlは、mysqlデータベースへの接続をサポートするためのpdoデータベース抽象化用のプラグインです。
1
nobody0day

PDO :: ATTR_TIMEOUT:タイムアウト期間を秒単位で指定します。 すべてのドライバーがこのオプションをサポートしているわけではなく、その意味はドライバーごとに異なる場合があります。たとえば、sqliteは書き込み可能なロックの取得をあきらめる前にこの時間値まで待機しますが、他のドライバーはこれを接続または読み取りタイムアウト間隔として解釈する場合があります。

このドキュメントには、接続タイムアウト間隔を意味しない場合や、ドライバーがサポートしていない場合があることが明記されています。

1
invisal

私の場合、オプションをPDOのコンストラクターに入れると、機能します。また、php.iniの設定はすべて無視されます。

$options = array(PDO::ATTR_TIMEOUT] => 1);//must be in the constructor
$db = new DB($dsn, $username, $password, $options);

ここでは初期接続をテストしているので、接続を開くときにこのオプションが必要であることは理にかなっています。したがって、以下は、最初の接続後のすべてのクエリで機能するはずです。

$db = new DB($dsn, $username, $password, $options);
$db->setAttribute(PDO::ATTR_TIMEOUT, 2);
1
Aris