42 lines
1.8 KiB
TypeScript
42 lines
1.8 KiB
TypeScript
import { z } from 'zod'
|
|
|
|
export const DirectionSchema = z.enum(['up', 'down', 'left', 'right'])
|
|
export const PlayerCommandSchema = z.discriminatedUnion('type', [
|
|
z.object({ type: z.literal('move'), direction: DirectionSchema }),
|
|
z.object({ type: z.literal('attack'), targetId: z.string().min(1).max(128) }),
|
|
z.object({ type: z.literal('heal-self') }),
|
|
z.object({ type: z.literal('pass') })
|
|
])
|
|
export const CommandEnvelopeSchema = z.object({
|
|
requestId: z.string().min(1).max(128),
|
|
runId: z.string().min(1),
|
|
floorId: z.string().min(1),
|
|
phaseId: z.string().min(1),
|
|
command: PlayerCommandSchema
|
|
})
|
|
export const SpawnMessageSchema = z.object({
|
|
type: z.literal('spawn-requested'), externalEventId: z.string().min(1),
|
|
twitchUserId: z.string().min(1), displayName: z.string().min(1).max(40),
|
|
broadcasterId: z.string().min(1), followerVerified: z.boolean()
|
|
})
|
|
export const ChannelPointRedemptionSchema = z.object({
|
|
type: z.literal('channel-point-resurrection-redeemed'), externalEventId: z.string().min(1),
|
|
twitchUserId: z.string().min(1), rewardId: z.string().min(1)
|
|
})
|
|
|
|
export type PlayerCommand = z.infer<typeof PlayerCommandSchema>
|
|
export type CommandEnvelope = z.infer<typeof CommandEnvelopeSchema>
|
|
export type SpawnMessage = z.infer<typeof SpawnMessageSchema>
|
|
export type ChannelPointRedemption = z.infer<typeof ChannelPointRedemptionSchema>
|
|
export type RejectionReason = 'UNAUTHENTICATED' | 'IDENTITY_NOT_BOUND' | 'CHARACTER_NOT_FOUND' |
|
|
'CHARACTER_DEAD' | 'WRONG_PHASE' | 'STALE_RUN' | 'STALE_FLOOR' | 'STALE_PHASE' |
|
|
'DEADLINE_PASSED' | 'NO_AP' | 'INVALID_TARGET' | 'BLOCKED_TILE' | 'HEAL_USED' | 'DUPLICATE'
|
|
|
|
export interface CommandResult {
|
|
requestId: string
|
|
accepted: boolean
|
|
eventSequence: number
|
|
reason: RejectionReason | null
|
|
message: string
|
|
}
|