socket_connect ня тайм-аўт

Я выкарыстоўваю сокеты для адпраўкі дадзеных на сервер, які не можа быць адказвае. Так што я спрабую вызначыць таймаўт, з дапамогай гэтага рашэння ў SO.

зрабіць PHP socket_connect таймаўт

socket_set_option($socket, SOL_SOCKET, SO_RCVTIMEO, array('sec' => 1, 'usec' => 0));
socket_set_option($socket, SOL_SOCKET, SO_SNDTIMEO, array('sec' => 1, 'usec' => 0));

Гэта працуе, калі злучэнне вырабляецца і сервер займае занадта шмат часу, каб адказаць. Але калі ён не можа стварыць злучэнне socket_connect ($ панэлька, $ адр, $ порт); тайм-аўт складае каля 20 секунд.

Чаму гэта 20 другі тайм-аўт адбываецца і як я магу прымусіць стварэнне падлучэння да тайм-аўт пасьля 1 секунды таксама?

3
мікрасекунды з'яўляюцца мікрасекунды чаму вы ўсталявалі на 0?
дададзена аўтар Robert, крыніца
@RobertPodwika, таму што я хачу, каб гэта было exacly 1 другое і 0 мікрасекунд
дададзена аўтар letiagoalves, крыніца
@RobertPodwika, таму што я хачу, каб гэта было exacly 1 другое і 0 мікрасекунд
дададзена аўтар letiagoalves, крыніца
@RobertPodwika, таму што я хачу, каб гэта было exacly 1 другое і 0 мікрасекунд
дададзена аўтар letiagoalves, крыніца

12 адказы

Вы можаце зрабіць гэта шляхам пераключэння на неблокирующем гняздо, зацыкленне, пакуль альбо злучэнне не будзе атрымана або тайм-аўт быў дасягнуты, а затым назад да блакаванні зноў.

// an unreachable address
$host = '10.0.0.1';
$port = 50000;
$timeout = 2;

$sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);

// switch to non-blocking
socket_set_nonblock($sock);

// store the current time
$time = time();

// loop until a connection is gained or timeout reached
while ([email protected]_connect($sock, $host, $port)) {
    $err = socket_last_error($sock);

   //success!
    if($err === 56) {
        print('connected ok');
        break;
    }

   //if timeout reaches then call exit();
    if ((time() - $time) >= $timeout) {

        socket_close($sock);
        print('timeout reached!');
        exit();
    }

   //sleep for a bit
    usleep(250000);
}

// re-block the socket if needed
socket_set_block($sock);

Рэдагаванне: гл @letiagoalves адказваць за акуратным рашэнне, калі вы карыстаецеся сокеты, створаныя з fsockopen() або stream_socket_client ()

3
дададзена
+1 дзякуй. Я выкарыстаў іншы механізм. гэта было лёгка змяніць. см мой адказ
дададзена аўтар letiagoalves, крыніца

Вы можаце зрабіць гэта шляхам пераключэння на неблокирующем гняздо, зацыкленне, пакуль альбо злучэнне не будзе атрымана або тайм-аўт быў дасягнуты, а затым назад да блакаванні зноў.

// an unreachable address
$host = '10.0.0.1';
$port = 50000;
$timeout = 2;

$sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);

// switch to non-blocking
socket_set_nonblock($sock);

// store the current time
$time = time();

// loop until a connection is gained or timeout reached
while ([email protected]_connect($sock, $host, $port)) {
    $err = socket_last_error($sock);

   //success!
    if($err === 56) {
        print('connected ok');
        break;
    }

   //if timeout reaches then call exit();
    if ((time() - $time) >= $timeout) {

        socket_close($sock);
        print('timeout reached!');
        exit();
    }

   //sleep for a bit
    usleep(250000);
}

// re-block the socket if needed
socket_set_block($sock);

