Skip to content

Commit

Permalink
fix(core): fix querying embeddables over cast fields (#1639)
Browse files Browse the repository at this point in the history
Co-authored-by: Martin Adámek <banan23@gmail.com>
  • Loading branch information
francisco-sanchez-molina and B4nan committed Apr 3, 2021
1 parent 4480bd3 commit cb5b25c
Show file tree
Hide file tree
Showing 3 changed files with 28 additions and 12 deletions.
7 changes: 6 additions & 1 deletion packages/knex/src/query/QueryBuilderHelper.ts
Original file line number Diff line number Diff line change
Expand Up @@ -516,7 +516,12 @@ export class QueryBuilderHelper {

if (!this.isPrefixed(field)) {
const alias = always ? (quote ? this.alias : this.platform.quoteIdentifier(this.alias)) + '.' : '';
ret = alias + this.fieldName(field, this.alias);
const fieldName = this.fieldName(field, this.alias);
if (fieldName.startsWith('(')) {
ret = '(' + alias + fieldName.slice(1);
} else {
ret = alias + fieldName;
}
} else {
const [a, f] = field.split('.');
ret = a + '.' + this.fieldName(f, a);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`embedded entities in postgresql schema: embeddables 1 1`] = `
"create table \\"user\\" (\\"id\\" serial primary key, \\"address1_street\\" varchar(255) not null, \\"address1_postal_code\\" varchar(255) not null, \\"address1_city\\" varchar(255) not null, \\"address1_country\\" varchar(255) not null, \\"addr_street\\" varchar(255) null, \\"addr_postal_code\\" varchar(255) null, \\"addr_city\\" varchar(255) null, \\"addr_country\\" varchar(255) null, \\"street\\" varchar(255) not null, \\"postal_code\\" varchar(255) not null, \\"city\\" varchar(255) not null, \\"country\\" varchar(255) not null, \\"address4\\" jsonb not null, \\"addresses\\" jsonb not null, \\"after\\" int4 null);
"create table \\"user\\" (\\"id\\" serial primary key, \\"address1_street\\" varchar(255) not null, \\"address1_number\\" int4 not null, \\"address1_postal_code\\" varchar(255) not null, \\"address1_city\\" varchar(255) not null, \\"address1_country\\" varchar(255) not null, \\"addr_street\\" varchar(255) null, \\"addr_postal_code\\" varchar(255) null, \\"addr_city\\" varchar(255) null, \\"addr_country\\" varchar(255) null, \\"street\\" varchar(255) not null, \\"number\\" int4 not null, \\"postal_code\\" varchar(255) not null, \\"city\\" varchar(255) not null, \\"country\\" varchar(255) not null, \\"address4\\" jsonb not null, \\"addresses\\" jsonb not null, \\"after\\" int4 null);
"
`;
Expand Down
31 changes: 21 additions & 10 deletions tests/features/embeddables/embedded-entities.postgres.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@ class Address1 {
@Property()
street?: string;

@Property()
number?: number;

@Property()
postalCode?: string;

Expand All @@ -16,8 +19,9 @@ class Address1 {
@Property()
country?: string;

constructor(street?: string, postalCode?: string, city?: string, country?: string) {
constructor(street?: string, number?: number, postalCode?: string, city?: string, country?: string) {
this.street = street;
this.number = number;
this.postalCode = postalCode;
this.city = city;
this.country = country;
Expand Down Expand Up @@ -141,27 +145,28 @@ describe('embedded entities in postgresql', () => {

test('persist and load', async () => {
const user = new User();
user.address1 = new Address1('Downing street 10', '123', 'London 1', 'UK 1');
user.address1 = new Address1('Downing street 10', 10, '123', 'London 1', 'UK 1');
user.address2 = new Address2('Downing street 11', 'London 2', 'UK 2');
user.address3 = new Address1('Downing street 12', '789', 'London 3', 'UK 3');
user.address4 = new Address1('Downing street 13', '10', 'London 4', 'UK 4');
user.addresses.push(new Address1('Downing street 13A', '10A', 'London 4A', 'UK 4A'));
user.addresses.push(new Address1('Downing street 13B', '10B', 'London 4B', 'UK 4B'));
user.address3 = new Address1('Downing street 12', 10, '789', 'London 3', 'UK 3');
user.address4 = new Address1('Downing street 13', 10, '10', 'London 4', 'UK 4');
user.addresses.push(new Address1('Downing street 13A', 10, '10A', 'London 4A', 'UK 4A'));
user.addresses.push(new Address1('Downing street 13B', 10, '10B', 'London 4B', 'UK 4B'));

const mock = jest.fn();
const logger = new Logger(mock, ['query']);
Object.assign(orm.config, { logger });
await orm.em.persistAndFlush(user);
orm.em.clear();
expect(mock.mock.calls[0][0]).toMatch('begin');
expect(mock.mock.calls[1][0]).toMatch('insert into "user" ("addr_city", "addr_country", "addr_postal_code", "addr_street", "address1_city", "address1_country", "address1_postal_code", "address1_street", "address4", "addresses", "city", "country", "postal_code", "street") values ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11, $12, $13, $14) returning "id"');
expect(mock.mock.calls[1][0]).toMatch('insert into "user" ("addr_city", "addr_country", "addr_postal_code", "addr_street", "address1_city", "address1_country", "address1_number", "address1_postal_code", "address1_street", "address4", "addresses", "city", "country", "number", "postal_code", "street") values ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11, $12, $13, $14, $15, $16) returning "id"');
expect(mock.mock.calls[2][0]).toMatch('commit');

const u = await orm.em.findOneOrFail(User, user.id);
expect(mock.mock.calls[3][0]).toMatch('select "e0".* from "user" as "e0" where "e0"."id" = $1 limit $2');
expect(u.address1).toBeInstanceOf(Address1);
expect(u.address1).toEqual({
street: 'Downing street 10',
number: 10,
postalCode: '123',
city: 'London 1',
country: 'UK 1',
Expand All @@ -176,13 +181,15 @@ describe('embedded entities in postgresql', () => {
expect(u.address3).toBeInstanceOf(Address1);
expect(u.address3).toEqual({
street: 'Downing street 12',
number: 10,
postalCode: '789',
city: 'London 3',
country: 'UK 3',
});
expect(u.address4).toBeInstanceOf(Address1);
expect(u.address4).toEqual({
street: 'Downing street 13',
number: 10,
postalCode: '10',
city: 'London 4',
country: 'UK 4',
Expand Down Expand Up @@ -215,6 +222,10 @@ describe('embedded entities in postgresql', () => {
const u4 = await orm.em.findOneOrFail(User, { address4: { postalCode: '999' } });
expect(u4).toBe(u1);
expect(mock.mock.calls[10][0]).toMatch('select "e0".* from "user" as "e0" where "e0"."address4"->>\'postalCode\' = $1 limit $2');

const u5 = await orm.em.findOneOrFail(User, { address4: { number: { $gt: 2 } } });
expect(u5).toBe(u1);
expect(mock.mock.calls[11][0]).toMatch('select "e0".* from "user" as "e0" where ("e0"."address4"->>\'number\')::float8 > $1 limit $2');
});

test('assign', async () => {
Expand Down Expand Up @@ -251,9 +262,9 @@ describe('embedded entities in postgresql', () => {

test('query by complex custom expressions with JSON operator and casting (GH issue 1261)', async () => {
const user = new User();
user.address1 = new Address1('Test', '12000', 'Prague', 'CZ');
user.address3 = new Address1('Test', '12000', 'Prague', 'CZ');
user.address4 = new Address1('Test', '12000', 'Prague', 'CZ');
user.address1 = new Address1('Test', 10, '12000', 'Prague', 'CZ');
user.address3 = new Address1('Test', 10, '12000', 'Prague', 'CZ');
user.address4 = new Address1('Test', 10, '12000', 'Prague', 'CZ');
await orm.em.persistAndFlush(user);
orm.em.clear();

Expand Down

0 comments on commit cb5b25c

Please sign in to comment.