Migrate to a monorepo structure (#2909)

This commit is contained in:
Charles Bochet
2023-12-10 18:10:54 +01:00
committed by GitHub
parent a70a9281eb
commit 5bdca9de6c
2304 changed files with 37152 additions and 25869 deletions

View File

@ -0,0 +1,9 @@
import { ObjectType, Field } from '@nestjs/graphql';
@ObjectType()
export class Analytics {
@Field(() => Boolean, {
description: 'Boolean that confirms query was dispatched',
})
success: boolean;
}

View File

@ -0,0 +1,9 @@
import { Module } from '@nestjs/common';
import { AnalyticsService } from './analytics.service';
import { AnalyticsResolver } from './analytics.resolver';
@Module({
providers: [AnalyticsResolver, AnalyticsService],
})
export class AnalyticsModule {}

View File

@ -0,0 +1,29 @@
import { Test, TestingModule } from '@nestjs/testing';
import { EnvironmentService } from 'src/integrations/environment/environment.service';
import { AnalyticsResolver } from './analytics.resolver';
import { AnalyticsService } from './analytics.service';
describe('AnalyticsResolver', () => {
let resolver: AnalyticsResolver;
beforeEach(async () => {
const module: TestingModule = await Test.createTestingModule({
providers: [
AnalyticsResolver,
AnalyticsService,
{
provide: EnvironmentService,
useValue: {},
},
],
}).compile();
resolver = module.get<AnalyticsResolver>(AnalyticsResolver);
});
it('should be defined', () => {
expect(resolver).toBeDefined();
});
});

View File

@ -0,0 +1,28 @@
import { Resolver, Mutation, Args } from '@nestjs/graphql';
import { UseGuards } from '@nestjs/common';
import { OptionalJwtAuthGuard } from 'src/guards/optional-jwt.auth.guard';
import { AuthWorkspace } from 'src/decorators/auth-workspace.decorator';
import { AuthUser } from 'src/decorators/auth-user.decorator';
import { Workspace } from 'src/core/workspace/workspace.entity';
import { User } from 'src/core/user/user.entity';
import { AnalyticsService } from './analytics.service';
import { Analytics } from './analytics.entity';
import { CreateAnalyticsInput } from './dto/create-analytics.input';
@UseGuards(OptionalJwtAuthGuard)
@Resolver(() => Analytics)
export class AnalyticsResolver {
constructor(private readonly analyticsService: AnalyticsService) {}
@Mutation(() => Analytics)
createEvent(
@Args() createEventInput: CreateAnalyticsInput,
@AuthWorkspace() workspace: Workspace | undefined,
@AuthUser() user: User | undefined,
) {
return this.analyticsService.create(createEventInput, user, workspace);
}
}

View File

@ -0,0 +1,27 @@
import { Test, TestingModule } from '@nestjs/testing';
import { EnvironmentService } from 'src/integrations/environment/environment.service';
import { AnalyticsService } from './analytics.service';
describe('AnalyticsService', () => {
let service: AnalyticsService;
beforeEach(async () => {
const module: TestingModule = await Test.createTestingModule({
providers: [
AnalyticsService,
{
provide: EnvironmentService,
useValue: {},
},
],
}).compile();
service = module.get<AnalyticsService>(AnalyticsService);
});
it('should be defined', () => {
expect(service).toBeDefined();
});
});

View File

@ -0,0 +1,58 @@
import { Injectable } from '@nestjs/common';
import axios, { AxiosInstance } from 'axios';
import { anonymize } from 'src/utils/anonymize';
import { EnvironmentService } from 'src/integrations/environment/environment.service';
import { User } from 'src/core/user/user.entity';
import { Workspace } from 'src/core/workspace/workspace.entity';
import { CreateAnalyticsInput } from './dto/create-analytics.input';
@Injectable()
export class AnalyticsService {
private readonly httpService: AxiosInstance;
constructor(private readonly environmentService: EnvironmentService) {
this.httpService = axios.create({
baseURL: 'https://t.twenty.com/api/v1/s2s',
});
}
async create(
createEventInput: CreateAnalyticsInput,
user: User | undefined,
workspace: Workspace | undefined,
) {
if (!this.environmentService.isTelemetryEnabled()) {
return { success: true };
}
const anonymizationEnabled =
this.environmentService.isTelemetryAnonymizationEnabled();
const data = {
type: createEventInput.type,
data: {
userUUID: user
? anonymizationEnabled
? anonymize(user.id)
: user.id
: undefined,
workspaceUUID: workspace
? anonymizationEnabled
? anonymize(workspace.id)
: workspace.id
: undefined,
workspaceDomain: workspace ? workspace.domainName : undefined,
...createEventInput.data,
},
};
try {
await this.httpService.post('/event?noToken', data);
} catch {}
return { success: true };
}
}

View File

@ -0,0 +1,16 @@
import { ArgsType, Field } from '@nestjs/graphql';
import graphqlTypeJson from 'graphql-type-json';
import { IsNotEmpty, IsString, IsObject } from 'class-validator';
@ArgsType()
export class CreateAnalyticsInput {
@Field({ description: 'Type of the event' })
@IsNotEmpty()
@IsString()
type: string;
@Field(() => graphqlTypeJson, { description: 'Event data in JSON format' })
@IsObject()
data: JSON;
}