src/lanes/lanes.controller.ts
lanes
Methods |
|
| Async addTariff | ||||||||||||
addTariff(orgId: string, id: string, dto: CreateTariffDto)
|
||||||||||||
Decorators :
@Post(':id/tariffs')
|
||||||||||||
|
Defined in src/lanes/lanes.controller.ts:98
|
||||||||||||
|
Parameters :
Returns :
unknown
|
| Async bulkUpload | |||||||||
bulkUpload(orgId: string, file: Express.Multer.File)
|
|||||||||
Decorators :
@Post('upload')
|
|||||||||
|
Defined in src/lanes/lanes.controller.ts:149
|
|||||||||
|
Parameters :
Returns :
unknown
|
| Async create | |||||||||
create(orgId: string, dto: CreateLaneDto)
|
|||||||||
Decorators :
@Post()
|
|||||||||
|
Defined in src/lanes/lanes.controller.ts:46
|
|||||||||
|
Parameters :
Returns :
unknown
|
| Async findAll | |||||||||
findAll(orgId: string, query: PaginationParams)
|
|||||||||
Decorators :
@Get()
|
|||||||||
|
Defined in src/lanes/lanes.controller.ts:56
|
|||||||||
|
Parameters :
Returns :
unknown
|
| Async findOne |
findOne(orgId: string, id: string)
|
Decorators :
@Get(':id')
|
|
Defined in src/lanes/lanes.controller.ts:65
|
|
Returns :
unknown
|
| Async getTariffs |
getTariffs(orgId: string, id: string, activeOnly?: string)
|
Decorators :
@Get(':id/tariffs')
|
|
Defined in src/lanes/lanes.controller.ts:109
|
|
Returns :
unknown
|
| Async remove |
remove(orgId: string, id: string)
|
Decorators :
@Delete(':id')
|
|
Defined in src/lanes/lanes.controller.ts:86
|
|
Returns :
unknown
|
| Async removeTariff |
removeTariff(orgId: string, id: string, tariffId: string)
|
Decorators :
@Delete(':id/tariffs/:tariffId')
|
|
Defined in src/lanes/lanes.controller.ts:134
|
|
Returns :
unknown
|
| Async update | ||||||||||||
update(orgId: string, id: string, dto: UpdateLaneDto)
|
||||||||||||
Decorators :
@Patch(':id')
|
||||||||||||
|
Defined in src/lanes/lanes.controller.ts:75
|
||||||||||||
|
Parameters :
Returns :
unknown
|
| Async updateTariff | |||||||||||||||
updateTariff(orgId: string, id: string, tariffId: string, dto: Partial<CreateTariffDto>)
|
|||||||||||||||
Decorators :
@Patch(':id/tariffs/:tariffId')
|
|||||||||||||||
|
Defined in src/lanes/lanes.controller.ts:122
|
|||||||||||||||
|
Parameters :
Returns :
unknown
|
import {
Controller,
Get,
Post,
Patch,
Delete,
Body,
Param,
Query,
UseGuards,
UseInterceptors,
UploadedFile,
BadRequestException,
} from '@nestjs/common';
import { FileInterceptor } from '@nestjs/platform-express';
import { ApiTags, ApiBearerAuth, ApiOperation, ApiConsumes, ApiQuery } from '@nestjs/swagger';
import { LanesService } from './lanes.service';
import { CreateLaneDto } from './dto/create-lane.dto';
import { UpdateLaneDto } from './dto/update-lane.dto';
import { CreateTariffDto } from './dto/create-tariff.dto';
import { CombinedAuthGuard } from '../auth/guards/combined-auth.guard';
import { RolesGuard } from '../auth/guards/roles.guard';
import { Roles } from '../auth/decorators/roles.decorator';
import { CurrentUser } from '../auth/decorators/current-user.decorator';
import { ApiPagination } from '../common/decorators/api-pagination.decorator';
import { PaginationParams } from '../common/utils/pagination.util';
/**
* Lane geometry can be edited by ops staff (PLANNER builds routes daily).
* Tariffs are commercial decisions, so they're locked tighter — only the
* org admins / SUPER_ADMIN can touch rate cards.
*/
const LANE_WRITERS = ['SUPER_ADMIN', 'ADMIN', 'OPERATIONS_MANAGER', 'PLANNER'] as const;
const TARIFF_WRITERS = ['SUPER_ADMIN', 'ADMIN', 'OPERATIONS_MANAGER'] as const;
@ApiTags('Lanes')
@ApiBearerAuth()
@UseGuards(CombinedAuthGuard, RolesGuard)
@Controller('lanes')
export class LanesController {
constructor(private readonly lanesService: LanesService) {}
@Post()
@Roles(...LANE_WRITERS)
@ApiOperation({ summary: 'Create a new lane' })
async create(
@CurrentUser('organizationId') orgId: string,
@Body() dto: CreateLaneDto,
) {
return this.lanesService.create(orgId, dto);
}
@Get()
@ApiPagination()
@ApiOperation({ summary: 'List all lanes (org-scoped)' })
async findAll(
@CurrentUser('organizationId') orgId: string,
@Query() query: PaginationParams,
) {
return this.lanesService.findAll(orgId, query);
}
@Get(':id')
@ApiOperation({ summary: 'Get lane by ID (org-scoped, includes tariffs)' })
async findOne(
@CurrentUser('organizationId') orgId: string,
@Param('id') id: string,
) {
return this.lanesService.findOne(orgId, id);
}
@Patch(':id')
@Roles(...LANE_WRITERS)
@ApiOperation({ summary: 'Update a lane (org-scoped)' })
async update(
@CurrentUser('organizationId') orgId: string,
@Param('id') id: string,
@Body() dto: UpdateLaneDto,
) {
return this.lanesService.update(orgId, id, dto);
}
@Delete(':id')
@Roles(...LANE_WRITERS)
@ApiOperation({ summary: 'Delete a lane (blocked when in use by trips/orders)' })
async remove(
@CurrentUser('organizationId') orgId: string,
@Param('id') id: string,
) {
return this.lanesService.remove(orgId, id);
}
// ── Tariffs ──────────────────────────────────────────────────────
@Post(':id/tariffs')
@Roles(...TARIFF_WRITERS)
@ApiOperation({ summary: 'Add a tariff to a lane' })
async addTariff(
@CurrentUser('organizationId') orgId: string,
@Param('id') id: string,
@Body() dto: CreateTariffDto,
) {
return this.lanesService.addTariff(orgId, id, dto);
}
@Get(':id/tariffs')
@ApiOperation({ summary: 'List tariffs for a lane (with isActive flag)' })
@ApiQuery({ name: 'activeOnly', required: false, type: Boolean })
async getTariffs(
@CurrentUser('organizationId') orgId: string,
@Param('id') id: string,
@Query('activeOnly') activeOnly?: string,
) {
return this.lanesService.getTariffs(orgId, id, {
activeOnly: activeOnly === 'true' || activeOnly === '1',
});
}
@Patch(':id/tariffs/:tariffId')
@Roles(...TARIFF_WRITERS)
@ApiOperation({ summary: 'Update a tariff on a lane' })
async updateTariff(
@CurrentUser('organizationId') orgId: string,
@Param('id') id: string,
@Param('tariffId') tariffId: string,
@Body() dto: Partial<CreateTariffDto>,
) {
return this.lanesService.updateTariff(orgId, id, tariffId, dto);
}
@Delete(':id/tariffs/:tariffId')
@Roles(...TARIFF_WRITERS)
@ApiOperation({ summary: 'Delete a tariff from a lane' })
async removeTariff(
@CurrentUser('organizationId') orgId: string,
@Param('id') id: string,
@Param('tariffId') tariffId: string,
) {
return this.lanesService.removeTariff(orgId, id, tariffId);
}
// ── Bulk import ──────────────────────────────────────────────────
@Post('upload')
@Roles(...LANE_WRITERS)
@ApiOperation({ summary: 'Bulk upload lanes from Excel/CSV' })
@ApiConsumes('multipart/form-data')
@UseInterceptors(FileInterceptor('file', { limits: { fileSize: 10 * 1024 * 1024 } }))
async bulkUpload(
@CurrentUser('organizationId') orgId: string,
@UploadedFile() file: Express.Multer.File,
) {
if (!file) throw new BadRequestException('No file uploaded');
return this.lanesService.bulkUploadFromFile(orgId, file);
}
}