Skip to content

Commit

Permalink
feat: added venues back-end #78
Browse files Browse the repository at this point in the history
  • Loading branch information
rbento1096 committed Feb 17, 2024
1 parent ff6f620 commit 86ad0af
Show file tree
Hide file tree
Showing 4 changed files with 289 additions and 1 deletion.
6 changes: 5 additions & 1 deletion back-end/deploy/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,8 @@ const apiResources: ResourceController[] = [
{ name: 'configurations', paths: ['/configurations'] },
{ name: 'users', paths: ['/users', '/users/{userId}'] },
{ name: 'eventSpots', paths: ['/event-spots', '/event-spots/{spotId}'] },
{ name: 'usefulLinks', paths: ['/useful-links', '/useful-links/{linkId}'] }
{ name: 'usefulLinks', paths: ['/useful-links', '/useful-links/{linkId}'] },
{ name: 'venues', paths: ['/venues', '/venues/{venueId}'] }
];

const tables: { [tableName: string]: DDBTable } = {
Expand All @@ -42,6 +43,9 @@ const tables: { [tableName: string]: DDBTable } = {
},
usefulLinks: {
PK: { name: 'linkId', type: DDB.AttributeType.STRING }
},
venues: {
PK: { name: 'venueId', type: DDB.AttributeType.STRING }
}
};

Expand Down
105 changes: 105 additions & 0 deletions back-end/src/handlers/venues.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
///
/// IMPORTS
///

import { DynamoDB, RCError, ResourceController } from 'idea-aws';

import { Venue } from '../models/venue.model';
import { User } from '../models/user.model';

///
/// CONSTANTS, ENVIRONMENT VARIABLES, HANDLER
///

const PROJECT = process.env.PROJECT;

const DDB_TABLES = { users: process.env.DDB_TABLE_users, venues: process.env.DDB_TABLE_venues };

const ddb = new DynamoDB();

export const handler = (ev: any, _: any, cb: any) => new Venues(ev, cb).handleRequest();

///
/// RESOURCE CONTROLLER
///

class Venues extends ResourceController {
user: User;
venue: Venue;

constructor(event: any, callback: any) {
super(event, callback, { resourceId: 'venueId' });
}

protected async checkAuthBeforeRequest(): Promise<void> {
try {
this.user = new User(await ddb.get({ TableName: DDB_TABLES.users, Key: { userId: this.principalId } }));
} catch (err) {
throw new RCError('User not found');
}

if (!this.resourceId) return;

try {
this.venue = new Venue(await ddb.get({ TableName: DDB_TABLES.venues, Key: { venueId: this.resourceId } }));
} catch (err) {
throw new RCError('Venue not found');
}
}

protected async getResource(): Promise<Venue> {
return this.venue;
}

protected async putResource(): Promise<Venue> {
if (!this.user.permissions.canManageContents) throw new RCError('Unauthorized');

const oldResource = new Venue(this.venue);
this.venue.safeLoad(this.body, oldResource);

return await this.putSafeResource();
}
private async putSafeResource(opts: { noOverwrite?: boolean } = {}): Promise<Venue> {
const errors = this.venue.validate();
if (errors.length) throw new RCError(`Invalid fields: ${errors.join(', ')}`);

try {
const putParams: any = { TableName: DDB_TABLES.venues, Item: this.venue };
if (opts.noOverwrite) putParams.ConditionExpression = 'attribute_not_exists(venueId)';
await ddb.put(putParams);

return this.venue;
} catch (err) {
throw new RCError('Operation failed');
}
}

protected async deleteResource(): Promise<void> {
if (!this.user.permissions.canManageContents) throw new RCError('Unauthorized');

try {
await ddb.delete({ TableName: DDB_TABLES.venues, Key: { venueId: this.resourceId } });
} catch (err) {
throw new RCError('Delete failed');
}
}

protected async postResources(): Promise<Venue> {
if (!this.user.permissions.canManageContents) throw new RCError('Unauthorized');

this.venue = new Venue(this.body);
this.venue.venueId = await ddb.IUNID(PROJECT);

return await this.putSafeResource({ noOverwrite: true });
}

protected async getResources(): Promise<Venue[]> {
try {
return (await ddb.scan({ TableName: DDB_TABLES.venues }))
.map((x: Venue) => new Venue(x))
.sort((a, b) => a.name.localeCompare(b.name));
} catch (err) {
throw new RCError('Operation failed');
}
}
}
70 changes: 70 additions & 0 deletions back-end/src/models/venue.model.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
import { Resource, isEmpty } from 'idea-toolbox';

