Skip to content

Commit

Permalink
feat(platform,platform-server): delete project
Browse files Browse the repository at this point in the history
  • Loading branch information
lizimeow committed Sep 13, 2022
1 parent a9f8f27 commit 4104f53
Show file tree
Hide file tree
Showing 40 changed files with 495 additions and 74 deletions.
235 changes: 235 additions & 0 deletions db/migrations/1662709646753-cascade.ts

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ export class AccessToken extends BaseEntity {
@RelationId('user')
userId!: number

@ManyToOne('User', 'accessTokens')
@ManyToOne('User', 'accessTokens', { onDelete: 'CASCADE' })
user!: User

@Field()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ export class AppVersion extends BaseEntity {
@RelationId('project')
projectId!: number

@ManyToOne('Project', 'appVersions')
@ManyToOne('Project', 'appVersions', { onDelete: 'CASCADE' })
project!: Project

@Field(() => String, { description: 'commit hash' })
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,15 +49,15 @@ export class ArtifactEntrypoint extends BaseEntity {
@PrimaryGeneratedColumn('increment')
id!: number

@ManyToOne('Project', 'artifacts')
@ManyToOne('Project', 'artifacts', { onDelete: 'CASCADE' })
project!: Project

@RelationId('project')
@Index()
@Column()
projectId!: number

@ManyToOne('Artifact', 'entrypoints')
@ManyToOne('Artifact', 'entrypoints', { onDelete: 'CASCADE' })
artifact!: Artifact

@RelationId('artifact')
Expand Down
4 changes: 2 additions & 2 deletions packages/platform-server/src/db/mysql/artifact.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ export class Artifact extends BaseEntity {
@PrimaryGeneratedColumn('increment')
id!: number

@ManyToOne('Project', 'artifacts')
@ManyToOne('Project', 'artifacts', { onDelete: 'CASCADE' })
project!: Project

@RelationId('project')
Expand Down Expand Up @@ -142,7 +142,7 @@ export class ArtifactName extends BaseEntity {
@PrimaryGeneratedColumn('increment')
id!: number

@ManyToOne('Project', 'artifacts')
@ManyToOne('Project', 'artifacts', { onDelete: 'CASCADE' })
project!: Project

@RelationId('project')
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ export class InternalId extends BaseEntity {
@RelationId('project')
projectId!: number

@ManyToOne('Project', { createForeignKeyConstraints: false })
@ManyToOne('Project', { onDelete: 'CASCADE' })
project!: Project

@Column({ type: 'tinyint' })
Expand Down
5 changes: 1 addition & 4 deletions packages/platform-server/src/db/mysql/job.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,10 +59,7 @@ export class Job extends BaseEntity {
@RelationId('project')
projectId!: number

@ManyToOne('Project', 'jobs', {
// some global jobs didn't have project
createForeignKeyConstraints: false,
})
@ManyToOne('Project', 'jobs', { onDelete: 'CASCADE' })
project!: Project

@Field(() => JobType)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ export class PageWithCompetitor extends BaseEntity {
@Index()
pageId!: number

@ManyToOne('Page')
@ManyToOne('Page', 'pageWithCompetitors', { onDelete: 'CASCADE' })
page!: Page

@Field()
Expand Down
4 changes: 2 additions & 2 deletions packages/platform-server/src/db/mysql/page-with-env.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,14 +28,14 @@ export class PageWithEnv extends BaseEntity {
@Index()
pageId!: number

@ManyToOne('Page')
@ManyToOne('Page', 'pageWithEnvs', { onDelete: 'CASCADE' })
page!: Page

@Column()
@RelationId('env')
@Index()
envId!: number

@ManyToOne('Environment')
@ManyToOne('Environment', 'pageWithEnvs', { onDelete: 'CASCADE' })
env!: Environment
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,14 +28,14 @@ export class PageWithProfile extends BaseEntity {
@Index()
pageId!: number

@ManyToOne('Page')
@ManyToOne('Page', 'pageWithProfiles', { onDelete: 'CASCADE' })
page!: Page

@Column()
@Index()
@RelationId('profile')
profileId!: number

@ManyToOne('Profile')
@ManyToOne('Profile', 'pageWithProfiles', { onDelete: 'CASCADE' })
profile!: Profile
}
6 changes: 3 additions & 3 deletions packages/platform-server/src/db/mysql/property.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ export class Page extends BaseEntity {
@RelationId('project')
projectId!: number

@ManyToOne('Project', 'pages')
@ManyToOne('Project', 'pages', { onDelete: 'CASCADE' })
project!: Project

@Field(() => Boolean, { description: 'is competitor page' })
Expand Down Expand Up @@ -108,7 +108,7 @@ export class Profile extends BaseEntity {
@Column({ default: 'no' })
bandWidth!: string

@ManyToOne('Project', 'profiles')
@ManyToOne('Project', 'profiles', { onDelete: 'CASCADE' })
project!: Project

@RelationId('project')
Expand Down Expand Up @@ -152,7 +152,7 @@ export class Environment extends BaseEntity {
@Column({ type: 'json', nullable: true })
headers!: HeaderType[]

@ManyToOne('Project', 'environments')
@ManyToOne('Project', 'environments', { onDelete: 'CASCADE' })
project!: Project

@RelationId('project')
Expand Down
2 changes: 1 addition & 1 deletion packages/platform-server/src/db/mysql/setting.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ export class Setting extends BaseEntity {
@RelationId('project')
projectId!: number

@OneToOne('Project', 'setting')
@OneToOne('Project', 'setting', { onDelete: 'CASCADE' })
@JoinColumn()
project!: Project

Expand Down
10 changes: 5 additions & 5 deletions packages/platform-server/src/db/mysql/snapshot-report.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -49,37 +49,37 @@ export class SnapshotReport extends BaseEntity {
@Column({ type: 'int' })
iid!: number

@ManyToOne('Project', 'snapshotReports')
@ManyToOne('Project', 'snapshotReports', { onDelete: 'CASCADE' })
project!: Project

@Index()
@Column()
@RelationId('project')
projectId!: number

@ManyToOne('Snapshot', 'reports')
@ManyToOne('Snapshot', 'reports', { onDelete: 'CASCADE' })
snapshot!: Snapshot

@Index()
@Column()
@RelationId('snapshot')
snapshotId!: number

@ManyToOne('Page', 'reports')
@ManyToOne('Page', 'reports', { onDelete: 'CASCADE' })
page!: Page

@RelationId('page')
@Column({ type: 'int' })
pageId!: number

@ManyToOne('Profile', 'reports')
@ManyToOne('Profile', 'reports', { onDelete: 'CASCADE' })
profile!: Profile

@RelationId('profile')
@Column({ type: 'int' })
profileId!: number

@ManyToOne('Environment', 'reports')
@ManyToOne('Environment', 'reports', { onDelete: 'CASCADE' })
env!: Environment

@RelationId('env')
Expand Down
2 changes: 1 addition & 1 deletion packages/platform-server/src/db/mysql/snapshot.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ export class Snapshot extends BaseEntity {
@PrimaryGeneratedColumn('increment')
id!: number

@ManyToOne('Project', 'snapshots')
@ManyToOne('Project', 'snapshots', { onDelete: 'CASCADE' })
project!: Project

@RelationId('project')
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ export class SourceIssue extends BaseEntity {
@RelationId('project')
projectId!: number

@ManyToOne('Project', 'sourceIssues')
@ManyToOne('Project', 'sourceIssues', { onDelete: 'CASCADE' })
project!: Project

@Field({ description: 'git commit hash' })
Expand Down
2 changes: 1 addition & 1 deletion packages/platform-server/src/db/mysql/timer.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ export class Timer extends BaseEntity {
@RelationId('project')
projectId!: number

@OneToOne('Project', 'timer')
@OneToOne('Project', 'timer', { onDelete: 'CASCADE' })
@JoinColumn()
project!: Project

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,15 +43,15 @@ export class UserPermission extends BaseEntity {
@RelationId('user')
userId!: number

@ManyToOne('User', 'permissions')
@ManyToOne('User', 'permissions', { onDelete: 'CASCADE' })
user!: User

@Column({ type: 'int' })
@Index()
@RelationId('project')
projectId!: number

@ManyToOne('Project', 'permissions')
@ManyToOne('Project', 'permissions', { onDelete: 'CASCADE' })
project!: Project

@Column({ type: 'varchar', length: 255 })
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,13 +28,13 @@ export class UserStarredProject extends BaseEntity {
@RelationId('user')
userId!: number

@ManyToOne('User')
@ManyToOne('User', 'userStarredProjects', { onDelete: 'CASCADE' })
user!: User

@Column()
@RelationId('project')
projectId!: number

@ManyToOne('Project')
@ManyToOne('Project', 'userStarredProjects', { onDelete: 'CASCADE' })
project!: Project
}
2 changes: 1 addition & 1 deletion packages/platform-server/src/modules/job/service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ export function getJobGroupNames(): JobType[] {
}

function getLogStorageKey(job: Job) {
return `logs/${job.jobType}/${job.id}.json`
return `logs/${job.projectId}/${job.jobType}/${job.id}.json`
}

const LATEST_DONE_JOB_KEY = 'LATEST_DONE_JOB_ID'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -187,3 +187,20 @@ test.serial('project owners', async (t) => {
t.is(ownersWithEmail.length, 1)
t.is(ownersWithEmail[0].username, user.username)
})

test.serial('delete project', async (t) => {
const service = t.context.module.get(ProjectService)

const projectCreated = await service.create(user, {
id: faker.internet.domainWord(),
host: GitHost.Github,
namespace: faker.internet.domainWord(),
name: faker.internet.userName(),
artifactBaselineBranch: 'master',
})
await service.deleteProject(projectCreated.id)

const project = await Project.findOneBy({ id: projectCreated.id })

t.is(project, null)
})
3 changes: 2 additions & 1 deletion packages/platform-server/src/modules/project/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ limitations under the License.
import { Module } from '@nestjs/common'

import { DBModule } from '@perfsee/platform-server/db'
import { StorageModule } from '@perfsee/platform-server/storage'

import { GithubModule } from '../github'
import { UserModule } from '../user'
Expand All @@ -25,7 +26,7 @@ import { ProjectResolver, UserProjectResolver } from './resolver'
import { ProjectService } from './service'

@Module({
imports: [DBModule, UserModule, GithubModule],
imports: [DBModule, UserModule, GithubModule, StorageModule],
providers: [ProjectService, ProjectResolver, UserProjectResolver],
exports: [ProjectService],
})
Expand Down
11 changes: 11 additions & 0 deletions packages/platform-server/src/modules/project/resolver.ts
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,17 @@ export class ProjectResolver {
async owners(@Parent() project: Project) {
return this.projectService.getProjectOwners(project)
}

@Mutation(() => Boolean, {
description: 'Delete project with given id. NOTE: all data in this project will be deleted.',
})
@PermissionGuard(Permission.Admin, 'projectId')
async deleteProject(@Args({ name: 'projectId', type: () => ID }) slug: string) {
const projectRawId = await this.projectService.resolveRawProjectIdBySlug(slug)
await this.projectService.deleteProject(projectRawId)

return true
}
}

@Resolver(() => User)
Expand Down
20 changes: 20 additions & 0 deletions packages/platform-server/src/modules/project/service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,9 @@ import {
import { mapInternalError, UserError } from '@perfsee/platform-server/error'
import { PaginationInput } from '@perfsee/platform-server/graphql'
import { InternalIdService } from '@perfsee/platform-server/helpers'
import { Logger } from '@perfsee/platform-server/logger'
import { Metric } from '@perfsee/platform-server/metrics'
import { ObjectStorage } from '@perfsee/platform-server/storage'
import { createDataLoader } from '@perfsee/platform-server/utils'
import { GitHost } from '@perfsee/shared'

Expand All @@ -60,6 +62,8 @@ export class ProjectService {
private readonly metricService: Metric,
private readonly internalIdService: InternalIdService,
private readonly config: Config,
private readonly logger: Logger,
private readonly storage: ObjectStorage,
) {}

async resolveRawProjectIdBySlug(slug: string) {
Expand Down Expand Up @@ -354,6 +358,22 @@ export class ProjectService {
}
}

async deleteProject(projectId: number) {
this.logger.log('start delete project', { projectId })
await Project.delete({ id: projectId })

setImmediate(() => {
void this.deleteFolders(projectId)
})

return true
}

private async deleteFolders(projectId: number) {
await this.storage.deleteFolder(`logs/${projectId}`)
await this.storage.deleteFolder(`artifacts/${projectId}`)
}

private async getActiveProjectCountByPeriod(value: number, period: 'DAY' | 'WEEK' | 'MONTH') {
return Job.createQueryBuilder()
.select('count(distinct project_id) as count')
Expand Down
2 changes: 2 additions & 0 deletions packages/platform-server/src/modules/snapshot/service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ import {
Project,
Profile,
SnapshotTrigger,
AppVersion,
} from '@perfsee/platform-server/db'
import { UserError } from '@perfsee/platform-server/error'
import { EventEmitter, OnEvent } from '@perfsee/platform-server/event'
Expand Down Expand Up @@ -257,6 +258,7 @@ export class SnapshotService implements OnApplicationBootstrap {
const { id } = snapshot

await this.db.transaction(async (manager) => {
await manager.getRepository(AppVersion).delete({ snapshotId: id })
await this.reportService.deleteSnapshotsReports(manager, { snapshotId: id })
await manager.remove(snapshot)
})
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,7 @@ export class SnapshotReportService {
const reports = await SnapshotReport.findBy(conditions)
const reportIds = reports.map(({ id }) => id)

this.logger.log('start delete page', { count: reportIds.length })
this.logger.log('start delete snapshot report', { conditions, count: reportIds.length })

// delete reports slowly in case too many reports
for (let i = 0; i < Math.ceil(reportIds.length / 30); i++) {
Expand Down

0 comments on commit 4104f53

Please sign in to comment.