chore: add delegated event message handler

This commit is contained in:
Ricardo Arturo Cabral Mejia 2022-10-14 03:11:46 +00:00
parent f0a10527c3
commit 13bd023a1b
No known key found for this signature in database
GPG Key ID: 5931EBF43A650245
3 changed files with 83 additions and 1 deletions

View File

@ -0,0 +1,21 @@
import { isDeleteEvent, isEphemeralEvent, isReplaceableEvent } from '../utils/event'
import { DefaultEventStrategy } from '../handlers/event-strategies/default-event-strategy'
import { EphemeralEventStrategy } from '../handlers/event-strategies/ephemeral-event-strategy'
import { Event } from '../@types/event'
import { Factory } from '../@types/base'
import { IEventRepository } from '../@types/repositories'
import { IEventStrategy } from '../@types/message-handlers'
import { IWebSocketAdapter } from '../@types/adapters'
export const delegatedEventStrategyFactory = (
eventRepository: IEventRepository,
): Factory<IEventStrategy<Event, Promise<void>>, [Event, IWebSocketAdapter]> =>
([event, adapter]: [Event, IWebSocketAdapter]) => {
if (isEphemeralEvent(event)) {
return new EphemeralEventStrategy(adapter)
} else if (isReplaceableEvent(event) || isDeleteEvent(event)) {
return
}
return new DefaultEventStrategy(adapter, eventRepository)
}

View File

@ -1,7 +1,10 @@
import { IncomingMessage, MessageType } from '../@types/messages'
import { DelegatedEventMessageHandler } from '../handlers/delegated-event-message-handler'
import { delegatedEventStrategyFactory } from './delegated-event-strategy-factory'
import { EventMessageHandler } from '../handlers/event-message-handler'
import { eventStrategyFactory } from './event-strategy-factory'
import { IEventRepository } from '../@types/repositories'
import { isDelegatedEvent } from '../utils/event'
import { IWebSocketAdapter } from '../@types/adapters'
import { Settings } from '../utils/settings'
import { SubscribeMessageHandler } from '../handlers/subscribe-message-handler'
@ -12,7 +15,13 @@ export const messageHandlerFactory = (
) => ([message, adapter]: [IncomingMessage, IWebSocketAdapter]) => {
switch (message[0]) {
case MessageType.EVENT:
return new EventMessageHandler(adapter, eventStrategyFactory(eventRepository), Settings)
{
if (isDelegatedEvent(message[1])) {
return new DelegatedEventMessageHandler(adapter, delegatedEventStrategyFactory(eventRepository), Settings)
}
return new EventMessageHandler(adapter, eventStrategyFactory(eventRepository), Settings)
}
case MessageType.REQ:
return new SubscribeMessageHandler(adapter, eventRepository)
case MessageType.CLOSE:

View File

@ -0,0 +1,52 @@
import { EventDelegatorMetadataKey, EventTags } from '../constants/base'
import { createNoticeMessage } from '../utils/messages'
import { Event } from '../@types/event'
import { EventMessageHandler } from './event-message-handler'
import { IMessageHandler } from '../@types/message-handlers'
import { IncomingEventMessage } from '../@types/messages'
import { isDelegatedEventValid } from '../utils/event'
import { WebSocketAdapterEvent } from '../constants/adapter'
export class DelegatedEventMessageHandler extends EventMessageHandler implements IMessageHandler {
public async handleMessage(message: IncomingEventMessage): Promise<void> {
const [, event] = message
let reason = this.canAcceptEvent(event)
if (reason) {
this.webSocket.emit(WebSocketAdapterEvent.Message, createNoticeMessage(`Event rejected: ${reason}`))
console.warn(`Event ${event.id} rejected. Reason: ${reason}`)
return
}
reason = await this.isEventValid(event)
if (reason) {
console.warn(`Event ${event.id} rejected. Reason: ${reason}`)
return
}
const [, delegator] = event.tags.find((tag) => tag.length === 4 && tag[0] === EventTags.Delegation)
event[EventDelegatorMetadataKey] = delegator
const strategy = this.strategyFactory([event, this.webSocket])
if (typeof strategy?.execute !== 'function') {
return
}
try {
await strategy.execute(event)
} catch (error) {
console.error('Error handling message:', message, error)
}
}
protected async isEventValid(event: Event): Promise<string | undefined> {
const reason = super.isEventValid(event)
if (reason) {
return reason
}
if (!await isDelegatedEventValid(event)) {
return `Event with id ${event.id} from ${event.pubkey} is invalid delegated event`
}
}
}