import assert from 'node:assert' import { Un$Typed } from '@atproto/lex' import { Server, UpstreamFailureError } from '@atproto/xrpc-server' import { AppContext } from '../../../../context.js' import { app } from '../../../../lexicons/index.js' import { GetNotificationPreferencesResponse } from '../../../../proto/bsky_pb.js' import { Namespaces } from '../../../../stash.js' import { protobufToLex } from './util.js' export default function (server: Server, ctx: AppContext) { server.add(app.bsky.notification.putPreferencesV2, { auth: ctx.authVerifier.standard, handler: async ({ auth, input }) => { const actorDid = auth.credentials.iss const preferences = await computePreferences(ctx, actorDid, input) // Notification preferences are created automatically on the dataplane on signup, so we just update. await ctx.stashClient.update({ actorDid, namespace: Namespaces.AppBskyNotificationDefsPreferences, key: 'self', payload: preferences, }) return { encoding: 'application/json', body: { preferences, }, } }, }) } const computePreferences = async ( ctx: AppContext, actorDid: string, input: app.bsky.notification.putPreferencesV2.$Input, ): Promise> => { let res: GetNotificationPreferencesResponse try { res = await ctx.dataplane.getNotificationPreferences({ dids: [actorDid], }) } catch (err) { throw new UpstreamFailureError( 'cannot get current notification preferences', 'NotificationPreferencesFailed', { cause: err }, ) } assert( res.preferences.length === 1, `expected exactly one preferences entry, got ${res.preferences.length}`, ) const currentPreferences = protobufToLex(res.preferences[0]) const preferences = { ...currentPreferences, ...input.body } return preferences }