- Migration 013: loot_profiles table (JSONB loot_table + loot_groups, license-scoped) - TypeORM entity matching migration schema exactly - NestJS loot module: 10 endpoints (CRUD, duplicate, apply, import, export, containers) - Multiplier logic recursively scales Min/Max/Scrap across loot tables and groups - Apply-to-server writes BetterLoot JSON via NATS file manager + RCON reload - Frontend static data: 191 Rust items, 51 container prefabs - TypeScript types for BetterLoot data model (PrefabLoot, LootEntry, LootRNG, etc.) - Fix vue-tsc errors: UngroupedItems uses LootRNG, null safety in store/view Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
113 lines
3.8 KiB
TypeScript
113 lines
3.8 KiB
TypeScript
import {
|
|
Controller,
|
|
Get,
|
|
Post,
|
|
Put,
|
|
Delete,
|
|
Body,
|
|
Param,
|
|
Query,
|
|
UseGuards,
|
|
} from '@nestjs/common';
|
|
import { ApiTags, ApiBearerAuth, ApiOperation, ApiQuery } from '@nestjs/swagger';
|
|
import { LootService } from './loot.service';
|
|
import { CreateLootProfileDto } from './dto/create-loot-profile.dto';
|
|
import { UpdateLootProfileDto } from './dto/update-loot-profile.dto';
|
|
import { ApplyLootProfileDto } from './dto/apply-loot-profile.dto';
|
|
import { ImportLootProfileDto } from './dto/import-loot-profile.dto';
|
|
import { CurrentTenant } from '../../common/decorators/current-tenant.decorator';
|
|
import { RequirePermission } from '../../common/decorators/require-permission.decorator';
|
|
import { JwtAuthGuard } from '../../common/guards/jwt-auth.guard';
|
|
import { PermissionsGuard } from '../../common/guards/permissions.guard';
|
|
|
|
@ApiTags('loot')
|
|
@ApiBearerAuth()
|
|
@Controller('loot')
|
|
@UseGuards(JwtAuthGuard, PermissionsGuard)
|
|
export class LootController {
|
|
constructor(private readonly lootService: LootService) {}
|
|
|
|
@Get('profiles')
|
|
@RequirePermission('loot.view')
|
|
@ApiOperation({ summary: 'List loot profiles (summaries)' })
|
|
getProfiles(@CurrentTenant() licenseId: string) {
|
|
return this.lootService.getProfiles(licenseId);
|
|
}
|
|
|
|
@Get('profiles/:id')
|
|
@RequirePermission('loot.view')
|
|
@ApiOperation({ summary: 'Get full loot profile with data' })
|
|
getProfile(@CurrentTenant() licenseId: string, @Param('id') id: string) {
|
|
return this.lootService.getProfile(licenseId, id);
|
|
}
|
|
|
|
@Post('profiles')
|
|
@RequirePermission('loot.manage')
|
|
@ApiOperation({ summary: 'Create loot profile' })
|
|
createProfile(@CurrentTenant() licenseId: string, @Body() dto: CreateLootProfileDto) {
|
|
return this.lootService.createProfile(licenseId, dto);
|
|
}
|
|
|
|
@Put('profiles/:id')
|
|
@RequirePermission('loot.manage')
|
|
@ApiOperation({ summary: 'Update loot profile' })
|
|
updateProfile(
|
|
@CurrentTenant() licenseId: string,
|
|
@Param('id') id: string,
|
|
@Body() dto: UpdateLootProfileDto,
|
|
) {
|
|
return this.lootService.updateProfile(licenseId, id, dto);
|
|
}
|
|
|
|
@Delete('profiles/:id')
|
|
@RequirePermission('loot.manage')
|
|
@ApiOperation({ summary: 'Delete loot profile' })
|
|
deleteProfile(@CurrentTenant() licenseId: string, @Param('id') id: string) {
|
|
return this.lootService.deleteProfile(licenseId, id);
|
|
}
|
|
|
|
@Post('profiles/:id/duplicate')
|
|
@RequirePermission('loot.manage')
|
|
@ApiOperation({ summary: 'Duplicate loot profile' })
|
|
duplicateProfile(@CurrentTenant() licenseId: string, @Param('id') id: string) {
|
|
return this.lootService.duplicateProfile(licenseId, id);
|
|
}
|
|
|
|
@Post('profiles/:id/apply')
|
|
@RequirePermission('loot.manage')
|
|
@ApiOperation({ summary: 'Apply loot profile to server with multiplier' })
|
|
applyToServer(
|
|
@CurrentTenant() licenseId: string,
|
|
@Param('id') id: string,
|
|
@Body() dto: ApplyLootProfileDto,
|
|
) {
|
|
return this.lootService.applyToServer(licenseId, id, dto.multiplier);
|
|
}
|
|
|
|
@Post('import')
|
|
@RequirePermission('loot.manage')
|
|
@ApiOperation({ summary: 'Import BetterLoot/Looty JSON as new profile' })
|
|
importProfile(@CurrentTenant() licenseId: string, @Body() dto: ImportLootProfileDto) {
|
|
return this.lootService.importProfile(licenseId, dto);
|
|
}
|
|
|
|
@Get('export/:id')
|
|
@RequirePermission('loot.view')
|
|
@ApiOperation({ summary: 'Export loot profile as BetterLoot JSON' })
|
|
@ApiQuery({ name: 'multiplier', required: false, example: 1 })
|
|
exportProfile(
|
|
@CurrentTenant() licenseId: string,
|
|
@Param('id') id: string,
|
|
@Query('multiplier') multiplier: string,
|
|
) {
|
|
return this.lootService.exportProfile(licenseId, id, multiplier ? parseInt(multiplier, 10) : 1);
|
|
}
|
|
|
|
@Get('containers')
|
|
@RequirePermission('loot.view')
|
|
@ApiOperation({ summary: 'Get list of Rust container prefabs' })
|
|
getContainers() {
|
|
return this.lootService.getContainers();
|
|
}
|
|
}
|