Skip to content

Commit

Permalink
feat: class fetching and caching
Browse files Browse the repository at this point in the history
  • Loading branch information
bddvlpr committed Sep 3, 2023
1 parent eba2e9a commit 39c79a3
Show file tree
Hide file tree
Showing 11 changed files with 287 additions and 3 deletions.
5 changes: 4 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -20,13 +20,16 @@
"test:e2e": "jest --config ./test/jest-e2e.json"
},
"dependencies": {
"@nestjs/cache-manager": "^2.1.0",
"@nestjs/common": "^9.0.0",
"@nestjs/core": "^9.0.0",
"@nestjs/platform-express": "^9.0.0",
"@nestjs/swagger": "^7.1.10",
"cache-manager": "^5.2.3",
"helmet": "^7.0.0",
"reflect-metadata": "^0.1.13",
"rxjs": "^7.2.0"
"rxjs": "^7.2.0",
"webuntis": "^2.0.3"
},
"devDependencies": {
"@nestjs/cli": "^9.0.0",
Expand Down
9 changes: 8 additions & 1 deletion src/app.module.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,13 @@
import { Module } from '@nestjs/common';
import { UntisModule } from './untis/untis.module';
import { ClassesModule } from './classes/classes.module';
import { CacheModule } from '@nestjs/cache-manager';

@Module({
imports: [],
imports: [
CacheModule.register({ isGlobal: true }),
UntisModule,
ClassesModule,
],
})
export class AppModule {}
18 changes: 18 additions & 0 deletions src/classes/classes.controller.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import { Test, TestingModule } from '@nestjs/testing';
import { ClassesController } from './classes.controller';

describe('ClassesController', () => {
let controller: ClassesController;

beforeEach(async () => {
const module: TestingModule = await Test.createTestingModule({
controllers: [ClassesController],
}).compile();

controller = module.get<ClassesController>(ClassesController);
});

it('should be defined', () => {
expect(controller).toBeDefined();
});
});
49 changes: 49 additions & 0 deletions src/classes/classes.controller.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
import { CacheInterceptor } from '@nestjs/cache-manager';
import {
CacheTTL,
Controller,
Get,
HttpException,
HttpStatus,
Param,
ParseIntPipe,
UseInterceptors,
} from '@nestjs/common';
import { ApiNotFoundResponse, ApiOkResponse, ApiTags } from '@nestjs/swagger';
import { UntisService } from 'src/untis/untis.service';
import { GetClassDto } from './dto/get-class.dto';

@ApiTags('classes')
@UseInterceptors(CacheInterceptor)
@CacheTTL(30)
@Controller('classes')
export class ClassesController {
constructor(private readonly untisService: UntisService) {}

@ApiOkResponse({
description:
'The classes of the (currently latest) schoolyear are returned.',
type: [GetClassDto],
})
@Get()
async getClasses() {
return await this.untisService.fetchClasses();
}

@ApiOkResponse({
description: 'The requested class is returned.',
type: GetClassDto,
})
@ApiNotFoundResponse({ description: 'The requested class was not found.' })
@Get(':id')
async getClass(@Param('id', ParseIntPipe) id: number) {
const targetClass = (await this.untisService.fetchClasses()).find(
(c) => c.id === id,
);

if (!targetClass)
throw new HttpException('Class not found.', HttpStatus.NOT_FOUND);

return targetClass;
}
}
9 changes: 9 additions & 0 deletions src/classes/classes.module.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
import { Module } from '@nestjs/common';
import { UntisModule } from 'src/untis/untis.module';
import { ClassesController } from './classes.controller';

@Module({
controllers: [ClassesController],
imports: [UntisModule],
})
export class ClassesModule {}
21 changes: 21 additions & 0 deletions src/classes/dto/get-class.dto.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import { ApiProperty, ApiPropertyOptional } from '@nestjs/swagger';

export class GetClassDto {
@ApiProperty()
id: number;

@ApiProperty()
name: string;

@ApiProperty()
longName: string;

@ApiProperty()
did: number;

@ApiPropertyOptional()
foreColor: string;

@ApiPropertyOptional()
backColor: string;
}
8 changes: 8 additions & 0 deletions src/untis/untis.module.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import { Module } from '@nestjs/common';
import { UntisService } from './untis.service';

@Module({
providers: [UntisService],
exports: [UntisService],
})
export class UntisModule {}
18 changes: 18 additions & 0 deletions src/untis/untis.service.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import { Test, TestingModule } from '@nestjs/testing';
import { UntisService } from './untis.service';

describe('UntisService', () => {
let service: UntisService;

beforeEach(async () => {
const module: TestingModule = await Test.createTestingModule({
providers: [UntisService],
}).compile();

service = module.get<UntisService>(UntisService);
});

it('should be defined', () => {
expect(service).toBeDefined();
});
});
35 changes: 35 additions & 0 deletions src/untis/untis.service.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import { Injectable, Logger } from '@nestjs/common';
import { WebUntis } from 'webuntis';

@Injectable()
export class UntisService {
private readonly logger = new Logger(UntisService.name);

client: WebUntis;

constructor() {
this.client = new WebUntis();
// TODO: Environment loading
}

async validateSession() {
if (!(await this.client.validateSession())) {
this.logger.debug('Session is invalid. Renewing now...');
await this.client.login();
}
}

async fetchLatestSchoolyear() {
await this.validateSession();

return this.client.getLatestSchoolyear();
}

async fetchClasses(schoolyearId?: number) {
await this.validateSession();

if (!schoolyearId) schoolyearId = (await this.fetchLatestSchoolyear()).id;
this.logger.log(`Fetching classes for schoolyear ${schoolyearId}...`);
return this.client.getClasses(false, schoolyearId);
}
}
1 change: 0 additions & 1 deletion tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@
"baseUrl": "./",
"incremental": true,
"skipLibCheck": true,
"strict": true,
"strictNullChecks": false,
"noImplicitAny": false,
"strictBindCallApply": false,
Expand Down
Loading

0 comments on commit 39c79a3

Please sign in to comment.