typeorm: Not loading data from @OneToOne relation
There is a problem with loading object from database. The creating and saving works (I looked in the database) but when loading from database it doesn’t load the data from relation.
import "reflect-metadata";
import { createConnection } from "typeorm";
import { Post } from "./post";
import { PostDetails } from "./post-details";
async function main() {
try {
console.log(`Before connection!`);
let connection = await createConnection({
driver: {
type: "mysql",
host: "localhost",
port: 3306,
username: "root",
password: "qwerty123",
database: "typeorm"
},
entities: [
Post, PostDetails
],
logging: {
logQueries: true,
logFailedQueryError: true,
},
autoSchemaSync: true,
});
console.log(`Connected!`);
let post = new Post();
post.title = "Title";
post.text = "Lorem ipsum";
post.details = new PostDetails();
post.details.testField = "test";
console.log(post);
post = await connection.getRepository(Post).persist(post);
console.log(post);
let loadedPost = await connection.getRepository(Post).findOneById(post.id);
console.log(loadedPost);
console.log(`Saved ok!`);
process.exit(0);
} catch (error) {
console.log(`Error!`, error);
process.exit(1);
}
}
main();
My entities:
import { Table, PrimaryGeneratedColumn, Column, OneToOne, JoinColumn } from "typeorm";
import { PostDetails } from "./post-details";
@Table()
export class Post {
@PrimaryGeneratedColumn()
public id: number;
@Column()
title: string;
@Column("text")
text: string;
@JoinColumn()
@OneToOne(type => PostDetails, { cascadeInsert: true, nullable: true })
details: PostDetails | null;
}
import { Table, PrimaryGeneratedColumn, Column } from "typeorm";
@Table()
export class PostDetails {
@PrimaryGeneratedColumn()
public id: number;
@Column()
testField: string;
}
Created object looks like this:
Post {
title: 'Title',
text: 'Lorem ipsum',
details: PostDetails { testField: 'test', id: 1 },
id: 1 }
But it generates sql without joins on relation, so only id is returned not the data:
SELECT post.id AS post_id, post.title AS post_title, post.text AS post_text, post.details AS post_details FROM post post WHERE post.id=? -- PARAMETERS: [1]
So the loaded object has empty details field:
Post { id: 1, title: 'Title', text: 'Lorem ipsum' }
This is a bug or I should add some decorator in PostDetails?
About this issue
- Original URL
- State: closed
- Created 8 years ago
- Comments: 19 (15 by maintainers)
findOneByIdnever joins relations by itself, you need to specify manually what relations you want to join. This is implemented this way because your object can have tons of relations, which can be nested deep and even recursive, thats why its not possible to always join all relations. User needs to be explicit what he wants. You have two choices: use query builder or provide find options tofindOneByIdmethod. Docs for both you can find on siteIt’s not an user friendly solution. People use ORM to simplify data access - just use
@Decoratorand don’t worry about foreing keys, joins and other stuffs.If someone have relation which might be bigger (not one-to-one) eg. 1000 relations, and he don’t want do load it all, he can use lazy relations. But when I add new relation to my class I have to remember to change joins in all query builder or make another layer with custom repository which will do that.
I think we should stick to the idea of Hibernate - eager and lazy loding.
QueryBuilderor joins infindshould be used only to make custom joins on columns that aren’t defined as relations.It will look like this:
Also its generally better to use query builder for complex queries:
Eager relations are added in
0.1.0-alpha.44. Docs can be found here.@19majkel94 done in 57e13f6
actually you are not worrying about keys or joins. You are just telling which relation you need to load.
But I got your point, I have some ideas how to add automatic joins, i’ll try to implement them later. Until that use query builder or find options
@19majkel94 is awesome guy and made lot of contributions in different other libraries, strange that he is still not in contributors list of typeorm
@19majkel94 if it’s so easy couldn’t you you have made a pull request? doesn’t seem right to hassle someone who is already so busy and volunteering his time…
If it’s
OneToMany, you will get an empty array. If it’sOneToOneorManyToOne- undefined. Of course when it works ok - now it’s not working due to wrong sql syntax 😜