import { HttpStatusCode } from '@standardnotes/responses' import { Role } from '@standardnotes/security' import { BaseHttpController, results } from 'inversify-express-utils' import { Request, Response } from 'express' import { ControllerContainerInterface, MapperInterface } from '@standardnotes/domain-core' import { Revision } from '../../../Domain/Revision/Revision' import { RevisionMetadata } from '../../../Domain/Revision/RevisionMetadata' import { DeleteRevision } from '../../../Domain/UseCase/DeleteRevision/DeleteRevision' import { GetRevision } from '../../../Domain/UseCase/GetRevision/GetRevision' import { GetRevisionsMetada } from '../../../Domain/UseCase/GetRevisionsMetada/GetRevisionsMetada' import { RevisionHttpRepresentation } from '../../../Mapping/Http/RevisionHttpRepresentation' import { RevisionMetadataHttpRepresentation } from '../../../Mapping/Http/RevisionMetadataHttpRepresentation' import { TriggerTransitionFromPrimaryToSecondaryDatabaseForUser } from '../../../Domain/UseCase/Transition/TriggerTransitionFromPrimaryToSecondaryDatabaseForUser/TriggerTransitionFromPrimaryToSecondaryDatabaseForUser' export class BaseRevisionsController extends BaseHttpController { constructor( protected getRevisionsMetadata: GetRevisionsMetada, protected doGetRevision: GetRevision, protected doDeleteRevision: DeleteRevision, protected revisionHttpMapper: MapperInterface, protected revisionMetadataHttpMapper: MapperInterface, protected triggerTransitionFromPrimaryToSecondaryDatabaseForUser: TriggerTransitionFromPrimaryToSecondaryDatabaseForUser, private controllerContainer?: ControllerContainerInterface, ) { super() if (this.controllerContainer !== undefined) { this.controllerContainer.register('revisions.revisions.getRevisions', this.getRevisions.bind(this)) this.controllerContainer.register('revisions.revisions.getRevision', this.getRevision.bind(this)) this.controllerContainer.register('revisions.revisions.deleteRevision', this.deleteRevision.bind(this)) this.controllerContainer.register('revisions.revisions.transition', this.transition.bind(this)) } } async getRevisions(request: Request, response: Response): Promise { const revisionMetadataOrError = await this.getRevisionsMetadata.execute({ itemUuid: request.params.itemUuid, userUuid: response.locals.user.uuid, roleNames: response.locals.roles.map((role: Role) => role.name), sharedVaultUuids: response.locals.belongsToSharedVaults.map( (association: { shared_vault_uuid: string; permission: string }) => association.shared_vault_uuid, ), }) if (revisionMetadataOrError.isFailed()) { return this.json( { error: { message: 'Could not retrieve revisions.', }, }, HttpStatusCode.BadRequest, ) } const revisions = revisionMetadataOrError.getValue() return this.json({ revisions: revisions.map((revision) => this.revisionMetadataHttpMapper.toProjection(revision)), }) } async getRevision(request: Request, response: Response): Promise { const revisionOrError = await this.doGetRevision.execute({ revisionUuid: request.params.uuid, userUuid: response.locals.user.uuid, roleNames: response.locals.roles.map((role: Role) => role.name), }) if (revisionOrError.isFailed()) { return this.json( { error: { message: 'Could not retrieve revision.', }, }, HttpStatusCode.BadRequest, ) } return this.json({ revision: this.revisionHttpMapper.toProjection(revisionOrError.getValue()), }) } async deleteRevision(request: Request, response: Response): Promise { const revisionOrError = await this.doDeleteRevision.execute({ revisionUuid: request.params.uuid, userUuid: response.locals.user.uuid, roleNames: response.locals.roles.map((role: Role) => role.name), }) if (revisionOrError.isFailed()) { return this.json( { error: { message: 'Could not delete revision.', }, }, HttpStatusCode.BadRequest, ) } return this.json({ message: revisionOrError.getValue(), }) } async transition(_request: Request, response: Response): Promise { const result = await this.triggerTransitionFromPrimaryToSecondaryDatabaseForUser.execute({ userUuid: response.locals.user.uuid, }) if (result.isFailed()) { return this.json( { error: { message: result.getError() }, }, 400, ) } response.setHeader('x-invalidate-cache', response.locals.user.uuid) return this.json({ success: true }) } }