export class Venue extends Resource {
/**
* The ID of the venue.
*/
venueId: string;
/**
* The name of the venue.
*/
name: string;
/**
* The image URI for a picture of the venue.
*/
imageURI: string;
/**
* The venue's address.
*/
address: string;
/**
* A description of the venue.
*/
description: string;
/**
* The venue's longitude coordinates.
*/
longitude: number;
/**
* The venue's latitude coordinates.
*/
latitude: number;

static getCoordinates(venue: Venue): [number, number] {
return [venue.longitude, venue.latitude];
}

load(x: any): void {
super.load(x);
this.venueId = this.clean(x.venueId, String);
this.name = this.clean(x.name, String);
this.imageURI = this.clean(x.imageURI, String);
this.address = this.clean(x.address, String);
this.description = this.clean(x.description, String);
this.longitude = this.clean(x.longitude, Number);
this.latitude = this.clean(x.latitude, Number);
}
safeLoad(newData: any, safeData: any): void {
super.safeLoad(newData, safeData);
this.venueId = safeData.venueId;
}
validate(): string[] {
const e = super.validate();
if (isEmpty(this.name)) e.push('name');
if (isEmpty(this.address)) e.push('address');
if (isEmpty(this.longitude)) e.push('longitude');
if (isEmpty(this.latitude)) e.push('latitude');
return e;
}
}

export class VenueLinked extends Resource {
venueId: string;
name: string;

load(x: any): void {
super.load(x);
this.venueId = this.clean(x.venueId, String);
this.name = this.clean(x.name, String);
}
}
109 changes: 109 additions & 0 deletions back-end/swagger.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@ tags:
description: The event-related actions
- name: UsefulLinks
description: The useful links available to the users to explore more contents
- name: Venues
description: The venues of the event

paths:
/status:
Expand Down Expand Up @@ -477,6 +479,89 @@ paths:
$ref: '#/components/responses/OperationCompleted'
400:
$ref: '#/components/responses/BadParameters'
/venues:
get:
summary: Get the venues
tags: [Venues]
security:
- AuthFunction: []
responses:
200:
$ref: '#/components/responses/Venues'
post:
summary: Insert a new venue
description: Requires to be content manager
tags: [Venues]
security:
- AuthFunction: []
requestBody:
required: true
description: Venue
content:
application/json:
schema:
type: object
responses:
200:
$ref: '#/components/responses/Venue'
400:
$ref: '#/components/responses/BadParameters'
/venues/{venueId}:
get:
summary: Get a venue
tags: [Venues]
security:
- AuthFunction: []
parameters:
- name: venueId
in: path
required: true
schema:
type: string
responses:
200:
$ref: '#/components/responses/Venue'
put:
summary: Edit a venue
description: Requires to be content manager
tags: [Venues]
security:
- AuthFunction: []
parameters:
- name: venueId
in: path
required: true
schema:
type: string
requestBody:
required: true
description: Venue
content:
application/json:
schema:
type: object
responses:
200:
$ref: '#/components/responses/Venue'
400:
$ref: '#/components/responses/BadParameters'
delete:
summary: Delete a venue
description: Requires to be content manager
tags: [Venues]
security:
- AuthFunction: []
parameters:
- name: venueId
in: path
required: true
schema:
type: string
responses:
200:
$ref: '#/components/responses/OperationCompleted'
400:
$ref: '#/components/responses/BadParameters'

components:
schemas:
Expand All @@ -495,6 +580,15 @@ components:
UsefulLink:
type: object
additionalProperties: {}
Venue:
type: object
additionalProperties: {}
Communication:
type: object
additionalProperties: {}
Organization:
type: object
additionalProperties: {}

responses:
AppStatus:
Expand Down Expand Up @@ -556,6 +650,21 @@ components:
type: array
items:
$ref: '#/components/schemas/UsefulLink'
Venue:
description: Venue
content:
application/json:
schema:
type: object
$ref: '#/components/schemas/Venue'
Venues:
description: Venue[]
content:
application/json:
schema:
type: array
items:
$ref: '#/components/schemas/Venue'
BadParameters:
description: Bad input parameters
content:
Expand Down

0 comments on commit 86ad0af

Please sign in to comment.