Content-Type: text/event-stream 에 대해서 예제를 포함하여 자세히 설명해줘
Content-Type: text/event-stream은 서버에서 클라이언트로 실시간으로 데이터를 전송하기 위해 사용되는 MIME 타입입니다. 이 방식은 주로 서버 전송 이벤트(Server-Sent Events, SSE)에서 사용되며, 클라이언트가 서버로부터 지속적으로 업데이트를 받을 수 있도록 합니다. SSE는 HTTP 프로토콜을 기반으로 하며, 클라이언트는 서버에 연결을 유지하고 서버는 클라이언트에게 데이터를 푸시할 수 있습니다.
주요 특징
단방향 통신: SSE는 서버에서 클라이언트로의 단방향 통신을 지원합니다. 클라이언트는 서버에 요청을 보내고, 서버는 클라이언트에게 데이터를 전송합니다. 클라이언트에서 서버로의 데이터 전송은 일반적인 HTTP 요청을 통해 이루어집니다.
연결 유지: 클라이언트는 서버와의 연결을 유지하며, 서버는 클라이언트에게 새로운 이벤트가 발생할 때마다 데이터를 전송합니다.
자동 재연결: 클라이언트가 서버와의 연결이 끊어지면, 자동으로 재연결을 시도합니다.
예제
아래는 간단한 서버 전송 이벤트를 구현하는 예제입니다.
const express = require('express');
const app = express();
const PORT = 3000;
app.get('/events', (req, res) => {
// SSE 헤더 설정
res.setHeader('Content-Type', 'text/event-stream');
res.setHeader('Cache-Control', 'no-cache');
res.setHeader('Connection', 'keep-alive');
// 클라이언트에 데이터 전송
const sendEvent = (data) => {
res.write(`data: ${JSON.stringify(data)}\n\n`);
};
// 5초마다 이벤트 전송
const intervalId = setInterval(() => {
const eventData = { message: 'Hello, this is a server-sent event!', timestamp: new Date() };
sendEvent(eventData);
}, 5000);
// 클라이언트 연결 종료 시 인터벌 클리어
req.on('close', () => {
clearInterval(intervalId);
res.end();
});
});
app.listen(PORT, () => {
console.log(`Server is running on http://localhost:${PORT}`);
});
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>SSE Example</title>
</head>
<body>
<h1>Server-Sent Events Example</h1>
<div id="events"></div>
<script>
const eventSource = new EventSource('/events');
eventSource.onmessage = function(event) {
const data = JSON.parse(event.data);
const eventsDiv = document.getElementById('events');
eventsDiv.innerHTML += `<p>${data.timestamp}: ${data.message}</p>`;
};
eventSource.onerror = function(event) {
console.error("EventSource failed:", event);
};
</script>
</body>
</html>
PHP 와 연동하는 예제를 3가지만 작성해줘
PHP와 서버 전송 이벤트(Server-Sent Events, SSE)를 연동하는 예제를 세 가지 제공하겠습니다. 각 예제는 PHP를 사용하여 클라이언트에 실시간 데이터를 전송하는 방법을 보여줍니다.
예제 1: 기본 SSE 구현
1. PHP 서버 코드 (sse.php)
<?php
header('Content-Type: text/event-stream');
header('Cache-Control: no-cache');
$counter = 0;
while (true) {
// 데이터 전송
echo "data: " . json_encode(['message' => 'Hello, this is event number ' . $counter]) . "\n\n";
ob_flush(); // 출력 버퍼를 비웁니다.
flush(); // 클라이언트로 즉시 전송합니다.
$counter++;
sleep(5); // 5초 대기
}
?>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>SSE Example</title>
</head>
<body>
<h1>Server-Sent Events Example</h1>
<div id="events"></div>
<script>
const eventSource = new EventSource('sse.php');
eventSource.onmessage = function(event) {
const data = JSON.parse(event.data);
const eventsDiv = document.getElementById('events');
eventsDiv.innerHTML += `<p>${data.message}</p>`;
};
eventSource.onerror = function(event) {
console.error("EventSource failed:", event);
};
</script>
</body>
</html>
예제 2: 실시간 시간 업데이트
<?php
header('Content-Type: text/event-stream');
header('Cache-Control: no-cache');
while (true) {
// 현재 시간 전송
echo "data: " . json_encode(['time' => date('H:i:s')]) . "\n\n";
ob_flush();
flush();
sleep(1); // 1초 대기
}
?>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Real-Time Clock</title>
</head>
<body>
<h1>Current Time</h1>
<div id="time"></div>
<script>
const eventSource = new EventSource('time.php');
eventSource.onmessage = function(event) {
const data = JSON.parse(event.data);
const timeDiv = document.getElementById('time');
timeDiv.innerHTML = `<p>${data.time}</p>`;
};
eventSource.onerror = function(event) {
console.error("EventSource failed:", event);
};
</script>
</body>
</html>
예제 3: 데이터베이스에서 실시간 데이터 전송
이 예제에서는 데이터베이스에서 실시간으로 데이터를 가져와 클라이언트에 전송합니다.
<?php
header('Content-Type: text/event-stream');
header('Cache-Control: no-cache');
// 데이터베이스 연결
$mysqli = new mysqli("localhost", "username", "password", "database");
if ($mysqli->connect_error) {
die("Connection failed: " . $mysqli->connect_error);
}
while (true) {
// 데이터베이스에서 최신 메시지 가져오기
$result = $mysqli->query("SELECT message FROM messages ORDER BY id DESC LIMIT 1");
$row = $result->fetch_assoc();
if ($row) {
echo "data: " . json_encode($row) . "\n\n";
ob_flush();
flush();
}
sleep(5); // 5초 대기
}
?>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Database Events</title>
</head>
<body>
<h1>Latest Message from Database</h1>
<div id="messages"></div>
<script>
const eventSource = new EventSource('db_events.php');
eventSource.onmessage = function(event) {
const data = JSON.parse(event.data);
const messagesDiv = document.getElementById('messages');
messagesDiv.innerHTML += `<p>${data.message}</p>`;
};
eventSource.onerror = function(event) {
console.error("EventSource failed:", event);
};
</script>
</body>
</html>
예제 1: 기본적인 SSE 구현으로, 5초마다 클라이언트에 이벤트를 전송합니다.
예제 2: 현재 시간을 1초마다 클라이언트에 전송하여 실시간 시계를 구현합니다.
예제 3: 데이터베이스에서 최신 메시지를 가져와 5초마다 클라이언트에 전송합니다. 데이터베이스 연결 정보를 적절히 수정해야 합니다.
이 예제들을 통해 PHP와 SSE를 연동하여 실시간 데이터를 클라이언트에 전송하는 방법을 이해할 수 있습니다.