React + PWA Tutorial (notifications,push)
PWAλ
νλ‘κ·Έλ μλΈ μΉ μ±(Progressive Web Apps)μ μΉ μ±κ³Ό λ€μ΄ν°λΈ μ±μ μ₯μ μ λͺ¨λ μ 곡νλ, λ³΄λ€ λ°μ λ ννμ μΉ μ ν리μΌμ΄μ
μ μ΄λ»κ² κ°λ° ν μ μλκ°μ λν λ
Όμμ΄μ κ°λ° μ² νμ λ§νλ€.
Google I/O 2016μμ μ²μ μκ°λμκ³ μ€μ¬μ PWAλΌκ³ λΆλ₯Έλ€
Notifications
const randomNotification = () => {
const notifTitle = "Title";
const notifBody = "Body";
const notifImg = imgUrl;
const options = {
body: notifBody,
icon: notifImg,
};
new Notification(notifTitle, options);
setTimeout(randomNotification, 30000);
};
<Button
id="notifications"
onClick={() => {
console.log(Notification.permission);
if (!("Notification" in window)) {
alert("not support notification ");
} else if (Notification.permission === "granted") {
randomNotification();
} else if (Notification.permission !== "denied") {
Notification.requestPermission().then((permission) => {
if (permission === "granted") {
const notification = new Notification("good!!");
}
});
}
}}
>
noti
</Button>
Buttonμ μμ±νμ¬ ν΄λ¦μ μλ¦Όμ΄ λνλκ² νλ κΈ°λ₯μ λλ€.
νλ² μ€νλλ©΄ 30μ΄μ© λ°λ³΅νμ¬ μ€νλλλ‘ μμ±λμμ΅λλ€.
Push
index.js
function urlBase64ToUint8Array(base64String) {
var padding = "=".repeat((4 - (base64String.length % 4)) % 4);
var base64 = (base64String + padding).replace(/\-/g, "+").replace(/_/g, "/");
var rawData = window.atob(base64);
var outputArray = new Uint8Array(rawData.length);
for (var i = 0; i < rawData.length; ++i) {
outputArray[i] = rawData.charCodeAt(i);
}
return outputArray;
}
navigator.serviceWorker.register("/service-worker.js");
navigator.serviceWorker.ready
.then(function (registration) {
return registration.pushManager.getSubscription().then(async function (subscription) {
console.log(subscription, "subscription");
if (subscription) {
return subscription;
}
const response = await axios.post("/api/vapidPublicKey");
const vapidPublicKey = response.data.data;
const convertedVapidKey = urlBase64ToUint8Array(vapidPublicKey);
return registration.pushManager.subscribe({
userVisibleOnly: true,
applicationServerKey: convertedVapidKey,
});
});
})
.then(function (subscription) {
fetch("/api/register", {
method: "post",
headers: {
"Content-type": "application/json",
},
body: JSON.stringify({
subscription: subscription,
}),
});
fetch("/api/sendNotification", {
method: "post",
headers: {
"Content-type": "application/json",
},
body: JSON.stringify({
subscription: subscription,
delay: 1,
}),
});
});
server.js
const webPush = require("web-push");
webPush.setVapidDetails("https://example.com/", process.env.VAPID_PUBLIC_KEY, process.env.VAPID_PRIVATE_KEY);
router.post(
"/api/vapidPublicKey",
asyncHandler(async (req, res, next) => {
res.send({data: process.env.VAPID_PUBLIC_KEY})
})
);
router.post(
"/api/register",
asyncHandler(async (req, res, next) => {
res.send('')
})
);
router.post(
"/api/sendNotification",
asyncHandler(async (req, res, next) => {
const payload = JSON.stringify({ title: "Push Test" });
setTimeout(() => {
webPush.sendNotification(subscription, payload).catch((err) => {
console.log(err);
});
}, req.body.delay * 1000);
})
);
μ°Έκ³
How to make PWAs re-engageable using Notifications and Push - Progressive web apps (PWAs) | MDN
Having the ability to cache the contents of an app to work offline is a great feature. Allowing the user to install the web app on their home screen is even better. But instead of relying only on user actions, we can do more, using push messages and notifi
developer.mozilla.org