mirror of
https://github.com/SyncrowIOT/backend.git
synced 2026-10-23 12:57:55 +00:00
created space model create service
This commit is contained in:
@@ -0,0 +1,33 @@
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
import { IsNotEmpty, IsString, IsArray, ValidateNested } from 'class-validator';
|
||||
import { Type } from 'class-transformer';
|
||||
import { CreateSubspaceModelDto } from './create-subspace-model.dto';
|
||||
import { CreateSpaceProductModelDto } from './create-space-product-model.dto';
|
||||
|
||||
export class CreateSpaceModelDto {
|
||||
@ApiProperty({
|
||||
description: 'Name of the space model',
|
||||
example: 'Apartment Model',
|
||||
})
|
||||
@IsNotEmpty()
|
||||
@IsString()
|
||||
modelName: string;
|
||||
|
||||
@ApiProperty({
|
||||
description: 'List of subspaces included in the model',
|
||||
type: [CreateSubspaceModelDto],
|
||||
})
|
||||
@IsArray()
|
||||
@ValidateNested({ each: true })
|
||||
@Type(() => CreateSubspaceModelDto)
|
||||
subspaceModels?: CreateSubspaceModelDto[];
|
||||
|
||||
@ApiProperty({
|
||||
description: 'List of products included in the model',
|
||||
type: [CreateSpaceProductModelDto],
|
||||
})
|
||||
@IsArray()
|
||||
@ValidateNested({ each: true })
|
||||
@Type(() => CreateSpaceProductModelDto)
|
||||
spaceProductModels?: CreateSpaceProductModelDto[];
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
import { IsNotEmpty, IsString } from 'class-validator';
|
||||
|
||||
export class CreateSpaceProductItemModelDto {
|
||||
@ApiProperty({
|
||||
description: 'Specific name for the product item',
|
||||
example: 'Light 1',
|
||||
})
|
||||
@IsNotEmpty()
|
||||
@IsString()
|
||||
tag: string;
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
import { IsNotEmpty, IsString, IsArray, ValidateNested } from 'class-validator';
|
||||
import { Type } from 'class-transformer';
|
||||
import { CreateSpaceProductItemModelDto } from './create-space-product-item-model.dto';
|
||||
|
||||
export class CreateSpaceProductModelDto {
|
||||
@ApiProperty({
|
||||
description: 'ID of the product associated with the model',
|
||||
example: 'product-uuid',
|
||||
})
|
||||
@IsNotEmpty()
|
||||
@IsString()
|
||||
productId: string;
|
||||
|
||||
@ApiProperty({
|
||||
description: 'Number of products in the model',
|
||||
example: 3,
|
||||
})
|
||||
@IsNotEmpty()
|
||||
productCount: number;
|
||||
|
||||
@ApiProperty({
|
||||
description: 'Specific names for each product item',
|
||||
type: [CreateSpaceProductItemModelDto],
|
||||
})
|
||||
@IsArray()
|
||||
@ValidateNested({ each: true })
|
||||
@Type(() => CreateSpaceProductItemModelDto)
|
||||
items: CreateSpaceProductItemModelDto[];
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
import { IsNotEmpty, IsString } from 'class-validator';
|
||||
|
||||
export class CreateSubspaceModelDto {
|
||||
@ApiProperty({
|
||||
description: 'Name of the subspace',
|
||||
example: 'Living Room',
|
||||
})
|
||||
@IsNotEmpty()
|
||||
@IsString()
|
||||
subspaceName: string;
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
export * from './create-space-model.dto';
|
||||
export * from './create-space-product-item-model.dto';
|
||||
export * from './create-space-product-model.dto';
|
||||
export * from './create-subspace-model.dto';
|
||||
export * from './project-param.dto';
|
||||
@@ -0,0 +1,11 @@
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
import { IsUUID } from 'class-validator';
|
||||
|
||||
export class projectParam {
|
||||
@ApiProperty({
|
||||
description: 'UUID of the Project',
|
||||
example: 'd290f1ee-6c54-4b01-90e6-d701748f0851',
|
||||
})
|
||||
@IsUUID()
|
||||
projectUuid: string;
|
||||
}
|
||||
@@ -0,0 +1,4 @@
|
||||
export * from './space-model.service';
|
||||
export * from './space-product-item-model.service';
|
||||
export * from './space-product-model.service';
|
||||
export * from './subspace-model.service';
|
||||
@@ -0,0 +1,94 @@
|
||||
import { SpaceModelRepository } from '@app/common/modules/space-model';
|
||||
import { HttpException, HttpStatus, Injectable } from '@nestjs/common';
|
||||
import { CreateSpaceModelDto } from '../dtos';
|
||||
import { ProjectRepository } from '@app/common/modules/project/repositiories';
|
||||
import { ProjectParam } from 'src/community/dtos';
|
||||
import { SuccessResponseDto } from '@app/common/dto/success.response.dto';
|
||||
import { SubSpaceModelService } from './subspace-model.service';
|
||||
import { SpaceProductModelService } from './space-product-model.service';
|
||||
|
||||
@Injectable()
|
||||
export class SpaceModelService {
|
||||
constructor(
|
||||
private readonly spaceModelRepository: SpaceModelRepository,
|
||||
private readonly projectRepository: ProjectRepository,
|
||||
private readonly subSpaceModelService: SubSpaceModelService,
|
||||
private readonly spaceProductModelService: SpaceProductModelService,
|
||||
) {}
|
||||
|
||||
async createSpaceModel(
|
||||
createSpaceModelDto: CreateSpaceModelDto,
|
||||
params: ProjectParam,
|
||||
) {
|
||||
const { modelName, subspaceModels, spaceProductModels } =
|
||||
createSpaceModelDto;
|
||||
const project = await this.validateProject(params.projectUuid);
|
||||
|
||||
try {
|
||||
const isModelExist = await this.validateName(
|
||||
modelName,
|
||||
params.projectUuid,
|
||||
);
|
||||
if (isModelExist) {
|
||||
throw new HttpException(
|
||||
`Model name "${modelName}" already exists in this project ${project.name}.`,
|
||||
HttpStatus.CONFLICT,
|
||||
);
|
||||
}
|
||||
|
||||
const spaceModel = await this.spaceModelRepository.create({
|
||||
modelName,
|
||||
project,
|
||||
});
|
||||
const savedSpaceModel = await this.spaceModelRepository.save(spaceModel);
|
||||
|
||||
await this.subSpaceModelService.createSubSpaceModels(
|
||||
subspaceModels,
|
||||
savedSpaceModel,
|
||||
);
|
||||
|
||||
await this.spaceProductModelService.createSpaceProductModels(
|
||||
spaceProductModels,
|
||||
savedSpaceModel,
|
||||
);
|
||||
|
||||
return new SuccessResponseDto({
|
||||
message: `Successfully created new space model with uuid ${savedSpaceModel.uuid}`,
|
||||
data: savedSpaceModel,
|
||||
statusCode: HttpStatus.CREATED,
|
||||
});
|
||||
} catch (error) {
|
||||
if (error instanceof HttpException) {
|
||||
throw error;
|
||||
}
|
||||
|
||||
throw new HttpException(
|
||||
error.message || `An unexpected error occurred`,
|
||||
HttpStatus.INTERNAL_SERVER_ERROR,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
async validateProject(projectUuid: string) {
|
||||
const project = await this.projectRepository.findOne({
|
||||
where: {
|
||||
uuid: projectUuid,
|
||||
},
|
||||
});
|
||||
|
||||
if (!project) {
|
||||
throw new HttpException(
|
||||
`Project with uuid ${projectUuid} not found`,
|
||||
HttpStatus.NOT_FOUND,
|
||||
);
|
||||
}
|
||||
return project;
|
||||
}
|
||||
|
||||
async validateName(modelName: string, projectUuid: string): Promise<boolean> {
|
||||
const isModelExist = await this.spaceModelRepository.exists({
|
||||
where: { modelName, project: { uuid: projectUuid } },
|
||||
});
|
||||
return isModelExist;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,79 @@
|
||||
import {
|
||||
SpaceModelEntity,
|
||||
SpaceProductItemModelRepository,
|
||||
SpaceProductModelEntity,
|
||||
} from '@app/common/modules/space-model';
|
||||
import { HttpException, HttpStatus, Injectable } from '@nestjs/common';
|
||||
import { CreateSpaceProductItemModelDto } from '../dtos';
|
||||
|
||||
@Injectable()
|
||||
export class SpaceProductItemModelService {
|
||||
constructor(
|
||||
private readonly spaceProductItemRepository: SpaceProductItemModelRepository,
|
||||
) {}
|
||||
|
||||
async createProdutItemModel(
|
||||
itemModelDtos: CreateSpaceProductItemModelDto[],
|
||||
spaceProductModel: SpaceProductModelEntity,
|
||||
spaceModel: SpaceModelEntity,
|
||||
) {
|
||||
try {
|
||||
await this.validateTags(itemModelDtos, spaceModel);
|
||||
|
||||
for (const itemModelDto of itemModelDtos) {
|
||||
await this.create(itemModelDto, spaceProductModel, spaceModel);
|
||||
}
|
||||
} catch (error) {
|
||||
throw new HttpException(
|
||||
error.message || `An unexpected error occurred`,
|
||||
HttpStatus.INTERNAL_SERVER_ERROR,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
async create(
|
||||
itemModelDto: CreateSpaceProductItemModelDto,
|
||||
spaceProductModel: SpaceProductModelEntity,
|
||||
spaceModel: SpaceModelEntity,
|
||||
) {
|
||||
const productItem = this.spaceProductItemRepository.create({
|
||||
tag: itemModelDto.tag,
|
||||
spaceProductModel,
|
||||
spaceModel,
|
||||
});
|
||||
await this.spaceProductItemRepository.save(productItem);
|
||||
}
|
||||
|
||||
async validateTags(
|
||||
itemModelDtos: CreateSpaceProductItemModelDto[],
|
||||
spaceModel: SpaceModelEntity,
|
||||
) {
|
||||
const incomingTags = itemModelDtos.map((item) => item.tag);
|
||||
|
||||
const duplicateTags = incomingTags.filter(
|
||||
(tag, index) => incomingTags.indexOf(tag) !== index,
|
||||
);
|
||||
if (duplicateTags.length > 0) {
|
||||
throw new HttpException(
|
||||
`Duplicate tags found in request: ${duplicateTags.join(', ')}`,
|
||||
HttpStatus.CONFLICT,
|
||||
);
|
||||
}
|
||||
|
||||
const existingTags = await this.spaceProductItemRepository.find({
|
||||
where: { spaceModel },
|
||||
select: ['tag'],
|
||||
});
|
||||
const existingTagSet = new Set(existingTags.map((item) => item.tag));
|
||||
|
||||
const conflictingTags = incomingTags.filter((tag) =>
|
||||
existingTagSet.has(tag),
|
||||
);
|
||||
if (conflictingTags.length > 0) {
|
||||
throw new HttpException(
|
||||
`Tags already exist in the model: ${conflictingTags.join(', ')}`,
|
||||
HttpStatus.CONFLICT,
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,61 @@
|
||||
import {
|
||||
SpaceModelEntity,
|
||||
SpaceProductModelRepository,
|
||||
} from '@app/common/modules/space-model';
|
||||
import { HttpException, HttpStatus, Injectable } from '@nestjs/common';
|
||||
import { CreateSpaceProductModelDto } from '../dtos';
|
||||
import { ProductRepository } from '@app/common/modules/product/repositories';
|
||||
import { SpaceProductItemModelService } from './space-product-item-model.service';
|
||||
|
||||
@Injectable()
|
||||
export class SpaceProductModelService {
|
||||
constructor(
|
||||
private readonly spaceProductModelRepository: SpaceProductModelRepository,
|
||||
private readonly productRepository: ProductRepository,
|
||||
private readonly spaceProductItemModelService: SpaceProductItemModelService,
|
||||
) {}
|
||||
|
||||
async createSpaceProductModels(
|
||||
spaceProductModelDtos: CreateSpaceProductModelDto[],
|
||||
spaceModel: SpaceModelEntity,
|
||||
) {
|
||||
try {
|
||||
for (const spaceProductModelDto of spaceProductModelDtos) {
|
||||
await this.create(spaceProductModelDto, spaceModel);
|
||||
}
|
||||
} catch (error) {
|
||||
throw new HttpException(
|
||||
error.message || `An unexpected error occurred`,
|
||||
HttpStatus.INTERNAL_SERVER_ERROR,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
async create(
|
||||
spaceProductModelDto: CreateSpaceProductModelDto,
|
||||
spaceModel: SpaceModelEntity,
|
||||
) {
|
||||
const product = await this.productRepository.findOneBy({
|
||||
uuid: spaceProductModelDto.productId,
|
||||
});
|
||||
if (!product) {
|
||||
throw new HttpException(
|
||||
`Product with ID ${spaceProductModelDto.productId} not found`,
|
||||
HttpStatus.NOT_FOUND,
|
||||
);
|
||||
}
|
||||
const spaceProductModel = this.spaceProductModelRepository.create({
|
||||
product,
|
||||
productCount: spaceProductModelDto.productCount,
|
||||
spaceModel: spaceModel,
|
||||
});
|
||||
const newProductModel =
|
||||
await this.spaceProductModelRepository.save(spaceProductModel);
|
||||
|
||||
await this.spaceProductItemModelService.createProdutItemModel(
|
||||
spaceProductModelDto.items,
|
||||
newProductModel,
|
||||
spaceModel,
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
import {
|
||||
SpaceModelEntity,
|
||||
SubspaceModelRepository,
|
||||
} from '@app/common/modules/space-model';
|
||||
import { HttpException, HttpStatus, Injectable } from '@nestjs/common';
|
||||
import { CreateSubspaceModelDto } from '../dtos';
|
||||
|
||||
@Injectable()
|
||||
export class SubSpaceModelService {
|
||||
constructor(
|
||||
private readonly subspaceModelRepository: SubspaceModelRepository,
|
||||
) {}
|
||||
|
||||
async createSubSpaceModels(
|
||||
subSpaceModelDtos: CreateSubspaceModelDto[],
|
||||
spaceModel: SpaceModelEntity,
|
||||
) {
|
||||
try {
|
||||
for (const subspaceDto of subSpaceModelDtos) {
|
||||
const subspace = this.subspaceModelRepository.create({
|
||||
subspaceName: subspaceDto.subspaceName,
|
||||
spaceModel: spaceModel,
|
||||
});
|
||||
await this.subspaceModelRepository.save(subspace);
|
||||
}
|
||||
} catch (error) {
|
||||
throw new HttpException(
|
||||
error.message || `An unexpected error occurred`,
|
||||
HttpStatus.INTERNAL_SERVER_ERROR,
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user