fix(db-postgres): sort by distance when the near operator is used (#12185)
Fixes https://github.com/payloadcms/payload/issues/12090, in MongoDB the documents are sorted by distance automatically whenever the `near` operation is used, which we have in the docs: > When querying using the near operator, the returned documents will be sorted by nearest first. This fixes this incosistensty between Postgres and MongoDB. ⚠️ This change potentially can cause to produce different results, if you used the `near` operator without `sort: 'pointFieldName'`.
This commit is contained in:
@@ -3,12 +3,14 @@ import type { FlattenedField, Where } from 'payload'
|
|||||||
|
|
||||||
import type { DrizzleAdapter, GenericColumn } from '../types.js'
|
import type { DrizzleAdapter, GenericColumn } from '../types.js'
|
||||||
import type { BuildQueryJoinAliases } from './buildQuery.js'
|
import type { BuildQueryJoinAliases } from './buildQuery.js'
|
||||||
|
import type { QueryContext } from './parseParams.js'
|
||||||
|
|
||||||
import { parseParams } from './parseParams.js'
|
import { parseParams } from './parseParams.js'
|
||||||
|
|
||||||
export function buildAndOrConditions({
|
export function buildAndOrConditions({
|
||||||
adapter,
|
adapter,
|
||||||
aliasTable,
|
aliasTable,
|
||||||
|
context,
|
||||||
fields,
|
fields,
|
||||||
joins,
|
joins,
|
||||||
locale,
|
locale,
|
||||||
@@ -21,6 +23,7 @@ export function buildAndOrConditions({
|
|||||||
adapter: DrizzleAdapter
|
adapter: DrizzleAdapter
|
||||||
aliasTable?: Table
|
aliasTable?: Table
|
||||||
collectionSlug?: string
|
collectionSlug?: string
|
||||||
|
context: QueryContext
|
||||||
fields: FlattenedField[]
|
fields: FlattenedField[]
|
||||||
globalSlug?: string
|
globalSlug?: string
|
||||||
joins: BuildQueryJoinAliases
|
joins: BuildQueryJoinAliases
|
||||||
@@ -41,6 +44,7 @@ export function buildAndOrConditions({
|
|||||||
const result = parseParams({
|
const result = parseParams({
|
||||||
adapter,
|
adapter,
|
||||||
aliasTable,
|
aliasTable,
|
||||||
|
context,
|
||||||
fields,
|
fields,
|
||||||
joins,
|
joins,
|
||||||
locale,
|
locale,
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ import type { PgTableWithColumns } from 'drizzle-orm/pg-core'
|
|||||||
import type { FlattenedField, Sort, Where } from 'payload'
|
import type { FlattenedField, Sort, Where } from 'payload'
|
||||||
|
|
||||||
import type { DrizzleAdapter, GenericColumn, GenericTable } from '../types.js'
|
import type { DrizzleAdapter, GenericColumn, GenericTable } from '../types.js'
|
||||||
|
import type { QueryContext } from './parseParams.js'
|
||||||
|
|
||||||
import { buildOrderBy } from './buildOrderBy.js'
|
import { buildOrderBy } from './buildOrderBy.js'
|
||||||
import { parseParams } from './parseParams.js'
|
import { parseParams } from './parseParams.js'
|
||||||
@@ -52,24 +53,14 @@ const buildQuery = function buildQuery({
|
|||||||
id: adapter.tables[tableName].id,
|
id: adapter.tables[tableName].id,
|
||||||
}
|
}
|
||||||
|
|
||||||
const orderBy = buildOrderBy({
|
|
||||||
adapter,
|
|
||||||
aliasTable,
|
|
||||||
fields,
|
|
||||||
joins,
|
|
||||||
locale,
|
|
||||||
parentIsLocalized,
|
|
||||||
selectFields,
|
|
||||||
sort,
|
|
||||||
tableName,
|
|
||||||
})
|
|
||||||
|
|
||||||
let where: SQL
|
let where: SQL
|
||||||
|
|
||||||
|
const context: QueryContext = { sort }
|
||||||
if (incomingWhere && Object.keys(incomingWhere).length > 0) {
|
if (incomingWhere && Object.keys(incomingWhere).length > 0) {
|
||||||
where = parseParams({
|
where = parseParams({
|
||||||
adapter,
|
adapter,
|
||||||
aliasTable,
|
aliasTable,
|
||||||
|
context,
|
||||||
fields,
|
fields,
|
||||||
joins,
|
joins,
|
||||||
locale,
|
locale,
|
||||||
@@ -81,6 +72,18 @@ const buildQuery = function buildQuery({
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const orderBy = buildOrderBy({
|
||||||
|
adapter,
|
||||||
|
aliasTable,
|
||||||
|
fields,
|
||||||
|
joins,
|
||||||
|
locale,
|
||||||
|
parentIsLocalized,
|
||||||
|
selectFields,
|
||||||
|
sort: context.sort,
|
||||||
|
tableName,
|
||||||
|
})
|
||||||
|
|
||||||
return {
|
return {
|
||||||
joins,
|
joins,
|
||||||
orderBy,
|
orderBy,
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import type { SQL, Table } from 'drizzle-orm'
|
import type { SQL, Table } from 'drizzle-orm'
|
||||||
import type { FlattenedField, Operator, Where } from 'payload'
|
import type { FlattenedField, Operator, Sort, Where } from 'payload'
|
||||||
|
|
||||||
import { and, isNotNull, isNull, ne, notInArray, or, sql } from 'drizzle-orm'
|
import { and, isNotNull, isNull, ne, notInArray, or, sql } from 'drizzle-orm'
|
||||||
import { PgUUID } from 'drizzle-orm/pg-core'
|
import { PgUUID } from 'drizzle-orm/pg-core'
|
||||||
@@ -14,9 +14,12 @@ import { buildAndOrConditions } from './buildAndOrConditions.js'
|
|||||||
import { getTableColumnFromPath } from './getTableColumnFromPath.js'
|
import { getTableColumnFromPath } from './getTableColumnFromPath.js'
|
||||||
import { sanitizeQueryValue } from './sanitizeQueryValue.js'
|
import { sanitizeQueryValue } from './sanitizeQueryValue.js'
|
||||||
|
|
||||||
|
export type QueryContext = { sort: Sort }
|
||||||
|
|
||||||
type Args = {
|
type Args = {
|
||||||
adapter: DrizzleAdapter
|
adapter: DrizzleAdapter
|
||||||
aliasTable?: Table
|
aliasTable?: Table
|
||||||
|
context: QueryContext
|
||||||
fields: FlattenedField[]
|
fields: FlattenedField[]
|
||||||
joins: BuildQueryJoinAliases
|
joins: BuildQueryJoinAliases
|
||||||
locale?: string
|
locale?: string
|
||||||
@@ -30,6 +33,7 @@ type Args = {
|
|||||||
export function parseParams({
|
export function parseParams({
|
||||||
adapter,
|
adapter,
|
||||||
aliasTable,
|
aliasTable,
|
||||||
|
context,
|
||||||
fields,
|
fields,
|
||||||
joins,
|
joins,
|
||||||
locale,
|
locale,
|
||||||
@@ -57,6 +61,7 @@ export function parseParams({
|
|||||||
const builtConditions = buildAndOrConditions({
|
const builtConditions = buildAndOrConditions({
|
||||||
adapter,
|
adapter,
|
||||||
aliasTable,
|
aliasTable,
|
||||||
|
context,
|
||||||
fields,
|
fields,
|
||||||
joins,
|
joins,
|
||||||
locale,
|
locale,
|
||||||
@@ -342,6 +347,7 @@ export function parseParams({
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
if (geoConstraints.length) {
|
if (geoConstraints.length) {
|
||||||
|
context.sort = relationOrPath
|
||||||
constraints.push(and(...geoConstraints))
|
constraints.push(and(...geoConstraints))
|
||||||
}
|
}
|
||||||
break
|
break
|
||||||
|
|||||||
@@ -1218,7 +1218,6 @@ describe('collections-rest', () => {
|
|||||||
.GET(`/${pointSlug}`, {
|
.GET(`/${pointSlug}`, {
|
||||||
query: {
|
query: {
|
||||||
limit: 5,
|
limit: 5,
|
||||||
sort: 'point',
|
|
||||||
where: {
|
where: {
|
||||||
point: {
|
point: {
|
||||||
// querying large enough range to include all docs
|
// querying large enough range to include all docs
|
||||||
|
|||||||
Reference in New Issue
Block a user