Handout management
This commit is contained in:
@@ -8,6 +8,7 @@ import { AuthGuard } from './core/guards/auth.guard';
|
||||
import { UserModule } from './modules/user/user.module';
|
||||
import { RoleModule } from './modules/role/role.module';
|
||||
import { KeyModule } from './modules/key/key.module';
|
||||
import { CustomerModule } from './modules/customer/customer.module';
|
||||
|
||||
@Module({
|
||||
imports: [
|
||||
@@ -20,6 +21,7 @@ import { KeyModule } from './modules/key/key.module';
|
||||
UserModule,
|
||||
RoleModule,
|
||||
KeyModule,
|
||||
CustomerModule,
|
||||
],
|
||||
controllers: [AppController],
|
||||
providers: [AppService, AuthGuard],
|
||||
|
||||
13
api/src/model/dto/handover-key.dto.ts
Normal file
13
api/src/model/dto/handover-key.dto.ts
Normal file
@@ -0,0 +1,13 @@
|
||||
import { IsNotEmpty } from 'class-validator';
|
||||
import { Customer, Key } from '../entitites';
|
||||
|
||||
export class HandoverKeyDto {
|
||||
@IsNotEmpty()
|
||||
key: Key;
|
||||
|
||||
@IsNotEmpty()
|
||||
customer: Customer;
|
||||
|
||||
@IsNotEmpty()
|
||||
direction: 'out' | 'return';
|
||||
}
|
||||
@@ -1,3 +1,4 @@
|
||||
export * from './login.dto';
|
||||
export * from './auth-code.dto';
|
||||
export * from './create-key-system.dto';
|
||||
export * from './handover-key.dto';
|
||||
|
||||
33
api/src/model/entitites/customer.entity.ts
Normal file
33
api/src/model/entitites/customer.entity.ts
Normal file
@@ -0,0 +1,33 @@
|
||||
import {
|
||||
Column,
|
||||
CreateDateColumn,
|
||||
Entity,
|
||||
ManyToOne,
|
||||
OneToMany,
|
||||
PrimaryGeneratedColumn,
|
||||
UpdateDateColumn,
|
||||
} from 'typeorm';
|
||||
import { Key } from './key.entity';
|
||||
import { KeySystem } from './system.entity';
|
||||
import { ICustomer } from '../interface';
|
||||
|
||||
@Entity()
|
||||
export class Customer implements ICustomer {
|
||||
@PrimaryGeneratedColumn('uuid')
|
||||
id: string;
|
||||
|
||||
@Column({ nullable: false, unique: false })
|
||||
name: string;
|
||||
|
||||
@OneToMany(() => Key, (key) => key.customer)
|
||||
keys: Key[];
|
||||
|
||||
@ManyToOne(() => KeySystem)
|
||||
system: KeySystem;
|
||||
|
||||
@CreateDateColumn({ name: 'created_at' })
|
||||
createdAt: Date;
|
||||
|
||||
@UpdateDateColumn({ name: 'updatet_at' })
|
||||
updatedAt: Date;
|
||||
}
|
||||
@@ -4,3 +4,5 @@ export * from './role.entity';
|
||||
export * from './cylinder.entity';
|
||||
export * from './key.entity';
|
||||
export * from './key_activity.entity';
|
||||
export * from './customer.entity';
|
||||
export * from './key-handout.entity';
|
||||
|
||||
38
api/src/model/entitites/key-handout.entity.ts
Normal file
38
api/src/model/entitites/key-handout.entity.ts
Normal file
@@ -0,0 +1,38 @@
|
||||
import {
|
||||
BeforeInsert,
|
||||
Column,
|
||||
CreateDateColumn,
|
||||
Entity,
|
||||
ManyToOne,
|
||||
PrimaryGeneratedColumn,
|
||||
} from 'typeorm';
|
||||
import { Key } from './key.entity';
|
||||
import { Customer } from './customer.entity';
|
||||
|
||||
@Entity()
|
||||
export class KeyHandout {
|
||||
@PrimaryGeneratedColumn('uuid')
|
||||
id: string;
|
||||
|
||||
@ManyToOne(() => Key)
|
||||
key: Key;
|
||||
|
||||
@Column()
|
||||
direction: 'out' | 'return';
|
||||
|
||||
@ManyToOne(() => Customer)
|
||||
customer: Customer;
|
||||
|
||||
@Column()
|
||||
timestamp: Date;
|
||||
|
||||
@CreateDateColumn()
|
||||
created: Date;
|
||||
|
||||
@BeforeInsert()
|
||||
insertTimestamp() {
|
||||
if (this.timestamp == null) {
|
||||
this.timestamp = new Date();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -8,6 +8,7 @@ import {
|
||||
} from 'typeorm';
|
||||
import { Cylinder } from './cylinder.entity';
|
||||
import { IKey } from '../interface/key.interface';
|
||||
import { Customer } from './customer.entity';
|
||||
|
||||
@Entity()
|
||||
export class Key implements IKey {
|
||||
@@ -26,6 +27,9 @@ export class Key implements IKey {
|
||||
@ManyToOne(() => Cylinder, (cylinder) => cylinder.keys)
|
||||
cylinder: Cylinder;
|
||||
|
||||
@ManyToOne(() => Customer, (customer) => customer.keys)
|
||||
customer: Customer;
|
||||
|
||||
@CreateDateColumn({ name: 'created_at' })
|
||||
createdAt: Date;
|
||||
|
||||
|
||||
@@ -8,6 +8,7 @@ import {
|
||||
import { User } from './user.entity';
|
||||
import { IKey } from '../interface/key.interface';
|
||||
import { Cylinder } from './cylinder.entity';
|
||||
import { Customer } from './customer.entity';
|
||||
|
||||
@Entity()
|
||||
export class KeyActivity implements IKey {
|
||||
@@ -29,6 +30,9 @@ export class KeyActivity implements IKey {
|
||||
@ManyToOne(() => Cylinder)
|
||||
cylinder: Cylinder;
|
||||
|
||||
@ManyToOne(() => Customer)
|
||||
customer: Customer;
|
||||
|
||||
@CreateDateColumn({ name: 'created_at' })
|
||||
createdAt: Date;
|
||||
|
||||
|
||||
11
api/src/model/interface/customer.interface.ts
Normal file
11
api/src/model/interface/customer.interface.ts
Normal file
@@ -0,0 +1,11 @@
|
||||
import { Key } from 'readline';
|
||||
import { KeySystem } from '../entitites/system.entity';
|
||||
|
||||
export interface ICustomer {
|
||||
id: string;
|
||||
name: string;
|
||||
keys: Key[];
|
||||
system: KeySystem;
|
||||
createdAt: Date;
|
||||
updatedAt: Date;
|
||||
}
|
||||
@@ -2,3 +2,4 @@ export * from './user.interface';
|
||||
export * from './external-access-token.payload.interface';
|
||||
export * from './payload.interface';
|
||||
export * from './key-system.interface';
|
||||
export * from './customer.interface';
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { Cylinder } from '../entitites';
|
||||
import { Customer, Cylinder } from '../entitites';
|
||||
|
||||
export interface IKey {
|
||||
id: string;
|
||||
@@ -6,5 +6,6 @@ export interface IKey {
|
||||
nr: number;
|
||||
handedOut: boolean;
|
||||
cylinder: Cylinder;
|
||||
customer: Customer;
|
||||
createdAt: Date;
|
||||
}
|
||||
|
||||
10
api/src/model/repositories/customer.repository.ts
Normal file
10
api/src/model/repositories/customer.repository.ts
Normal file
@@ -0,0 +1,10 @@
|
||||
import { Injectable } from '@nestjs/common';
|
||||
import { Repository, DataSource } from 'typeorm';
|
||||
import { Customer } from '../entitites';
|
||||
|
||||
@Injectable()
|
||||
export class CustomerRepository extends Repository<Customer> {
|
||||
constructor(dataSource: DataSource) {
|
||||
super(Customer, dataSource.createEntityManager());
|
||||
}
|
||||
}
|
||||
@@ -5,3 +5,4 @@ export * from './system.repository';
|
||||
export * from './cylinder.repository';
|
||||
export * from './key.repository';
|
||||
export * from './key_activity.repository';
|
||||
export * from './customer.repository';
|
||||
|
||||
10
api/src/model/repositories/key-handout.repository.ts
Normal file
10
api/src/model/repositories/key-handout.repository.ts
Normal file
@@ -0,0 +1,10 @@
|
||||
import { Injectable } from '@nestjs/common';
|
||||
import { Repository, DataSource } from 'typeorm';
|
||||
import { KeyHandout } from '../entitites';
|
||||
|
||||
@Injectable()
|
||||
export class KeyHandoutRepository extends Repository<KeyHandout> {
|
||||
constructor(dataSource: DataSource) {
|
||||
super(KeyHandout, dataSource.createEntityManager());
|
||||
}
|
||||
}
|
||||
20
api/src/modules/customer/customer.controller.ts
Normal file
20
api/src/modules/customer/customer.controller.ts
Normal file
@@ -0,0 +1,20 @@
|
||||
import { Body, Controller, Get, Post, Req, UseGuards } from '@nestjs/common';
|
||||
import { AuthGuard } from 'src/core/guards/auth.guard';
|
||||
import { AuthenticatedRequest } from 'src/model/interface/authenticated-request.interface';
|
||||
import { CustomerService } from './customer.service';
|
||||
|
||||
@Controller('customer')
|
||||
@UseGuards(AuthGuard)
|
||||
export class CustomerController {
|
||||
constructor(private service: CustomerService) {}
|
||||
|
||||
@Get()
|
||||
getCustomers(@Req() req: AuthenticatedRequest) {
|
||||
return this.service.getCustomers(req.user);
|
||||
}
|
||||
|
||||
@Post()
|
||||
createCustomer(@Req() req: AuthenticatedRequest, @Body() body: any) {
|
||||
return this.service.createCustomer(req.user, body);
|
||||
}
|
||||
}
|
||||
12
api/src/modules/customer/customer.module.ts
Normal file
12
api/src/modules/customer/customer.module.ts
Normal file
@@ -0,0 +1,12 @@
|
||||
import { Module } from '@nestjs/common';
|
||||
import { CustomerController } from './customer.controller';
|
||||
import { CustomerService } from './customer.service';
|
||||
import { DatabaseModule } from 'src/shared/database/database.module';
|
||||
import { AuthModule } from '../auth/auth.module';
|
||||
|
||||
@Module({
|
||||
controllers: [CustomerController],
|
||||
providers: [CustomerService],
|
||||
imports: [DatabaseModule, AuthModule],
|
||||
})
|
||||
export class CustomerModule {}
|
||||
24
api/src/modules/customer/customer.service.ts
Normal file
24
api/src/modules/customer/customer.service.ts
Normal file
@@ -0,0 +1,24 @@
|
||||
import { HttpException, HttpStatus, Injectable } from '@nestjs/common';
|
||||
import { Customer } from 'src/model/entitites';
|
||||
import { IUser } from 'src/model/interface';
|
||||
import { CustomerRepository } from 'src/model/repositories';
|
||||
|
||||
@Injectable()
|
||||
export class CustomerService {
|
||||
constructor(private customerRepository: CustomerRepository) {}
|
||||
|
||||
createCustomer(user: IUser, data: any) {
|
||||
if (!user || !data.name || data.name.length == 0 || !data.system) {
|
||||
throw new HttpException('invalid', HttpStatus.UNPROCESSABLE_ENTITY);
|
||||
}
|
||||
|
||||
return this.customerRepository.save(this.customerRepository.create(data));
|
||||
}
|
||||
|
||||
getCustomers(user: IUser): Promise<Customer[]> {
|
||||
return this.customerRepository.find({
|
||||
where: { system: { managers: { id: user.id } } },
|
||||
order: { name: { direction: 'ASC' } },
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -2,6 +2,7 @@ import {
|
||||
Body,
|
||||
Controller,
|
||||
Get,
|
||||
Param,
|
||||
Post,
|
||||
Put,
|
||||
Req,
|
||||
@@ -12,6 +13,7 @@ import { AuthenticatedRequest } from 'src/model/interface/authenticated-request.
|
||||
import { AuthGuard } from 'src/core/guards/auth.guard';
|
||||
import { Key } from 'src/model/entitites';
|
||||
import { CreateKeySystemDto } from 'src/model/dto/create-key-system.dto';
|
||||
import { HandoverKeyDto } from 'src/model/dto';
|
||||
|
||||
@UseGuards(AuthGuard)
|
||||
@Controller('key')
|
||||
@@ -34,7 +36,24 @@ export class KeyController {
|
||||
}
|
||||
|
||||
@Post('system')
|
||||
createKeySystem(@Req() req: AuthenticatedRequest, @Body() body: CreateKeySystemDto) {
|
||||
createKeySystem(
|
||||
@Req() req: AuthenticatedRequest,
|
||||
@Body() body: CreateKeySystemDto,
|
||||
) {
|
||||
return this.service.createKeySystem(req.user, body);
|
||||
}
|
||||
|
||||
@Post(':id/handover')
|
||||
handoutKey(
|
||||
@Req() req: AuthenticatedRequest,
|
||||
@Body() body: any,
|
||||
@Param('id') id: string,
|
||||
) {
|
||||
return this.service.handoverKey(req.user, body, id);
|
||||
}
|
||||
|
||||
@Get(':id/handover')
|
||||
getKeyHandouts(@Req() req: AuthenticatedRequest, @Param('id') id: string) {
|
||||
return this.service.getKeyHandovers(req.user, id);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,12 +1,14 @@
|
||||
import { HttpException, HttpStatus, Injectable } from '@nestjs/common';
|
||||
import { CreateKeySystemDto } from 'src/model/dto';
|
||||
import { Cylinder, Key, User } from 'src/model/entitites';
|
||||
import { IUser } from 'src/model/interface';
|
||||
import {
|
||||
CylinderRepository,
|
||||
KeyActivityRepository,
|
||||
KeyRepository,
|
||||
KeySystemRepository,
|
||||
} from 'src/model/repositories';
|
||||
import { KeyHandoutRepository } from 'src/model/repositories/key-handout.repository';
|
||||
|
||||
@Injectable()
|
||||
export class KeyService {
|
||||
@@ -15,12 +17,13 @@ export class KeyService {
|
||||
private readonly cylinderRepository: CylinderRepository,
|
||||
private readonly systemRepo: KeySystemRepository,
|
||||
private activityRepo: KeyActivityRepository,
|
||||
private handoverRepo: KeyHandoutRepository,
|
||||
) {}
|
||||
|
||||
async getUsersKeys(user: User): Promise<Key[]> {
|
||||
return this.keyrepository.find({
|
||||
where: { cylinder: { system: { managers: { id: user.id } } } },
|
||||
relations: ['cylinder', 'cylinder.system'],
|
||||
relations: ['cylinder', 'cylinder.system', 'customer'],
|
||||
});
|
||||
}
|
||||
|
||||
@@ -74,4 +77,35 @@ export class KeyService {
|
||||
throw new HttpException(e.code, HttpStatus.UNPROCESSABLE_ENTITY);
|
||||
}
|
||||
}
|
||||
|
||||
async handoverKey(user: IUser, data: any, keyID: string) {
|
||||
const key: Key = await this.keyrepository.findOneOrFail({
|
||||
where: { id: keyID, cylinder: { system: { managers: { id: user.id } } } },
|
||||
});
|
||||
|
||||
key.handedOut = data.direction == 'out';
|
||||
this.keyrepository.save(key);
|
||||
|
||||
return this.handoverRepo.save(
|
||||
this.handoverRepo.create({
|
||||
customer: data.customer,
|
||||
direction: data.direction,
|
||||
timestamp: data.timestamp,
|
||||
key: key,
|
||||
}),
|
||||
);
|
||||
}
|
||||
|
||||
getKeyHandovers(user: User, keyID: string) {
|
||||
return this.handoverRepo.find({
|
||||
where: {
|
||||
key: { cylinder: { system: { managers: { id: user.id } } }, id: keyID },
|
||||
},
|
||||
order: {
|
||||
timestamp: { direction: 'DESC' },
|
||||
created: { direction: 'DESC' },
|
||||
},
|
||||
relations: ['customer'],
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,18 +0,0 @@
|
||||
import { Test, TestingModule } from '@nestjs/testing';
|
||||
import { RoleController } from './role.controller';
|
||||
|
||||
describe('RoleController', () => {
|
||||
let controller: RoleController;
|
||||
|
||||
beforeEach(async () => {
|
||||
const module: TestingModule = await Test.createTestingModule({
|
||||
controllers: [RoleController],
|
||||
}).compile();
|
||||
|
||||
controller = module.get<RoleController>(RoleController);
|
||||
});
|
||||
|
||||
it('should be defined', () => {
|
||||
expect(controller).toBeDefined();
|
||||
});
|
||||
});
|
||||
@@ -1,18 +0,0 @@
|
||||
import { Test, TestingModule } from '@nestjs/testing';
|
||||
import { RoleService } from './role.service';
|
||||
|
||||
describe('RoleService', () => {
|
||||
let service: RoleService;
|
||||
|
||||
beforeEach(async () => {
|
||||
const module: TestingModule = await Test.createTestingModule({
|
||||
providers: [RoleService],
|
||||
}).compile();
|
||||
|
||||
service = module.get<RoleService>(RoleService);
|
||||
});
|
||||
|
||||
it('should be defined', () => {
|
||||
expect(service).toBeDefined();
|
||||
});
|
||||
});
|
||||
@@ -1,8 +1,18 @@
|
||||
import { Module } from '@nestjs/common';
|
||||
import { TypeOrmModule } from '@nestjs/typeorm';
|
||||
import { Cylinder, Key, KeyActivity, Role, SSOUser, User } from 'src/model/entitites';
|
||||
import {
|
||||
Customer,
|
||||
Cylinder,
|
||||
Key,
|
||||
KeyActivity,
|
||||
KeyHandout,
|
||||
Role,
|
||||
SSOUser,
|
||||
User,
|
||||
} from 'src/model/entitites';
|
||||
import { KeySystem } from 'src/model/entitites/system.entity';
|
||||
import {
|
||||
CustomerRepository,
|
||||
CylinderRepository,
|
||||
KeyActivityRepository,
|
||||
KeyRepository,
|
||||
@@ -11,8 +21,19 @@ import {
|
||||
SsoUserRepository,
|
||||
UserRepository,
|
||||
} from 'src/model/repositories';
|
||||
import { KeyHandoutRepository } from 'src/model/repositories/key-handout.repository';
|
||||
|
||||
const ENTITIES = [User, SSOUser, Role, KeySystem, Key, Cylinder, KeyActivity];
|
||||
const ENTITIES = [
|
||||
User,
|
||||
SSOUser,
|
||||
Role,
|
||||
KeySystem,
|
||||
Key,
|
||||
Cylinder,
|
||||
KeyActivity,
|
||||
Customer,
|
||||
KeyHandout,
|
||||
];
|
||||
const REPOSITORIES = [
|
||||
UserRepository,
|
||||
SsoUserRepository,
|
||||
@@ -21,6 +42,8 @@ const REPOSITORIES = [
|
||||
KeyRepository,
|
||||
CylinderRepository,
|
||||
KeyActivityRepository,
|
||||
CustomerRepository,
|
||||
KeyHandoutRepository,
|
||||
];
|
||||
|
||||
@Module({
|
||||
|
||||
Reference in New Issue
Block a user