I'm trying to save an Entity with a custom ManyToMany field in TypeORM
Main Entity
@Entity()
export class Routine extends BaseEntity {
@PrimaryGeneratedColumn()
id: number;
@Column('varchar', { length: 50 })
name: string;
@Column('timestamptz')
creationDate: Date;
@Column('boolean')
active: boolean;
@ManyToOne(
type => User,
user => user.routines,
{ eager: false },
)
user: User;
@Column()
userId: number;
@OneToMany(
type => ExerciseToRoutine,
exerciseToRoutine => exerciseToRoutine.routineId,
)
public exerciseToRoutine: ExerciseToRoutine[];
}
JoinTable
@Entity()
export class ExerciseToRoutine extends BaseEntity {
@PrimaryColumn()
exerciseId: number;
@PrimaryColumn()
routineId: number;
@Column()
day: number;
@ManyToOne(
type => Routine,
routine => routine.exerciseToRoutine,
)
routine: Routine;
@ManyToOne(
type => Exercise,
exercise => exercise.exerciseToRoutine,
)
exercise: Exercise;
}
Code trying to save Entity
const routine = new Routine(name, currentDate, user, exerciseToRoutine, false);
await this.trySaveRoutine(routine);
The problem is that I need to save the Routine entity with its exerciseToRoutine (JoinTable to Exercise Entity) before the Routine id is autogenerated, and the property exerciseToRoutine needs that ID. So how Im suposed to do this?? Thanks
A good example of ManyToMany and lazy relation. It will be enough to create user-author-like.entity.ts and implement it where necessary.
Since it uses lazy relations promise, it does not give me a flexible opportunity to use it as I wish. I produced such a solution in my application. I use it in all my GraphQL API.
user.entity.ts
import { Entity,
PrimaryGeneratedColumn,
Column,
BaseEntity,
OneToMany,
CreateDateColumn,
UpdateDateColumn,
ManyToMany,
JoinTable,
OneToOne } from 'typeorm';
import { ObjectType,
ID,
Field,
InputType,
ArgsType,
Int } from 'type-graphql';
import { Post } from '../post/post.entity';
import { Author } from '../author/author.entity';
@Entity()
@ObjectType()
export class User extends BaseEntity {
@PrimaryGeneratedColumn('uuid')
@Field(() => ID)
id: string;
@Column({ name: 'userName', unique: true })
@Field()
userName: string;
@Column({ name: 'email', unique: true })
@Field()
email: string;
@Column()
password: string;
@CreateDateColumn({ type: 'timestamp' })
createdAt: Date;
@UpdateDateColumn({ type: 'timestamp' })
updatedAt: Date;
// user_author_like
@ManyToMany(() => Author, author => author.yazariBegenenler, { lazy: true })
@JoinTable({
name: 'user_author_like',
joinColumn: {
name: 'userId',
referencedColumnName: 'id'
},
inverseJoinColumn: {
name: 'authorId',
referencedColumnName: 'id'
}
})
@Field(() => [Author])
begenilenYazarlar: Promise<Author[]>;
}
author.entity.ts
import { Entity, PrimaryGeneratedColumn, Column, BaseEntity, ManyToMany } from 'typeorm';
import { ObjectType, Field, ID } from 'type-graphql';
import { User } from '../user/user.entity';
@Entity()
@ObjectType()
export class Author extends BaseEntity {
@PrimaryGeneratedColumn('uuid')
@Field(() => ID)
id: string;
@Column()
@Field()
title: string
// yazari begenenler
@ManyToMany(() => User, user => user.begenilenYazarlar, { lazy: true })
@Field(() => [User])
yazariBegenenler: Promise<User[]>
}
user-author-like.entity.ts
import { BaseEntity, PrimaryColumn, Entity, CreateDateColumn } from 'typeorm';
@Entity()
export class UserAuthorLike extends BaseEntity {
@PrimaryColumn('uuid')
userId: string;
@PrimaryColumn('uuid')
authorId: string;
@CreateDateColumn({ type: 'timestamp' })
likedAt: Date;
}
user-author-like.resolver.ts
import { Resolver, Authorized, Mutation, Arg } from 'type-graphql';
import { UserAuthorLike } from './user-author-like.entity';
@Resolver()
export class UserAuthorLikeResolver {
@Authorized('ADMIN', 'MODERATOR', 'MEMBER')
@Mutation(() => Boolean)
async yazarBegen(
@Arg('userId') userId: string,
@Arg('authorId') authorId: string
): Promise<Boolean> {
await UserAuthorLike.create({ userId, authorId }).save();
return true;
};
@Authorized('ADMIN', 'MODERATOR', 'MEMBER')
@Mutation(() => Boolean)
async yazarBegenme(
@Arg('userId') userId: string,
@Arg('authorId') authorId: string
): Promise<Boolean> {
await UserAuthorLike.delete({ userId, authorId });
return true;
};
}
The OneToMany
field exerciseToRoutine
of Routine
does not store any foreign key to ExerciseToRoutine
, that will do the join table itself. To save a new Routine
entity just set the exerciseToRoutine
field to an empty array before. Then create a ExerciseToRoutine
with the newly generated Routine
id.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.