Skip to content

Commit

Permalink
Make users the joinTable for reef ManyToMany relationship
Browse files Browse the repository at this point in the history
  • Loading branch information
avalmas-programize committed Sep 10, 2020
1 parent 7b74822 commit 28deadb
Show file tree
Hide file tree
Showing 5 changed files with 45 additions and 45 deletions.
16 changes: 8 additions & 8 deletions packages/api/migration/1599586648784-ReefAdminManyToMany.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,29 +9,29 @@ export class ReefAdminManyToMany1599586648784 implements MigrationInterface {
);
await queryRunner.query(
`
CREATE TABLE "reef_admins_users" (
CREATE TABLE "users_administered_reefs_reef" (
"reef_id" integer NOT NULL,
"users_id" integer NOT NULL,
CONSTRAINT "PK_21f162e26e837a19d1e1accd1cd" PRIMARY KEY ("reef_id", "users_id")
)
`,
);
await queryRunner.query(
`CREATE INDEX "IDX_088a629ef23eb9eba6ac857ed6" ON "reef_admins_users" ("reef_id") `,
`CREATE INDEX "IDX_088a629ef23eb9eba6ac857ed6" ON "users_administered_reefs_reef" ("reef_id") `,
);
await queryRunner.query(
`CREATE INDEX "IDX_da52b9542bf7df43f4840ae439" ON "reef_admins_users" ("users_id") `,
`CREATE INDEX "IDX_da52b9542bf7df43f4840ae439" ON "users_administered_reefs_reef" ("users_id") `,
);
await queryRunner.query(`ALTER TABLE "reef" DROP COLUMN "admin_id"`);
await queryRunner.query(
`
ALTER TABLE "reef_admins_users" ADD CONSTRAINT "FK_088a629ef23eb9eba6ac857ed62"
ALTER TABLE "users_administered_reefs_reef" ADD CONSTRAINT "FK_088a629ef23eb9eba6ac857ed62"
FOREIGN KEY ("reef_id") REFERENCES "reef"("id") ON DELETE CASCADE ON UPDATE NO ACTION
`,
);
await queryRunner.query(
`
ALTER TABLE "reef_admins_users" ADD CONSTRAINT "FK_da52b9542bf7df43f4840ae4394"
ALTER TABLE "users_administered_reefs_reef" ADD CONSTRAINT "FK_da52b9542bf7df43f4840ae4394"
FOREIGN KEY ("users_id") REFERENCES "users"("id") ON DELETE CASCADE ON UPDATE NO ACTION
`,
);
Expand All @@ -48,15 +48,15 @@ export class ReefAdminManyToMany1599586648784 implements MigrationInterface {

public async down(queryRunner: QueryRunner): Promise<void> {
await queryRunner.query(
`ALTER TABLE "reef_admins_users" DROP CONSTRAINT "FK_da52b9542bf7df43f4840ae4394"`,
`ALTER TABLE "users_administered_reefs_reef" DROP CONSTRAINT "FK_da52b9542bf7df43f4840ae4394"`,
);
await queryRunner.query(
`ALTER TABLE "reef_admins_users" DROP CONSTRAINT "FK_088a629ef23eb9eba6ac857ed62"`,
`ALTER TABLE "users_administered_reefs_reef" DROP CONSTRAINT "FK_088a629ef23eb9eba6ac857ed62"`,
);
await queryRunner.query(`ALTER TABLE "reef" ADD "admin_id" integer`);
await queryRunner.query(`DROP INDEX "IDX_da52b9542bf7df43f4840ae439"`);
await queryRunner.query(`DROP INDEX "IDX_088a629ef23eb9eba6ac857ed6"`);
await queryRunner.query(`DROP TABLE "reef_admins_users"`);
await queryRunner.query(`DROP TABLE "users_administered_reefs_reef"`);
await queryRunner.query(
`
ALTER TABLE "reef" ADD CONSTRAINT "FK_dc56bfd6bfcd1f221ec83885294"
Expand Down
4 changes: 1 addition & 3 deletions packages/api/src/reefs/reefs.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ import {
OneToOne,
OneToMany,
ManyToMany,
JoinTable,
} from 'typeorm';
import { Region } from '../regions/regions.entity';
import { DailyData } from './daily-data.entity';
Expand Down Expand Up @@ -67,8 +66,7 @@ export class Reef {
@ManyToOne(() => VideoStream, { onDelete: 'CASCADE', nullable: true })
stream?: VideoStream;

@ManyToMany(() => User, (user) => user.administeredReefs, { cascade: true })
@JoinTable()
@ManyToMany(() => User, (user) => user.administeredReefs)
admins: User[];

@OneToOne(() => DailyData, (latestDailyData) => latestDailyData.reef)
Expand Down
4 changes: 3 additions & 1 deletion packages/api/src/users/users.entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import {
CreateDateColumn,
UpdateDateColumn,
ManyToMany,
JoinTable,
} from 'typeorm';
import { Exclude } from 'class-transformer';
import { Reef } from '../reefs/reefs.entity';
Expand Down Expand Up @@ -61,7 +62,8 @@ export class User {
@Column({ nullable: true })
imageUrl?: string;

@ManyToMany(() => Reef, (reef) => reef.admins)
@ManyToMany(() => Reef, (reef) => reef.admins, { cascade: true })
@JoinTable()
administeredReefs: Reef[];

@CreateDateColumn()
Expand Down
3 changes: 1 addition & 2 deletions packages/api/src/users/users.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,9 @@ import { UsersController } from './users.controller';
import { UsersService } from './users.service';
import { User } from './users.entity';
import { ReefApplication } from '../reef-applications/reef-applications.entity';
import { Reef } from '../reefs/reefs.entity';

@Module({
imports: [TypeOrmModule.forFeature([User, Reef, ReefApplication])],
imports: [TypeOrmModule.forFeature([User, ReefApplication])],
controllers: [UsersController],
providers: [UsersService],
exports: [UsersService],
Expand Down
63 changes: 32 additions & 31 deletions packages/api/src/users/users.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import {
BadRequestException,
} from '@nestjs/common';
import { InjectRepository } from '@nestjs/typeorm';
import { Repository, UpdateResult } from 'typeorm';
import { Repository } from 'typeorm';
import { AuthRequest } from '../auth/auth.types';
import { extractAndVerifyToken } from '../auth/firebase-auth.strategy';
import { CreateUserDto } from './dto/create-user.dto';
Expand All @@ -18,9 +18,6 @@ export class UsersService {
@InjectRepository(User)
private usersRepository: Repository<User>,

@InjectRepository(Reef)
private reefRepository: Repository<Reef>,

@InjectRepository(ReefApplication)
private reefApplicationRepository: Repository<ReefApplication>,
) {}
Expand Down Expand Up @@ -108,34 +105,38 @@ export class UsersService {
private async migrateUserAssociations(user: User) {
const reefAssociations = await this.reefApplicationRepository.find({
where: { user },
relations: ['reef', 'reef.admins'],
relations: ['reef'],
});

// User has associations so we have to explicitly change their admin level to reef manager
if (reefAssociations.length) {
await this.usersRepository.update(user.id, {
adminLevel: AdminLevel.ReefManager,
});
}

const newAdministeredReefs: Reef[] = [];

reefAssociations.forEach((reefAssociation) => {
const { reef } = reefAssociation;

const relationshipExists = newAdministeredReefs.find((newReef) => {
return newReef.id === reef.id;
});

// If relationship already exists, skip
if (relationshipExists) {
return;
}

// eslint-disable-next-line fp/no-mutating-methods
newAdministeredReefs.push(reef);
});

const reefEntities: Promise<UpdateResult | null>[] = reefAssociations.map(
async (reefAssociation) => {
const { reef } = reefAssociation;

const relationshipExists = reef.admins.find((admin) => {
return admin.id === user.id;
});

// If relationship already exists, skip
if (relationshipExists) {
return null;
}

// Add new user as admin
return this.reefRepository.update(
{
id: reef.id,
},
{
admins: [...reef.admins, user],
},
);
},
);

return Promise.all(reefEntities);
const newUser: User = {
...user,
administeredReefs: newAdministeredReefs,
};
return this.usersRepository.save(newUser);
}
}

0 comments on commit 28deadb

Please sign in to comment.