From c39a59e54ef0b1cc891684283422805af38969e3 Mon Sep 17 00:00:00 2001 From: Nicolai Ort Date: Thu, 21 Jan 2021 18:03:48 +0100 Subject: [PATCH] Implemented runner selfservice token generation ref #112 --- src/controllers/RunnerSelfServiceController.ts | 5 ++++- src/jwtcreator.ts | 14 ++++++++++++++ src/models/responses/ResponseSelfServiceRunner.ts | 10 +++++++++- 3 files changed, 27 insertions(+), 2 deletions(-) diff --git a/src/controllers/RunnerSelfServiceController.ts b/src/controllers/RunnerSelfServiceController.ts index 9c2c8bd..88de8f5 100644 --- a/src/controllers/RunnerSelfServiceController.ts +++ b/src/controllers/RunnerSelfServiceController.ts @@ -7,6 +7,7 @@ import { InvalidCredentialsError } from '../errors/AuthError'; import { RunnerEmailNeededError, RunnerNotFoundError } from '../errors/RunnerErrors'; import { RunnerGroupNotFoundError } from '../errors/RunnerGroupErrors'; import { RunnerOrganisationNotFoundError } from '../errors/RunnerOrganisationErrors'; +import { JwtCreator } from '../jwtcreator'; import { CreateSelfServiceCitizenRunner } from '../models/actions/create/CreateSelfServiceCitizenRunner'; import { CreateSelfServiceRunner } from '../models/actions/create/CreateSelfServiceRunner'; import { Runner } from '../models/entities/Runner'; @@ -58,7 +59,9 @@ export class RunnerSelfServiceController { let runner = await createRunner.toEntity(org); runner = await this.runnerRepository.save(runner); - return new ResponseSelfServiceRunner(await this.runnerRepository.findOne(runner, { relations: ['scans', 'group', 'scans.track', 'cards', 'distanceDonations', 'distanceDonations.donor', 'distanceDonations.runner', 'distanceDonations.runner.scans', 'distanceDonations.runner.scans.track'] })); + let response = new ResponseSelfServiceRunner(await this.runnerRepository.findOne(runner, { relations: ['scans', 'group', 'scans.track', 'cards', 'distanceDonations', 'distanceDonations.donor', 'distanceDonations.runner', 'distanceDonations.runner.scans', 'distanceDonations.runner.scans.track'] })); + response.token = JwtCreator.createSelfService(runner); + return response } /** diff --git a/src/jwtcreator.ts b/src/jwtcreator.ts index 0b8ff7e..15b2d13 100644 --- a/src/jwtcreator.ts +++ b/src/jwtcreator.ts @@ -1,6 +1,7 @@ import { IsBoolean, IsEmail, IsInt, IsNotEmpty, IsOptional, IsString, IsUUID } from 'class-validator'; import * as jsonwebtoken from "jsonwebtoken"; import { config } from './config'; +import { Runner } from './models/entities/Runner'; import { User } from './models/entities/User'; /** @@ -34,6 +35,19 @@ export class JwtCreator { }, config.jwt_secret) } + /** + * Creates a new selfservice token for a given runner. + * @param runner Runner entity that the access token shall be created for. + * @param expiry_timestamp Timestamp for the token expiry. Will be set about 9999 years if none provided. + */ + public static createSelfService(runner: Runner, expiry_timestamp?: number) { + if (!expiry_timestamp) { expiry_timestamp = Math.floor(Date.now() / 1000) + 36000 * 60 * 24 * 365 * 9999; } + return jsonwebtoken.sign({ + id: runner.id, + exp: expiry_timestamp + }, config.jwt_secret) + } + /** * Creates a new password reset token for a given user. * The token is valid for 15 minutes or 1 use - whatever comes first. diff --git a/src/models/responses/ResponseSelfServiceRunner.ts b/src/models/responses/ResponseSelfServiceRunner.ts index 6727c76..fa9a1f1 100644 --- a/src/models/responses/ResponseSelfServiceRunner.ts +++ b/src/models/responses/ResponseSelfServiceRunner.ts @@ -1,4 +1,4 @@ -import { IsInt, IsString } from "class-validator"; +import { IsInt, IsOptional, IsString } from "class-validator"; import { DistanceDonation } from '../entities/DistanceDonation'; import { Runner } from '../entities/Runner'; import { RunnerGroup } from '../entities/RunnerGroup'; @@ -36,6 +36,14 @@ export class ResponseSelfServiceRunner extends ResponseParticipant { @IsString() donations: ResponseSelfServiceDonation[] + /** + * The runner's self-service jwt for auth. + * Will only get delivered on registration/via email. + */ + @IsString() + @IsOptional() + token: string; + /** * Creates a ResponseRunner object from a runner. * @param runner The user the response shall be build for.