Рэдагаванне: гл @letiagoalves адказваць за акуратным рашэнне, калі вы карыстаецеся сокеты, створаныя з fsockopen() або stream_socket_client ()

3
дададзена
+1 дзякуй. Я выкарыстаў іншы механізм. гэта было лёгка змяніць. см мой адказ
дададзена аўтар letiagoalves, крыніца

Вы можаце зрабіць гэта шляхам пераключэння на неблокирующем гняздо, зацыкленне, пакуль альбо злучэнне не будзе атрымана або тайм-аўт быў дасягнуты, а затым назад да блакаванні зноў.

// an unreachable address
$host = '10.0.0.1';
$port = 50000;
$timeout = 2;

$sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);

// switch to non-blocking
socket_set_nonblock($sock);

// store the current time
$time = time();

// loop until a connection is gained or timeout reached
while ([email protected]_connect($sock, $host, $port)) {
    $err = socket_last_error($sock);

   //success!
    if($err === 56) {
        print('connected ok');
        break;
    }

   //if timeout reaches then call exit();
    if ((time() - $time) >= $timeout) {

        socket_close($sock);
        print('timeout reached!');
        exit();
    }

   //sleep for a bit
    usleep(250000);
}

// re-block the socket if needed
socket_set_block($sock);

Рэдагаванне: гл @letiagoalves адказваць за акуратным рашэнне, калі вы карыстаецеся сокеты, створаныя з fsockopen() або stream_socket_client ()

3
дададзена
+1 дзякуй. Я выкарыстаў іншы механізм. гэта было лёгка змяніць. см мой адказ
дададзена аўтар letiagoalves, крыніца

I changed my socket communication mechanism to use stream_socket_client ($remote_socket, &$errno, &$errstr, $timeout) function instead. This function allows to define the connect timeout unlike socket_connect ($socket, $address, $port) which doesn't.

Каб прымусіць тайм-аўт, выкарыстоўваючы socket_connect см @bigtallbill адказ.

2
дададзена
Гэта, безумоўна, нашмат акуратней: P Хоць гэта не вяртае файлавы рэсурс замест сокета rescource, таму выпадкі выкарыстання вызначана нешта разгледзець. Я не валодае дастаткова з гнездавой Унутраныя сказаць, ці лепш з дапамогай гэтых метадаў.
дададзена аўтар bigtallbill, крыніца

Варыянты SO_RCVTIMEO/SO_SNDTIMEO не працуюць socket_connect на некаторых платформах, але толькі для socket_recv/socket_send. Я магу бачыць, што гэта працуе на Ubuntu, але не Mac OSX.

0
дададзена

Варыянты SO_RCVTIMEO/SO_SNDTIMEO не працуюць socket_connect на некаторых платформах, але толькі для socket_recv/socket_send. Я магу бачыць, што гэта працуе на Ubuntu, але не Mac OSX.

0
дададзена

Варыянты SO_RCVTIMEO/SO_SNDTIMEO не працуюць socket_connect на некаторых платформах, але толькі для socket_recv/socket_send. Я магу бачыць, што гэта працуе на Ubuntu, але не Mac OSX.

0
дададзена

Варыянты SO_RCVTIMEO/SO_SNDTIMEO не працуюць socket_connect на некаторых платформах, але толькі для socket_recv/socket_send. Я магу бачыць, што гэта працуе на Ubuntu, але не Mac OSX.

0
дададзена

Я спрабаваў шмат варыянтаў з гнёздамі ..

fsockopen the best for simple operations, ex. testing connections

0
дададзена

Я спрабаваў шмат варыянтаў з гнёздамі ..

fsockopen the best for simple operations, ex. testing connections

0
дададзена

Я спрабаваў шмат варыянтаў з гнёздамі ..

fsockopen the best for simple operations, ex. testing connections

0
дададзена

Я спрабаваў шмат варыянтаў з гнёздамі ..

fsockopen the best for simple operations, ex. testing connections

0
дададзена