79 lines
3.0 KiB
Swift
79 lines
3.0 KiB
Swift
//
|
|
// MastodonController+Push.swift
|
|
// Tusker
|
|
//
|
|
// Created by Shadowfacts on 4/9/24.
|
|
// Copyright © 2024 Shadowfacts. All rights reserved.
|
|
//
|
|
|
|
import Foundation
|
|
import Pachyderm
|
|
import PushNotifications
|
|
import CryptoKit
|
|
|
|
extension MastodonController {
|
|
func createPushSubscription(subscription: PushNotifications.PushSubscription) async throws -> Pachyderm.PushSubscription {
|
|
let req = Pachyderm.PushSubscription.create(
|
|
endpoint: subscription.endpoint,
|
|
// mastodon docs just say "Base64 encoded string of a public key from a ECDH keypair using the prime256v1 curve."
|
|
// other apps use SecKeyCopyExternalRepresentation which is documented to use X9.63 for elliptic curve keys
|
|
// and that seems to work
|
|
publicKey: subscription.secretKey.publicKey.x963Representation,
|
|
authSecret: subscription.authSecret,
|
|
alerts: .init(subscription.alerts),
|
|
policy: .init(subscription.policy)
|
|
)
|
|
return try await run(req).0
|
|
}
|
|
|
|
func updatePushSubscription(subscription: PushNotifications.PushSubscription) async throws -> Pachyderm.PushSubscription {
|
|
// when updating anything other than the alerts/policy, we need to go through the create route
|
|
return try await createPushSubscription(subscription: subscription)
|
|
}
|
|
|
|
func updatePushSubscription(alerts: PushNotifications.PushSubscription.Alerts, policy: PushNotifications.PushSubscription.Policy) async throws -> Pachyderm.PushSubscription {
|
|
let req = Pachyderm.PushSubscription.update(alerts: .init(alerts), policy: .init(policy))
|
|
var result = try await run(req).0
|
|
if instanceFeatures.pushNotificationPolicyMissingFromResponse {
|
|
// see https://github.com/mastodon/mastodon/issues/23145
|
|
// so just assume if the request was successful that it worked
|
|
result.policy = .init(policy)
|
|
}
|
|
return result
|
|
}
|
|
|
|
func deletePushSubscription() async throws {
|
|
let req = Pachyderm.PushSubscription.delete()
|
|
_ = try await run(req)
|
|
}
|
|
}
|
|
|
|
private extension Pachyderm.PushSubscription.Alerts {
|
|
init(_ alerts: PushNotifications.PushSubscription.Alerts) {
|
|
self.init(
|
|
mention: alerts.contains(.mention),
|
|
status: alerts.contains(.status),
|
|
reblog: alerts.contains(.reblog),
|
|
follow: alerts.contains(.follow),
|
|
followRequest: alerts.contains(.followRequest),
|
|
favourite: alerts.contains(.favorite),
|
|
poll: alerts.contains(.poll),
|
|
update: alerts.contains(.update),
|
|
emojiReaction: alerts.contains(.emojiReaction)
|
|
)
|
|
}
|
|
}
|
|
|
|
private extension Pachyderm.PushSubscription.Policy {
|
|
init(_ policy: PushNotifications.PushSubscription.Policy) {
|
|
switch policy {
|
|
case .all:
|
|
self = .all
|
|
case .followers:
|
|
self = .followers
|
|
case .followed:
|
|
self = .followed
|
|
}
|
|
}
|
|
}
|