forked from noxious/server
Storage class is now OOP
This commit is contained in:
parent
04e081c31a
commit
5982422e04
@ -3,7 +3,7 @@ import * as path from 'path'
|
|||||||
import { pathToFileURL } from 'url'
|
import { pathToFileURL } from 'url'
|
||||||
|
|
||||||
import Logger, { LoggerType } from '#application/logger'
|
import Logger, { LoggerType } from '#application/logger'
|
||||||
import { getAppPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { Command } from '#application/types'
|
import { Command } from '#application/types'
|
||||||
|
|
||||||
export class CommandRegistry {
|
export class CommandRegistry {
|
||||||
@ -15,7 +15,7 @@ export class CommandRegistry {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public async loadCommands(): Promise<void> {
|
public async loadCommands(): Promise<void> {
|
||||||
const directory = getAppPath('commands')
|
const directory = Storage.getAppPath('commands')
|
||||||
this.logger.info(`Loading commands from: ${directory}`)
|
this.logger.info(`Loading commands from: ${directory}`)
|
||||||
|
|
||||||
try {
|
try {
|
||||||
@ -32,7 +32,7 @@ export class CommandRegistry {
|
|||||||
|
|
||||||
private async loadCommandFile(file: fs.Dirent): Promise<void> {
|
private async loadCommandFile(file: fs.Dirent): Promise<void> {
|
||||||
try {
|
try {
|
||||||
const filePath = getAppPath('commands', file.name)
|
const filePath = Storage.getAppPath('commands', file.name)
|
||||||
const commandName = path.basename(file.name, path.extname(file.name))
|
const commandName = path.basename(file.name, path.extname(file.name))
|
||||||
|
|
||||||
const module = await import(pathToFileURL(filePath).href)
|
const module = await import(pathToFileURL(filePath).href)
|
||||||
|
@ -1,34 +1,71 @@
|
|||||||
import fs from 'fs'
|
import fs from 'fs'
|
||||||
import path from 'path'
|
import path from 'path'
|
||||||
|
|
||||||
import config from './config'
|
import config from '#application/config'
|
||||||
|
|
||||||
export function getRootPath(folder: string, ...additionalSegments: string[]) {
|
class Storage {
|
||||||
return path.join(process.cwd(), folder, ...additionalSegments)
|
private readonly baseDir: string
|
||||||
}
|
private readonly rootDir: string
|
||||||
|
|
||||||
export function getAppPath(folder: string, ...additionalSegments: string[]) {
|
constructor() {
|
||||||
const baseDir = config.ENV === 'development' ? 'src' : 'dist'
|
this.rootDir = process.cwd()
|
||||||
return path.join(process.cwd(), baseDir, folder, ...additionalSegments)
|
this.baseDir = config.ENV === 'development' ? 'src' : 'dist'
|
||||||
}
|
}
|
||||||
|
|
||||||
export function getPublicPath(folder: string, ...additionalSegments: string[]) {
|
/**
|
||||||
return path.join(process.cwd(), 'public', folder, ...additionalSegments)
|
* Gets path relative to project root
|
||||||
}
|
*/
|
||||||
|
public getRootPath(folder: string, ...additionalSegments: string[]): string {
|
||||||
|
return path.join(this.rootDir, folder, ...additionalSegments)
|
||||||
|
}
|
||||||
|
|
||||||
export function doesPathExist(path: string) {
|
/**
|
||||||
try {
|
* Gets path relative to app directory (src/dist)
|
||||||
fs.accessSync(path, fs.constants.F_OK)
|
*/
|
||||||
return true
|
public getAppPath(folder: string, ...additionalSegments: string[]): string {
|
||||||
} catch (e) {
|
return path.join(this.rootDir, this.baseDir, folder, ...additionalSegments)
|
||||||
return false
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets path relative to public directory
|
||||||
|
*/
|
||||||
|
public getPublicPath(folder: string, ...additionalSegments: string[]): string {
|
||||||
|
return path.join(this.rootDir, 'public', folder, ...additionalSegments)
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if a path exists
|
||||||
|
* @throws Error if path is empty or invalid
|
||||||
|
*/
|
||||||
|
public doesPathExist(pathToCheck: string): boolean {
|
||||||
|
if (!pathToCheck) {
|
||||||
|
throw new Error('Path cannot be empty')
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
fs.accessSync(pathToCheck, fs.constants.F_OK)
|
||||||
|
return true
|
||||||
|
} catch (e) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a directory and any necessary parent directories
|
||||||
|
* @throws Error if directory creation fails
|
||||||
|
*/
|
||||||
|
public createDir(dirPath: string): void {
|
||||||
|
if (!dirPath) {
|
||||||
|
throw new Error('Directory path cannot be empty')
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
fs.mkdirSync(dirPath, { recursive: true })
|
||||||
|
} catch (error) {
|
||||||
|
const typedError = error as Error
|
||||||
|
throw new Error(`Failed to create directory: ${typedError.message}`)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export function createDir(path: string) {
|
export default new Storage()
|
||||||
try {
|
|
||||||
fs.mkdirSync(path, { recursive: true })
|
|
||||||
} catch (e) {
|
|
||||||
console.error(e)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
@ -1,11 +1,10 @@
|
|||||||
import fs from 'fs'
|
import fs from 'fs'
|
||||||
|
|
||||||
import sharp from 'sharp'
|
import sharp from 'sharp'
|
||||||
import { Server } from 'socket.io'
|
|
||||||
|
|
||||||
import { BaseCommand } from '#application/base/baseCommand'
|
import { BaseCommand } from '#application/base/baseCommand'
|
||||||
import { CharacterGender, CharacterRace } from '#application/enums'
|
import { CharacterGender, CharacterRace } from '#application/enums'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { UUID } from '#application/types'
|
import { UUID } from '#application/types'
|
||||||
import { Character } from '#entities/character'
|
import { Character } from '#entities/character'
|
||||||
import { CharacterHair } from '#entities/characterHair'
|
import { CharacterHair } from '#entities/characterHair'
|
||||||
@ -44,7 +43,7 @@ export default class InitCommand extends BaseCommand {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async importTiles(): Promise<void> {
|
private async importTiles(): Promise<void> {
|
||||||
for (const tile of fs.readdirSync(getPublicPath('tiles'))) {
|
for (const tile of fs.readdirSync(Storage.getPublicPath('tiles'))) {
|
||||||
const newTile = new Tile()
|
const newTile = new Tile()
|
||||||
newTile.setId(tile.split('.')[0] as UUID).setName('New tile')
|
newTile.setId(tile.split('.')[0] as UUID).setName('New tile')
|
||||||
|
|
||||||
@ -53,18 +52,18 @@ export default class InitCommand extends BaseCommand {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async importObjects(): Promise<void> {
|
private async importObjects(): Promise<void> {
|
||||||
for (const object of fs.readdirSync(getPublicPath('objects'))) {
|
for (const object of fs.readdirSync(Storage.getPublicPath('objects'))) {
|
||||||
const newMapObject = new MapObject()
|
const newMapObject = new MapObject()
|
||||||
newMapObject
|
newMapObject
|
||||||
.setId(object.split('.')[0] as UUID)
|
.setId(object.split('.')[0] as UUID)
|
||||||
.setName('New object')
|
.setName('New object')
|
||||||
.setFrameWidth(
|
.setFrameWidth(
|
||||||
(await sharp(getPublicPath('objects', object))
|
(await sharp(Storage.getPublicPath('objects', object))
|
||||||
.metadata()
|
.metadata()
|
||||||
.then((metadata) => metadata.height)) ?? 0
|
.then((metadata) => metadata.height)) ?? 0
|
||||||
)
|
)
|
||||||
.setFrameHeight(
|
.setFrameHeight(
|
||||||
(await sharp(getPublicPath('objects', object))
|
(await sharp(Storage.getPublicPath('objects', object))
|
||||||
.metadata()
|
.metadata()
|
||||||
.then((metadata) => metadata.width)) ?? 0
|
.then((metadata) => metadata.width)) ?? 0
|
||||||
)
|
)
|
||||||
|
@ -3,12 +3,12 @@ import fs from 'fs'
|
|||||||
import sharp from 'sharp'
|
import sharp from 'sharp'
|
||||||
|
|
||||||
import { BaseCommand } from '#application/base/baseCommand'
|
import { BaseCommand } from '#application/base/baseCommand'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
|
|
||||||
export default class TilesCommand extends BaseCommand {
|
export default class TilesCommand extends BaseCommand {
|
||||||
public async execute(): Promise<void> {
|
public async execute(): Promise<void> {
|
||||||
// Get all tiles
|
// Get all tiles
|
||||||
const tilesDir = getPublicPath('tiles')
|
const tilesDir = Storage.getPublicPath('tiles')
|
||||||
const tiles = fs.readdirSync(tilesDir).filter((file) => file.endsWith('.png'))
|
const tiles = fs.readdirSync(tilesDir).filter((file) => file.endsWith('.png'))
|
||||||
|
|
||||||
// Create output directory if it doesn't exist
|
// Create output directory if it doesn't exist
|
||||||
@ -18,14 +18,14 @@ export default class TilesCommand extends BaseCommand {
|
|||||||
|
|
||||||
for (const tile of tiles) {
|
for (const tile of tiles) {
|
||||||
// Check if tile is already 66x34
|
// Check if tile is already 66x34
|
||||||
const metadata = await sharp(getPublicPath('tiles', tile)).metadata()
|
const metadata = await sharp(Storage.getPublicPath('tiles', tile)).metadata()
|
||||||
if (metadata.width === 66 && metadata.height === 34) {
|
if (metadata.width === 66 && metadata.height === 34) {
|
||||||
this.logger.info(`Tile ${tile} already processed`)
|
this.logger.info(`Tile ${tile} already processed`)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
const inputPath = getPublicPath('tiles', tile)
|
const inputPath = Storage.getPublicPath('tiles', tile)
|
||||||
const tempPath = getPublicPath('tiles', `temp_${tile}`)
|
const tempPath = Storage.getPublicPath('tiles', `temp_${tile}`)
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await sharp(inputPath)
|
await sharp(inputPath)
|
||||||
|
@ -4,7 +4,7 @@ import { Server } from 'socket.io'
|
|||||||
|
|
||||||
import { gameLogger, gameMasterLogger } from '#application/logger'
|
import { gameLogger, gameMasterLogger } from '#application/logger'
|
||||||
import prisma from '#application/prisma'
|
import prisma from '#application/prisma'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import characterRepository from '#repositories/characterRepository'
|
import characterRepository from '#repositories/characterRepository'
|
||||||
|
|
||||||
@ -38,10 +38,10 @@ export default class ObjectRemoveEvent {
|
|||||||
})
|
})
|
||||||
|
|
||||||
// get root path
|
// get root path
|
||||||
const public_folder = getPublicPath('objects')
|
const public_folder = Storage.getPublicPath('objects')
|
||||||
|
|
||||||
// remove the tile from the disk
|
// remove the tile from the disk
|
||||||
const finalFilePath = getPublicPath('objects', data.object + '.png')
|
const finalFilePath = Storage.getPublicPath('objects', data.object + '.png')
|
||||||
fs.unlink(finalFilePath, (err) => {
|
fs.unlink(finalFilePath, (err) => {
|
||||||
if (err) {
|
if (err) {
|
||||||
gameMasterLogger.error(`Error deleting object ${data.object}: ${err.message}`)
|
gameMasterLogger.error(`Error deleting object ${data.object}: ${err.message}`)
|
||||||
|
@ -6,7 +6,7 @@ import { Server } from 'socket.io'
|
|||||||
|
|
||||||
import { gameMasterLogger } from '#application/logger'
|
import { gameMasterLogger } from '#application/logger'
|
||||||
import prisma from '#application/prisma'
|
import prisma from '#application/prisma'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import characterRepository from '#repositories/characterRepository'
|
import characterRepository from '#repositories/characterRepository'
|
||||||
|
|
||||||
@ -32,7 +32,7 @@ export default class ObjectUploadEvent {
|
|||||||
if (character.role !== 'gm') {
|
if (character.role !== 'gm') {
|
||||||
return callback(false)
|
return callback(false)
|
||||||
}
|
}
|
||||||
const public_folder = getPublicPath('objects')
|
const public_folder = Storage.getPublicPath('objects')
|
||||||
|
|
||||||
// Ensure the folder exists
|
// Ensure the folder exists
|
||||||
await fs.mkdir(public_folder, { recursive: true })
|
await fs.mkdir(public_folder, { recursive: true })
|
||||||
@ -56,7 +56,7 @@ export default class ObjectUploadEvent {
|
|||||||
|
|
||||||
const uuid = object.id
|
const uuid = object.id
|
||||||
const filename = `${uuid}.png`
|
const filename = `${uuid}.png`
|
||||||
const finalFilePath = getPublicPath('objects', filename)
|
const finalFilePath = Storage.getPublicPath('objects', filename)
|
||||||
await writeFile(finalFilePath, objectData)
|
await writeFile(finalFilePath, objectData)
|
||||||
|
|
||||||
gameMasterLogger.info('gm:object:upload', `Object ${key} uploaded with id ${uuid}`)
|
gameMasterLogger.info('gm:object:upload', `Object ${key} uploaded with id ${uuid}`)
|
||||||
|
@ -3,7 +3,7 @@ import fs from 'fs/promises'
|
|||||||
import { Server } from 'socket.io'
|
import { Server } from 'socket.io'
|
||||||
|
|
||||||
import prisma from '#application/prisma'
|
import prisma from '#application/prisma'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import characterRepository from '#repositories/characterRepository'
|
import characterRepository from '#repositories/characterRepository'
|
||||||
|
|
||||||
@ -26,7 +26,7 @@ export default class SpriteCreateEvent {
|
|||||||
return callback(false)
|
return callback(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
const public_folder = getPublicPath('sprites')
|
const public_folder = Storage.getPublicPath('sprites')
|
||||||
|
|
||||||
// Ensure the folder exists
|
// Ensure the folder exists
|
||||||
await fs.mkdir(public_folder, { recursive: true })
|
await fs.mkdir(public_folder, { recursive: true })
|
||||||
@ -39,7 +39,7 @@ export default class SpriteCreateEvent {
|
|||||||
const uuid = sprite.id
|
const uuid = sprite.id
|
||||||
|
|
||||||
// Create folder with uuid
|
// Create folder with uuid
|
||||||
const sprite_folder = getPublicPath('sprites', uuid)
|
const sprite_folder = Storage.getPublicPath('sprites', uuid)
|
||||||
await fs.mkdir(sprite_folder, { recursive: true })
|
await fs.mkdir(sprite_folder, { recursive: true })
|
||||||
|
|
||||||
callback(true)
|
callback(true)
|
||||||
|
@ -4,7 +4,7 @@ import { Server } from 'socket.io'
|
|||||||
|
|
||||||
import { gameMasterLogger } from '#application/logger'
|
import { gameMasterLogger } from '#application/logger'
|
||||||
import prisma from '#application/prisma'
|
import prisma from '#application/prisma'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import CharacterRepository from '#repositories/characterRepository'
|
import CharacterRepository from '#repositories/characterRepository'
|
||||||
|
|
||||||
@ -19,7 +19,7 @@ export default class GMSpriteDeleteEvent {
|
|||||||
private readonly io: Server,
|
private readonly io: Server,
|
||||||
private readonly socket: TSocket
|
private readonly socket: TSocket
|
||||||
) {
|
) {
|
||||||
this.public_folder = getPublicPath('sprites')
|
this.public_folder = Storage.getPublicPath('sprites')
|
||||||
}
|
}
|
||||||
|
|
||||||
public listen(): void {
|
public listen(): void {
|
||||||
@ -45,7 +45,7 @@ export default class GMSpriteDeleteEvent {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async deleteSpriteFolder(spriteId: string): Promise<void> {
|
private async deleteSpriteFolder(spriteId: string): Promise<void> {
|
||||||
const finalFilePath = getPublicPath('sprites', spriteId)
|
const finalFilePath = Storage.getPublicPath('sprites', spriteId)
|
||||||
|
|
||||||
if (fs.existsSync(finalFilePath)) {
|
if (fs.existsSync(finalFilePath)) {
|
||||||
await fs.promises.rmdir(finalFilePath, { recursive: true })
|
await fs.promises.rmdir(finalFilePath, { recursive: true })
|
||||||
|
@ -7,7 +7,7 @@ import type { Prisma, SpriteAction } from '@prisma/client'
|
|||||||
|
|
||||||
import { gameMasterLogger } from '#application/logger'
|
import { gameMasterLogger } from '#application/logger'
|
||||||
import prisma from '#application/prisma'
|
import prisma from '#application/prisma'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import CharacterRepository from '#repositories/characterRepository'
|
import CharacterRepository from '#repositories/characterRepository'
|
||||||
|
|
||||||
@ -314,13 +314,13 @@ export default class SpriteUpdateEvent {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async saveSpritesToDisk(id: string, actions: ProcessedSpriteAction[]): Promise<void> {
|
private async saveSpritesToDisk(id: string, actions: ProcessedSpriteAction[]): Promise<void> {
|
||||||
const publicFolder = getPublicPath('sprites', id)
|
const publicFolder = Storage.getPublicPath('sprites', id)
|
||||||
await mkdir(publicFolder, { recursive: true })
|
await mkdir(publicFolder, { recursive: true })
|
||||||
|
|
||||||
await Promise.all(
|
await Promise.all(
|
||||||
actions.map(async (action) => {
|
actions.map(async (action) => {
|
||||||
const spritesheet = await this.createSpritesheet(action.buffersWithDimensions)
|
const spritesheet = await this.createSpritesheet(action.buffersWithDimensions)
|
||||||
await writeFile(getPublicPath('sprites', id, `${action.action}.png`), spritesheet)
|
await writeFile(Storage.getPublicPath('sprites', id, `${action.action}.png`), spritesheet)
|
||||||
})
|
})
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
@ -4,7 +4,7 @@ import { Server } from 'socket.io'
|
|||||||
|
|
||||||
import { gameMasterLogger } from '#application/logger'
|
import { gameMasterLogger } from '#application/logger'
|
||||||
import prisma from '#application/prisma'
|
import prisma from '#application/prisma'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import characterRepository from '#repositories/characterRepository'
|
import characterRepository from '#repositories/characterRepository'
|
||||||
|
|
||||||
@ -19,7 +19,7 @@ export default class GMTileDeleteEvent {
|
|||||||
private readonly io: Server,
|
private readonly io: Server,
|
||||||
private readonly socket: TSocket
|
private readonly socket: TSocket
|
||||||
) {
|
) {
|
||||||
this.public_folder = getPublicPath('tiles')
|
this.public_folder = Storage.getPublicPath('tiles')
|
||||||
}
|
}
|
||||||
|
|
||||||
public listen(): void {
|
public listen(): void {
|
||||||
@ -56,7 +56,7 @@ export default class GMTileDeleteEvent {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async deleteTileFile(tileId: string): Promise<void> {
|
private async deleteTileFile(tileId: string): Promise<void> {
|
||||||
const finalFilePath = getPublicPath('tiles', `${tileId}.png`)
|
const finalFilePath = Storage.getPublicPath('tiles', `${tileId}.png`)
|
||||||
try {
|
try {
|
||||||
await fs.unlink(finalFilePath)
|
await fs.unlink(finalFilePath)
|
||||||
} catch (error: any) {
|
} catch (error: any) {
|
||||||
|
@ -5,7 +5,7 @@ import { Server } from 'socket.io'
|
|||||||
|
|
||||||
import { gameMasterLogger } from '#application/logger'
|
import { gameMasterLogger } from '#application/logger'
|
||||||
import prisma from '#application/prisma'
|
import prisma from '#application/prisma'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import characterRepository from '#repositories/characterRepository'
|
import characterRepository from '#repositories/characterRepository'
|
||||||
|
|
||||||
@ -32,7 +32,7 @@ export default class TileUploadEvent {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
const public_folder = getPublicPath('tiles')
|
const public_folder = Storage.getPublicPath('tiles')
|
||||||
|
|
||||||
// Ensure the folder exists
|
// Ensure the folder exists
|
||||||
await fs.mkdir(public_folder, { recursive: true })
|
await fs.mkdir(public_folder, { recursive: true })
|
||||||
@ -45,7 +45,7 @@ export default class TileUploadEvent {
|
|||||||
})
|
})
|
||||||
const uuid = tile.id
|
const uuid = tile.id
|
||||||
const filename = `${uuid}.png`
|
const filename = `${uuid}.png`
|
||||||
const finalFilePath = getPublicPath('tiles', filename)
|
const finalFilePath = Storage.getPublicPath('tiles', filename)
|
||||||
await writeFile(finalFilePath, tileData)
|
await writeFile(finalFilePath, tileData)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -4,7 +4,7 @@ import { Request, Response } from 'express'
|
|||||||
|
|
||||||
import { BaseController } from '#application/base/baseController'
|
import { BaseController } from '#application/base/baseController'
|
||||||
import Database from '#application/database'
|
import Database from '#application/database'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { AssetData, UUID } from '#application/types'
|
import { AssetData, UUID } from '#application/types'
|
||||||
import SpriteRepository from '#repositories/spriteRepository'
|
import SpriteRepository from '#repositories/spriteRepository'
|
||||||
import TileRepository from '#repositories/tileRepository'
|
import TileRepository from '#repositories/tileRepository'
|
||||||
@ -98,7 +98,7 @@ export class AssetsController extends BaseController {
|
|||||||
public async downloadAsset(req: Request, res: Response) {
|
public async downloadAsset(req: Request, res: Response) {
|
||||||
const { type, spriteId, file } = req.params
|
const { type, spriteId, file } = req.params
|
||||||
|
|
||||||
const assetPath = type === 'sprites' && spriteId ? getPublicPath(type, spriteId, file) : getPublicPath(type, file)
|
const assetPath = type === 'sprites' && spriteId ? Storage.getPublicPath(type, spriteId, file) : Storage.getPublicPath(type, file)
|
||||||
|
|
||||||
if (!fs.existsSync(assetPath)) {
|
if (!fs.existsSync(assetPath)) {
|
||||||
this.logger.error(`File not found: ${assetPath}`)
|
this.logger.error(`File not found: ${assetPath}`)
|
||||||
|
@ -4,14 +4,15 @@ import { Request, Response } from 'express'
|
|||||||
import sharp from 'sharp'
|
import sharp from 'sharp'
|
||||||
|
|
||||||
import { BaseController } from '#application/base/baseController'
|
import { BaseController } from '#application/base/baseController'
|
||||||
import { getPublicPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
|
import { UUID } from '#application/types'
|
||||||
import CharacterHairRepository from '#repositories/characterHairRepository'
|
import CharacterHairRepository from '#repositories/characterHairRepository'
|
||||||
import CharacterRepository from '#repositories/characterRepository'
|
import CharacterRepository from '#repositories/characterRepository'
|
||||||
import CharacterTypeRepository from '#repositories/characterTypeRepository'
|
import CharacterTypeRepository from '#repositories/characterTypeRepository'
|
||||||
|
|
||||||
interface AvatarOptions {
|
interface AvatarOptions {
|
||||||
characterTypeId: number
|
characterTypeId: UUID
|
||||||
characterHairId?: number
|
characterHairId?: UUID
|
||||||
}
|
}
|
||||||
|
|
||||||
export class AvatarController extends BaseController {
|
export class AvatarController extends BaseController {
|
||||||
@ -57,7 +58,7 @@ export class AvatarController extends BaseController {
|
|||||||
return this.sendError(res, 'Character type not found', 404)
|
return this.sendError(res, 'Character type not found', 404)
|
||||||
}
|
}
|
||||||
|
|
||||||
const bodySpritePath = getPublicPath('sprites', characterType.sprite.id, 'idle_right_down.png')
|
const bodySpritePath = Storage.getPublicPath('sprites', characterType.sprite.id, 'idle_right_down.png')
|
||||||
if (!fs.existsSync(bodySpritePath)) {
|
if (!fs.existsSync(bodySpritePath)) {
|
||||||
return this.sendError(res, 'Body sprite file not found', 404)
|
return this.sendError(res, 'Body sprite file not found', 404)
|
||||||
}
|
}
|
||||||
@ -71,7 +72,7 @@ export class AvatarController extends BaseController {
|
|||||||
if (options.characterHairId) {
|
if (options.characterHairId) {
|
||||||
const characterHair = await CharacterHairRepository.getById(options.characterHairId)
|
const characterHair = await CharacterHairRepository.getById(options.characterHairId)
|
||||||
if (characterHair?.sprite?.id) {
|
if (characterHair?.sprite?.id) {
|
||||||
const hairSpritePath = getPublicPath('sprites', characterHair.sprite.id, 'front.png')
|
const hairSpritePath = Storage.getPublicPath('sprites', characterHair.sprite.id, 'front.png')
|
||||||
if (fs.existsSync(hairSpritePath)) {
|
if (fs.existsSync(hairSpritePath)) {
|
||||||
avatar = avatar.composite([{ input: hairSpritePath, gravity: 'north' }])
|
avatar = avatar.composite([{ input: hairSpritePath, gravity: 'north' }])
|
||||||
}
|
}
|
||||||
|
@ -6,7 +6,7 @@ import { Server as SocketServer } from 'socket.io'
|
|||||||
|
|
||||||
import config from '#application/config'
|
import config from '#application/config'
|
||||||
import Logger, { LoggerType } from '#application/logger'
|
import Logger, { LoggerType } from '#application/logger'
|
||||||
import { getAppPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import SocketManager from '#managers/socketManager'
|
import SocketManager from '#managers/socketManager'
|
||||||
|
|
||||||
@ -56,9 +56,9 @@ class QueueManager {
|
|||||||
const { jobName, params, socketId } = job.data
|
const { jobName, params, socketId } = job.data
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const jobsDir = getAppPath('jobs')
|
const jobsDir = Storage.getAppPath('jobs')
|
||||||
const extension = config.ENV === 'development' ? '.ts' : '.js'
|
const extension = config.ENV === 'development' ? '.ts' : '.js'
|
||||||
const jobPath = getAppPath('jobs', `${jobName}${extension}`)
|
const jobPath = Storage.getAppPath('jobs', `${jobName}${extension}`)
|
||||||
|
|
||||||
if (!fs.existsSync(jobPath)) {
|
if (!fs.existsSync(jobPath)) {
|
||||||
this.logger.warn(`Job file not found: ${jobPath}`)
|
this.logger.warn(`Job file not found: ${jobPath}`)
|
||||||
|
@ -7,7 +7,7 @@ import { Server as SocketServer } from 'socket.io'
|
|||||||
|
|
||||||
import config from '#application/config'
|
import config from '#application/config'
|
||||||
import Logger, { LoggerType } from '#application/logger'
|
import Logger, { LoggerType } from '#application/logger'
|
||||||
import { getAppPath } from '#application/storage'
|
import Storage from '#application/storage'
|
||||||
import { TSocket } from '#application/types'
|
import { TSocket } from '#application/types'
|
||||||
import { Authentication } from '#middleware/authentication'
|
import { Authentication } from '#middleware/authentication'
|
||||||
|
|
||||||
@ -61,11 +61,11 @@ class SocketManager {
|
|||||||
*/
|
*/
|
||||||
private async loadEventHandlers(baseDir: string, subDir: string, socket: TSocket): Promise<void> {
|
private async loadEventHandlers(baseDir: string, subDir: string, socket: TSocket): Promise<void> {
|
||||||
try {
|
try {
|
||||||
const fullDir = getAppPath(baseDir, subDir)
|
const fullDir = Storage.getAppPath(baseDir, subDir)
|
||||||
const files = await fs.promises.readdir(fullDir, { withFileTypes: true })
|
const files = await fs.promises.readdir(fullDir, { withFileTypes: true })
|
||||||
|
|
||||||
for (const file of files) {
|
for (const file of files) {
|
||||||
const filePath = getAppPath(baseDir, subDir, file.name)
|
const filePath = Storage.getAppPath(baseDir, subDir, file.name)
|
||||||
|
|
||||||
if (file.isDirectory()) {
|
if (file.isDirectory()) {
|
||||||
await this.loadEventHandlers(baseDir, `${subDir}/${file.name}`, socket)
|
await this.loadEventHandlers(baseDir, `${subDir}/${file.name}`, socket)
|
||||||
|
Loading…
x
Reference in New Issue
Block a user