Server-Sent Eventsが期待通りに動かない
以下のソースコードを使ってSSEのテストをしています。ソースはMDNが公開しているサンプルを更に簡略化して使用しています。
<?php
header( "Content-Type: text/event-stream" );
while ( true ) {
$curDate = date( DATE_ISO8601 );
echo 'data: This is a message at time ' . $curDate, "\n\n";
while (ob_get_level() > 0) {
ob_end_flush();
}
flush();
if ( connection_aborted() ) break;
sleep(1);
}
<html>
<head>
<meta charset='UTF-8'>
<title>Server-sent events demo</title>
</head>
<body>
<button>Close the connection</button>
<ul>
</ul>
<script>
console.log( new Date() ); //(1)
var button = document.querySelector( 'button' );
var evtSource = new EventSource( 'sse.php' );
var eventList = document.querySelector( 'ul' );
evtSource.onopen = function () {
console.log( 'Connection to server opened.' );
};
evtSource.onmessage = function ( e ) {
console.log( new Date() ); //(2)
var newElement = document.createElement( 'li' );
newElement.textContent = 'message: ' + e.data;
eventList.appendChild( newElement );
};
evtSource.onerror = function () {
console.log( 'EventSource failed.' );
};
button.onclick = function () {
console.log( 'Connection closed' );
evtSource.close();
};
</script>
</body>
</html>
環境
- RockyLinux8
- apache2.4
- PHP7.2
phpのoutput_buffering=0を設定。
期待する動作
ウェブブラウザからindex.htmlに接続すると、1秒おきにphpからのメッセージをウェブブラウザ上に表示。
現状
index.htmlに接続すると即座には何も表示されず、接続後ちょうど1分で出力が始まります(JavaScriptの(1)と(2)の出力を確認しました)。このとき1件ずつでなく、5、6件ずつ位で出力されます。出力されるメッセージはサーバ上での実行時刻ですが、これは(1)の時刻以降の1秒刻みになります(下の画像のようになります)。つまり1分前の出力を数件単位で受け取っているようです。
実現したいこと・知りたいこと
期待する動作に近づけたいです。
読み込み後、即座に開始しなければ困る、ということではないのですが、せめて数秒以内に収まってほしいです。1分かかるのはどこか設定の問題でしょうか(apache?php?javascript?)。
実際には毎秒メッセージを送信することはありませんが、なぜ数件ずつまとめて送信されるのか原因が知りたいです。出力バッファの問題かと思い、前述の「output_buffering=0」を設定しましたが変化ありませんでした。こちらも設定の問題でしょうか(apache?php?javascript?)。
原因、解消方法等ささいなことでも構いませんので情報をご提供頂けますと助かります。足りない情報がありましたらお知らせください。
どうぞよろしくお願いいたします。
追記
バッファリングオフ等々で検索したところnginxでの事例が多々ありましたので、nginxで試したところ、期待通りの出力を得ることが出来ました。結果としてapacheがバッファリングしていることが問題と考えます。apacheの設定でバッファリング関連で試すべき箇所を教えて下さいますか。
「dnf install httpd」でインストールしたapacheをほぼそのまま使用しています。