웹 푸시로 작업할 때 고충 중 하나는 푸시 메시지를 트리거하는 것이 '까다로'입니다. 푸시 메시지를 트리거하려면 애플리케이션이 푸시에 POST 요청을 해야 함 웹 푸시 후 웹 푸시에 따라 프로토콜을 사용합니다. 모든 제품에 푸시를 사용하려면 VAPID를 사용해야 하는 브라우저 (애플리케이션 서버 키라고도 함). 이는 기본적으로 메시지를 보낼 수 있습니다 푸시 메시지로 데이터를 전송하려면 데이터가 암호화된 특정 헤더 를 추가해야 브라우저가 메시지를 올바르게 복호화할 수 있습니다.
푸시 트리거의 주요 문제는 문제가 발생하면 진단이 어렵고 있습니다. 시간이 지남에 따라 더 많은 브라우저가 지원되면서 개선되고 있지만 쉽지 않은 일입니다. 대상 라이브러리를 사용하여 암호화, 서식 지정 및 중요한 역할을 합니다
라이브러리가 하는 일에 대해 자세히 알아보고 싶다면 다음 섹션에서 살펴보겠습니다. 지금은 구독을 관리하고 기존 웹 푸시 라이브러리를 사용하여 푸시 요청을 할 수 있습니다.
이 섹션에서는 web-push 노드 라이브러리를 사용하여 v3 지도에 통합할 수 있습니다. 다른 언어에도 차이가 있지만 그렇게 다르지 않을 것입니다. Node는 JavaScript이고 가장 편한 방법이라는 것을 깨달았습니다.
단계는 다음과 같습니다.
- 백엔드로 구독을 전송하고 저장합니다.
- 저장된 구독을 검색하고 푸시 메시지를 트리거합니다.
구독 저장 중
데이터베이스에서 PushSubscription
를 저장하고 쿼리하는 방법은 다음에 따라 다릅니다.
서버 측 언어와 데이터베이스를 선택하게 되지만,
예시가 있었습니다.
데모 웹페이지에서는 간단한 POST 요청을 실행하여 PushSubscription
가 백엔드로 전송됩니다.
function sendSubscriptionToBackEnd(subscription) {
return fetch('/api/save-subscription/', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify(subscription),
})
.then(function (response) {
if (!response.ok) {
throw new Error('Bad status code from server.');
}
return response.json();
})
.then(function (responseData) {
if (!(responseData.data && responseData.data.success)) {
throw new Error('Bad response from server.');
}
});
}
데모의 Express 서버에는
/api/save-subscription/
엔드포인트:
app.post('/api/save-subscription/', function (req, res) {
이 경로에서는 요청이 양호하며 가비지:
const isValidSaveRequest = (req, res) => {
// Check the request body has at least an endpoint.
if (!req.body || !req.body.endpoint) {
// Not a valid subscription.
res.status(400);
res.setHeader('Content-Type', 'application/json');
res.send(
JSON.stringify({
error: {
id: 'no-endpoint',
message: 'Subscription must have an endpoint.',
},
}),
);
return false;
}
return true;
};
구독이 유효하면 구독을 저장하고 적절한 JSON 응답:
return saveSubscriptionToDatabase(req.body)
.then(function (subscriptionId) {
res.setHeader('Content-Type', 'application/json');
res.send(JSON.stringify({data: {success: true}}));
})
.catch(function (err) {
res.status(500);
res.setHeader('Content-Type', 'application/json');
res.send(
JSON.stringify({
error: {
id: 'unable-to-save-subscription',
message:
'The subscription was received but we were unable to save it to our database.',
},
}),
);
});
이 데모는 nedb를 사용하여 구독을 저장합니다. 간단한 파일 기반 데이터베이스이지만 원하는 데이터베이스를 사용할 수 있습니다. 우리는 이것을 단지 별도의 설정이 필요하지 않습니다. 프로덕션의 경우 보다 안정적인 것을 사용해야 합니다. 저는 오래된 MySQL을 사용하세요.)
function saveSubscriptionToDatabase(subscription) {
return new Promise(function (resolve, reject) {
db.insert(subscription, function (err, newDoc) {
if (err) {
reject(err);
return;
}
resolve(newDoc._id);
});
});
}
푸시 메시지 보내기
푸시 메시지를 보낼 때는 궁극적으로
메시지를 보낼 수 있습니다. 일반적인 방법은 관리자가 액세스할 수 있는 관리 페이지를 만드는 것입니다.
푸시 메시지를 구성하고 트리거합니다. 하지만 로컬에서 실행하거나
PushSubscription
목록에 액세스하고 코드를 실행하여
푸시 메시지를 트리거합니다.
데모에는 '관리자 추천'이 푸시를 트리거할 수 있는 페이지가 있습니다. 데모일 뿐이므로 공개 페이지로 이동합니다.
데모 작동과 관련된 각 단계를 살펴보겠습니다. 베이비 모든 사람이 따라야 하는 단계를 수행해야 합니다.
사용자 구독에 관해 설명할 때 applicationServerKey
를
옵션 subscribe()
개. 이 비공개 키는 백엔드에서 필요합니다.
데모에서는 이러한 값이 Node 앱에 이렇게 추가됩니다 (코드는 지루하지만 마법은 없다는 것을 알아두세요.)
const vapidKeys = {
publicKey:
'BEl62iUYgUivxIkv69yViEuiBIa-Ib9-SkvMeAtA3LFgDzkrxZJjSgSnfckjBJuBkr3qBUYIHBQFLXYp5Nksh8U',
privateKey: 'UUxI4O8-FbRouAevSmBQ6o18hgE4nSG3qwvJTfKc-ls',
};
다음으로 노드 서버의 web-push
모듈을 설치해야 합니다.
npm install web-push --save
그런 다음 Node 스크립트에 web-push
모듈이 필요합니다.
다음과 같습니다.
const webpush = require('web-push');
이제 web-push
모듈을 사용할 수 있습니다. 먼저 web-push
모듈에 다음 정보를 제공해야 합니다.
애플리케이션 서버 키를 사용합니다 VAPID 키라고도 하는
참조하세요.)
const vapidKeys = {
publicKey:
'BEl62iUYgUivxIkv69yViEuiBIa-Ib9-SkvMeAtA3LFgDzkrxZJjSgSnfckjBJuBkr3qBUYIHBQFLXYp5Nksh8U',
privateKey: 'UUxI4O8-FbRouAevSmBQ6o18hgE4nSG3qwvJTfKc-ls',
};
webpush.setVapidDetails(
'mailto:web-push-book@gauntface.com',
vapidKeys.publicKey,
vapidKeys.privateKey,
);
'mailto:' 문자열. 이 문자열은 URL 또는 mailto여야 합니다. 이메일 주소를 입력하세요. 이 정보는 실제로 웹 푸시 서비스에 푸시를 트리거합니다 이렇게 하는 이유는 웹 푸시 서비스에 몇 가지 정보를 확보하여 발신자에게 연락할 수 있습니다.
이제 web-push
모듈을 사용할 준비가 되었습니다. 다음 단계는 푸시 메시지를 트리거하는 것입니다.
데모에서는 역할 관리 패널을 사용하여 푸시 메시지를 트리거합니다.
'푸시 메시지 트리거' 클릭 버튼을 누르면 /api/trigger-push-msg/
에 POST 요청이 전송됩니다.
푸시 메시지를 보내라는 신호이므로 백엔드에서
익스프레스를 사용할 수 있습니다
app.post('/api/trigger-push-msg/', function (req, res) {
이 요청이 수신되면 데이터베이스에서 구독을 가져와 각각에 대해 푸시 메시지를 트리거합니다.
return getSubscriptionsFromDatabase().then(function (subscriptions) {
let promiseChain = Promise.resolve();
for (let i = 0; i < subscriptions.length; i++) {
const subscription = subscriptions[i];
promiseChain = promiseChain.then(() => {
return triggerPushMsg(subscription, dataToSend);
});
}
return promiseChain;
});
그러면 triggerPushMsg()
함수는 web-push 라이브러리를 사용하여
제공합니다.
const triggerPushMsg = function (subscription, dataToSend) {
return webpush.sendNotification(subscription, dataToSend).catch((err) => {
if (err.statusCode === 404 || err.statusCode === 410) {
console.log('Subscription has expired or is no longer valid: ', err);
return deleteSubscriptionFromDatabase(subscription._id);
} else {
throw err;
}
});
};
webpush.sendNotification()
를 호출하면 프로미스가 반환됩니다. 만약
성공적으로 전송된 후에 프라미스가 해결되고
별다른 조치를 취하지 않아도 됩니다 프라미스가 거부되면
PushSubscription
가 여전히 사용 중인지 알려줍니다.
여부를 지정합니다.
푸시 서비스의 오류 유형을 확인하려면 상태 코드를 확인하는 것이 가장 좋습니다. 오류 푸시 서비스에 따라 메시지가 다르며 어떤 것이 다른 메시지보다 더 유용할 수 있습니다.
이 예시에서는 404
및 410
상태 코드인
'찾을 수 없음' 'Gone'이 포함됩니다 이 중 하나가 수신되면 구독이 만료된 것입니다.
더 이상 유효하지 않습니다. 이 시나리오에서는 데이터베이스에서 구독을 삭제해야 합니다.
다른 오류가 발생한 경우에는 throw err
만 사용하여 프라미스에서 반환하는 프로미스를 만듭니다.
triggerPushMsg()
이(가) 거부되었습니다.
다음 섹션에서 웹 푸시를 살펴볼 때 다른 상태 코드에 대해 다룰 것입니다. 자세히 살펴보겠습니다
구독을 순환한 후에는 JSON 응답을 반환해야 합니다.
.then(() => {
res.setHeader('Content-Type', 'application/json');
res.send(JSON.stringify({ data: { success: true } }));
})
.catch(function(err) {
res.status(500);
res.setHeader('Content-Type', 'application/json');
res.send(JSON.stringify({
error: {
id: 'unable-to-send-messages',
message: `We were unable to send messages to all subscriptions : ` +
`'${err.message}'`
}
}));
});
주요 구현 단계를 살펴보았습니다.
- API를 만들어 웹페이지에서 백엔드로 구독을 전송합니다. 데이터베이스에 저장할 수 있습니다
- 푸시 메시지 전송을 트리거하는 API를 만듭니다 (이 경우 API로 가장한 관리자 패널에서 호출됨).
- 백엔드에서 모든 구독 가져오기 web-push 구현 중 하나를 사용하여 각 구독에 메시지를 라이브러리를 참조하세요.
백엔드 (Node, PHP, Python 등)에 상관없이 푸시를 구현하는 단계는 변경할 수 있습니다.
다음으로, 이러한 웹 푸시 라이브러리는 정확히 어떤 역할을 할까요?
다음에 수행할 작업
- 웹 푸시 알림 개요
- 푸시 작동 방식
- 사용자 구독
- 권한 UX
- 웹 푸시 라이브러리를 사용하여 메시지 보내기
- 웹 푸시 프로토콜
- 푸시 이벤트 처리
- 알림 표시
- 알림 동작
- 일반 알림 패턴
- 푸시 알림 FAQ
- 일반적인 문제 및 버그 신고