1
0
forked from noxious/server

Added online column to user and char. models, updated send chat message event to new format, removed unused code, fixed typo, replaced console.log()'s with logger

This commit is contained in:
Dennis Postma 2024-09-08 03:14:55 +02:00
parent 7682d1fd01
commit a64506d3ee
5 changed files with 56 additions and 43 deletions

View File

@ -41,6 +41,7 @@ CREATE TABLE `User` (
`id` INTEGER NOT NULL AUTO_INCREMENT,
`username` VARCHAR(191) NOT NULL,
`password` VARCHAR(191) NOT NULL,
`online` BOOLEAN NOT NULL DEFAULT false,
UNIQUE INDEX `User_username_key`(`username`),
PRIMARY KEY (`id`)
@ -64,6 +65,7 @@ CREATE TABLE `Character` (
`id` INTEGER NOT NULL AUTO_INCREMENT,
`userId` INTEGER NOT NULL,
`name` VARCHAR(191) NOT NULL,
`online` BOOLEAN NOT NULL DEFAULT false,
`hitpoints` INTEGER NOT NULL DEFAULT 100,
`mana` INTEGER NOT NULL DEFAULT 100,
`level` INTEGER NOT NULL DEFAULT 1,

View File

@ -2,6 +2,7 @@ model User {
id Int @id @default(autoincrement())
username String @unique
password String
online Boolean @default(false)
characters Character[]
}
@ -19,15 +20,15 @@ enum CharacterRace {
}
model CharacterType {
id Int @id @default(autoincrement())
name String
gender CharacterGender
race CharacterRace
characters Character[]
spriteId String
sprite Sprite @relation(fields: [spriteId], references: [id], onDelete: Cascade)
createdAt DateTime @default(now())
updatedAt DateTime @updatedAt
id Int @id @default(autoincrement())
name String
gender CharacterGender
race CharacterRace
characters Character[]
spriteId String
sprite Sprite @relation(fields: [spriteId], references: [id], onDelete: Cascade)
createdAt DateTime @default(now())
updatedAt DateTime @updatedAt
}
model Character {
@ -35,19 +36,20 @@ model Character {
userId Int
user User @relation(fields: [userId], references: [id], onDelete: Cascade)
name String @unique
online Boolean @default(false)
hitpoints Int @default(100)
mana Int @default(100)
level Int @default(1)
experience Int @default(0)
alignment Int @default(50)
role String @default("player")
positionX Int @default(0)
positionY Int @default(0)
positionX Int @default(0)
positionY Int @default(0)
rotation Int @default(0)
zoneId Int @default(1)
zone Zone @relation(fields: [zoneId], references: [id], onDelete: Cascade)
characterTypeId Int?
characterType CharacterType? @relation(fields: [characterTypeId], references: [id], onDelete: Cascade)
characterType CharacterType? @relation(fields: [characterTypeId], references: [id], onDelete: Cascade)
chats Chat[]
items CharacterItem[]
}

View File

@ -3,31 +3,52 @@ import { TSocket } from '../../utilities/types'
import CharacterRepository from '../../repositories/characterRepository'
import ZoneRepository from '../../repositories/zoneRepository'
import { isCommand } from '../../utilities/chat'
import logger from '../../utilities/logger'
type TypePayload = {
message: string
}
export default function (socket: TSocket, io: Server) {
socket.on('chat:send_message', async (data: TypePayload, callback: (response: boolean) => void) => {
try {
if (!data.message) return
if (isCommand(data.message)) return
export default class ChatMessageEvent {
constructor(
private readonly io: Server,
private readonly socket: TSocket
) {}
const character = await CharacterRepository.getByUserAndId(socket.user?.id as number, socket.character?.id as number)
if (!character) return
public listen(): void {
this.socket.on('chat:send_message', this.handleChatMessage.bind(this))
}
private async handleChatMessage(data: TypePayload, callback: (response: boolean) => void): Promise<void> {
try {
if (!data.message || isCommand(data.message)) {
callback(false)
return
}
const character = await CharacterRepository.getByUserAndId(this.socket.user?.id as number, this.socket.character?.id as number)
if (!character) {
logger.error('chat:send_message error', 'Character not found')
callback(false)
return
}
const zone = await ZoneRepository.getById(character.zoneId)
if (!zone) return
if (!zone) {
logger.error('chat:send_message error', 'Zone not found')
callback(false)
return
}
callback(true)
io.to(zone.id.toString()).emit('chat:message', {
this.io.to(zone.id.toString()).emit('chat:message', {
character: character,
message: data.message
})
} catch (error: any) {
console.log(`---Error sending message: ${error.message}`)
logger.error('chat:send_message error', error.message)
callback(false)
}
})
}
}
}

View File

@ -3,6 +3,7 @@ import { TSocket } from '../utilities/types'
import config from '../utilities/config'
import UserRepository from '../repositories/userRepository'
import { User } from '@prisma/client'
import logger from '../utilities/logger'
/**
* Socket io jwt auth middleware
@ -11,7 +12,7 @@ import { User } from '@prisma/client'
*/
export async function Authentication(socket: TSocket, next: any) {
if (!socket.request.headers.cookie) {
console.log('No cookie provided')
logger.warn('No cookie provided')
return next(new Error('Authentication error'))
}
@ -32,7 +33,7 @@ export async function Authentication(socket: TSocket, next: any) {
if (token) {
verify(token, config.JWT_SECRET, async (err: any, decoded: any) => {
if (err) {
console.log('err')
logger.error('Invalid token')
return next(new Error('Authentication error'))
}
@ -40,7 +41,7 @@ export async function Authentication(socket: TSocket, next: any) {
next()
})
} else {
console.log('No token provided')
logger.warn('No token provided')
next(new Error('Authentication error'))
}
}

View File

@ -3,10 +3,9 @@ import { AStar } from '../../utilities/character/aStar'
import ZoneManager from '../../managers/zoneManager'
import prisma from '../../utilities/prisma'
import Rotation from '../../utilities/character/rotation'
import logger from '../../utilities/logger'
export class CharacterMoveService {
private moveTokens: Map<number, symbol> = new Map()
public async updatePosition(character: ExtendedCharacter, position: { x: number; y: number }, newZoneId?: number): Promise<void> {
Object.assign(character, {
positionX: position.x,
@ -29,7 +28,7 @@ export class CharacterMoveService {
public async calculatePath(character: ExtendedCharacter, targetX: number, targetY: number): Promise<Array<{ x: number; y: number }> | null> {
const grid = await ZoneManager.getGrid(character.zoneId)
if (!grid?.length) {
console.error('character:move error', 'Grid not found or empty')
logger.error('character:move error', 'Grid not found or empty')
return null
}
@ -39,19 +38,7 @@ export class CharacterMoveService {
return AStar.findPath(start, end, grid)
}
public startMovement(characterId: number): void {
this.moveTokens.set(characterId, Symbol('moveToken'))
}
public stopMovement(characterId: number): void {
this.moveTokens.delete(characterId)
}
public isMoving(characterId: number): boolean {
return this.moveTokens.has(characterId)
}
public async applyMovementDelay(): Promise<void> {
await new Promise((resolve) => setTimeout(resolve, 210)) // 50ms delay between steps
await new Promise((resolve) => setTimeout(resolve, 250)) // 250ms delay between steps
}
}