diff --git a/packages/analytics/src/Bootstrap/Container.ts b/packages/analytics/src/Bootstrap/Container.ts index 9d4d24b23..2180d4d37 100644 --- a/packages/analytics/src/Bootstrap/Container.ts +++ b/packages/analytics/src/Bootstrap/Container.ts @@ -32,6 +32,7 @@ import { AnalyticsEntityRepositoryInterface } from '../Domain/Entity/AnalyticsEn import { MySQLAnalyticsEntityRepository } from '../Infra/MySQL/MySQLAnalyticsEntityRepository' import { Repository } from 'typeorm' import { AnalyticsEntity } from '../Domain/Entity/AnalyticsEntity' +import { GetUserAnalyticsId } from '../Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsId' // eslint-disable-next-line @typescript-eslint/no-var-requires const newrelicFormatter = require('@newrelic/winston-enricher') @@ -111,6 +112,7 @@ export class ContainerConfigLoader { .toConstantValue(AppDataSource.getRepository(AnalyticsEntity)) // Use Case + container.bind(TYPES.GetUserAnalyticsId).to(GetUserAnalyticsId) // Hanlders diff --git a/packages/analytics/src/Bootstrap/Types.ts b/packages/analytics/src/Bootstrap/Types.ts index 6b4f2bf6d..a8f949b60 100644 --- a/packages/analytics/src/Bootstrap/Types.ts +++ b/packages/analytics/src/Bootstrap/Types.ts @@ -16,6 +16,7 @@ const TYPES = { // ORM ORMAnalyticsEntityRepository: Symbol.for('ORMAnalyticsEntityRepository'), // Use Case + GetUserAnalyticsId: Symbol.for('GetUserAnalyticsId'), // Handlers // Services DomainEventPublisher: Symbol.for('DomainEventPublisher'), diff --git a/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsId.spec.ts b/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsId.spec.ts new file mode 100644 index 000000000..c0ecc2fe0 --- /dev/null +++ b/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsId.spec.ts @@ -0,0 +1,37 @@ +import 'reflect-metadata' + +import { AnalyticsEntity } from '../../Entity/AnalyticsEntity' +import { AnalyticsEntityRepositoryInterface } from '../../Entity/AnalyticsEntityRepositoryInterface' + +import { GetUserAnalyticsId } from './GetUserAnalyticsId' + +describe('GetUserAnalyticsId', () => { + let analyticsEntityRepository: AnalyticsEntityRepositoryInterface + let analyticsEntity: AnalyticsEntity + + const createUseCase = () => new GetUserAnalyticsId(analyticsEntityRepository) + + beforeEach(() => { + analyticsEntity = { id: 123 } as jest.Mocked + + analyticsEntityRepository = {} as jest.Mocked + analyticsEntityRepository.findOneByUserUuid = jest.fn().mockReturnValue(analyticsEntity) + }) + + it('should return analytics id for a user', async () => { + expect(await createUseCase().execute({ userUuid: '1-2-3' })).toEqual({ analyticsId: 123 }) + }) + + it('should throw error if user is missing analytics entity', async () => { + analyticsEntityRepository.findOneByUserUuid = jest.fn().mockReturnValue(null) + let error = null + + try { + await createUseCase().execute({ userUuid: '1-2-3' }) + } catch (caughtError) { + error = caughtError + } + + expect(error).not.toBeNull() + }) +}) diff --git a/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsId.ts b/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsId.ts new file mode 100644 index 000000000..d3391d4be --- /dev/null +++ b/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsId.ts @@ -0,0 +1,25 @@ +import { inject, injectable } from 'inversify' +import TYPES from '../../../Bootstrap/Types' +import { AnalyticsEntityRepositoryInterface } from '../../Entity/AnalyticsEntityRepositoryInterface' +import { UseCaseInterface } from '../UseCaseInterface' +import { GetUserAnalyticsIdDTO } from './GetUserAnalyticsIdDTO' +import { GetUserAnalyticsIdResponse } from './GetUserAnalyticsIdResponse' + +@injectable() +export class GetUserAnalyticsId implements UseCaseInterface { + constructor( + @inject(TYPES.AnalyticsEntityRepository) private analyticsEntityRepository: AnalyticsEntityRepositoryInterface, + ) {} + + async execute(dto: GetUserAnalyticsIdDTO): Promise { + const analyticsEntity = await this.analyticsEntityRepository.findOneByUserUuid(dto.userUuid) + + if (analyticsEntity === null) { + throw new Error(`Could not find analytics entity for user ${dto.userUuid}`) + } + + return { + analyticsId: analyticsEntity.id, + } + } +} diff --git a/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsIdDTO.ts b/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsIdDTO.ts new file mode 100644 index 000000000..19c054e8f --- /dev/null +++ b/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsIdDTO.ts @@ -0,0 +1,5 @@ +import { Uuid } from '@standardnotes/common' + +export type GetUserAnalyticsIdDTO = { + userUuid: Uuid +} diff --git a/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsIdResponse.ts b/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsIdResponse.ts new file mode 100644 index 000000000..4eedb6f23 --- /dev/null +++ b/packages/analytics/src/Domain/UseCase/GetUserAnalyticsId/GetUserAnalyticsIdResponse.ts @@ -0,0 +1,3 @@ +export type GetUserAnalyticsIdResponse = { + analyticsId: number +} diff --git a/packages/analytics/src/Domain/UseCase/UseCaseInterface.ts b/packages/analytics/src/Domain/UseCase/UseCaseInterface.ts new file mode 100644 index 000000000..7c8405a9a --- /dev/null +++ b/packages/analytics/src/Domain/UseCase/UseCaseInterface.ts @@ -0,0 +1,3 @@ +export interface UseCaseInterface { + execute(...args: any[]): Promise> +}