# Request must contain valid subscription JSON
abort(400)
- row = db.query(
- """
- INSERT INTO users_push_subscriptions (userid, subscription, settings)
- VALUES (?, ?, ?)
- RETURNING subid
- """,
- [g.userid, json.dumps(request.json), 0], expect_one=True)
+ subid = request.args.get("subid", None)
+ existing_sub = None
+ if subid:
+ existing_sub = db.query(
+ "SELECT * FROM users_push_subscriptions WHERE subid = ? AND userid = ?",
+ [subid, g.userid])
+
+ if existing_sub:
+ row = db.query(
+ """
+ UPDATE users_push_subscriptions
+ SET userid = ?, subscription = ?
+ WHERE subid = ? AND userid = ?
+ RETURNING subid
+ """,
+ [g.userid, json.dumps(request.json), subid, g.userid], expect_one=True)
+ else:
+ row = db.query(
+ """
+ INSERT INTO users_push_subscriptions (userid, subscription, settings)
+ VALUES (?, ?, ?)
+ RETURNING subid
+ """,
+ [g.userid, json.dumps(request.json), 0], expect_one=True)
db.commit()
current_app.logger.info(f"{g.username} registered push subscription")
return {"status": "success", "subid": row["subid"]}
+@bp.get("/vapid-public-key")
+def vapid_public_key():
+ try:
+ with open(datadir.get_vapid_public_key_path(), "r") as keyfile:
+ key = keyfile.read().strip()
+ return {"status": "ok", "public_key": key}
+ except OSError:
+ return {"status": "error"}
+
@bp.get("/settings")
@auth.requires_login
def get_settings():
});
}
+async function periodicPushSync() {
+ console.log("sync");
+ if (!("serviceWorker" in navigator)) {
+ return; // No service woker available
+ }
+ const subid = window.localStorage.getItem("subid");
+ console.log(subid);
+ if (subid) {
+ await syncPushSubscription();
+ }
+}
+
+async function syncPushSubscription() {
+ const registration = await navigator.serviceWorker.getRegistration();
+ let subscription = await registration.pushManager.getSubscription();
+ if (!subscription)
+ {
+ // Subscribe via browser's push service
+ const data = await fetch("/push-notifications/vapid-public-key").then((r) => { return r.json() });
+ const vapid_public_key = data.public_key;
+ const options = {userVisibleOnly: true, applicationServerKey: vapid_public_key};
+ subscription = await registration.pushManager.subscribe(options);
+ console.log(JSON.stringify(subscription));
+ }
+
+ // Register (or update) subscription with LSP server
+ const subid = window.localStorage.getItem("subid");
+ const params = subid ? `?subid=${subid}` : "";
+ const response = await fetch(
+ `/push-notifications/subscribe${params}`, {
+ method: "post",
+ headers: {"Content-Type": "application/json"},
+ body: JSON.stringify(subscription)
+ }
+ );
+
+ const rspJson = await response.json();
+ console.log("Subscription ID:", rspJson.subid);
+ window.localStorage.setItem("subid", rspJson.subid);
+}
+
+periodicPushSync();
+setInterval(periodicPushSync, 10000);
+
if (permission === "granted") {
// Subscribe to push notifications (if we don't already have an active subscription)
try {
- const registration = await navigator.serviceWorker.getRegistration();
- const existingSubscription = await registration.pushManager.getSubscription();
- if (!existingSubscription || !window.localStorage.getItem("subid"))
- {
- // Subscribe via browser's push service
- const vapid_public_key = "{{ vapid_public_key }}";
- const options = {userVisibleOnly: true, applicationServerKey: vapid_public_key};
- const subscription = await registration.pushManager.subscribe(options);
- console.log(JSON.stringify(subscription));
-
- // Register subscription with LSP server
- const response = await fetch(
- "/push-notifications/subscribe", {
- method: "post",
- headers: {"Content-Type": "application/json"},
- body: JSON.stringify(subscription)
- }
- );
-
- const rspJson = await response.json();
- console.log("Subscription ID:", rspJson.subid);
- window.localStorage.setItem("subid", rspJson.subid);
- }
+ await syncPushSubscription();
}
catch (err) {
console.log("Error subscribing to push notifications:", err);