In one to one relations, the side without foreign key shouldn't have relation opts
jansedlon opened this issue · 6 comments
TL;DR
This is correct
export const oneToOneBsRelations = relations(oneToOneBs, (helpers) => ({
a: helpers.one(oneToOneAs)
);
export const oneToOneAsRelations = relations(oneToOneAs, (helpers) => ({
b: helpers.one(oneToOneBs, {
relationName: 'OneToOne_AToOneToOne_B',
fields: [ oneToOneAs.bId ],
references: [ oneToOneBs.id ] })
})
);
This is not
export const oneToOneBsRelations = relations(oneToOneBs, (helpers) => ({
a: helpers.one(oneToOneAs, {
relationName: 'OneToOne_AToOneToOne_B',
fields: [oneToOneBs.id],
references: [oneToOneAs.bId] })
})
// This whole opts object shouldn't be there
);
export const oneToOneAsRelations = relations(oneToOneAs, (helpers) => ({
b: helpers.one(oneToOneBs, {
relationName: 'OneToOne_AToOneToOne_B',
fields: [ oneToOneAs.bId ],
references: [ oneToOneBs.id ] })
})
);
Hi, if you have one to one relation (A, B) and the foreign key is in table A
, the one
relation on the other side shouldn't have any opts.
If it does, drizzle query with with
does not infer it as an optional relation.
The best showcase is if you open this repo, hover your mouse over result
in packages/usage/tests/shared/testOneToOne.ts
You can see that the a
property is not nullable even though it should be.
From my understanding, if you pass any opts into one
relation function, it's then inferred as required when using drizzle query.
https://orm.drizzle.team/docs/rqb#one-to-one
I found that the issue is here
https://github.com/farreldarian/prisma-generator-drizzle/blob/ed849c2e304a4bdf9b0daaa66d4c4e01e46542c2/packages/generator/src/lib/adapter/declarations/generateTableRelationsDeclaration.ts#L126
In this case the whole object shouldn't be passed there. I don't really understand the black magic of that code, but in this case, it shouldn't be there :D
From my understanding, if you pass any opts into one relation function, it's then inferred as required when using drizzle query.
Yeah it was tricky since I didn't had the absolute reference when building the relational generator, whether defining or not defining opts determines the optionality. I thought it was a bug in drizzle.
I think we can proceed following the current (your) finding for the optionality rule.
Expect the fix at last this week.
—
UPDATE: optionality doesn't matter, it should always be nullable
Ah, I now understand the reason for including all these references.
Given the following schema:
model Disambiguating_Transfer {
id String @id
salePayment Disambiguating_Sale? @relation("Disambiguating_Sale_payment")
saleTax Disambiguating_Sale? @relation("Disambiguating_Sale_tax")
}
model Disambiguating_Sale {
id String @id
payment Disambiguating_Transfer @relation("Disambiguating_Sale_payment", fields: [paymentId], references: [id])
paymentId String @unique
tax Disambiguating_Transfer @relation("Disambiguating_Sale_tax", fields: [taxId], references: [id])
taxId String @unique
}
To determine Transfer.salePayment
and Transfer.saleTax
(table name is simplified), ideally, we could just specify the relationName
, but how can we achieve that in drizzle?
—
Specifying the name, field, and references, makes the field required
Posted in drizzle's help
https://discord.com/channels/1043890932593987624/1254869164607143998
Nice, good observations, thank you! Luckily i don't have this use case in my code and i haven't encountered that.
I think we can proceed with the no-opts
option, and utilizing opts
for cases that have disambiguating relationship. This should cover most cases
Sounds good