From d20e38445c84d0274375afe7879a94b9b0516b7c Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 30 Oct 2024 18:19:35 +1100 Subject: [PATCH 01/12] feat: point --- sqlx-postgres/src/type_checking.rs | 2 + sqlx-postgres/src/types/geometry/mod.rs | 1 + sqlx-postgres/src/types/geometry/point.rs | 138 ++++++++++++++++++++++ sqlx-postgres/src/types/mod.rs | 4 + sqlx-test/src/lib.rs | 14 +++ tests/postgres/types.rs | 11 ++ 6 files changed, 170 insertions(+) create mode 100644 sqlx-postgres/src/types/geometry/mod.rs create mode 100644 sqlx-postgres/src/types/geometry/point.rs diff --git a/sqlx-postgres/src/type_checking.rs b/sqlx-postgres/src/type_checking.rs index e22d3b9007..f789347fd2 100644 --- a/sqlx-postgres/src/type_checking.rs +++ b/sqlx-postgres/src/type_checking.rs @@ -32,6 +32,8 @@ impl_type_checking!( sqlx::postgres::types::PgCube, + sqlx::postgres::types::PgPoint, + #[cfg(feature = "uuid")] sqlx::types::Uuid, diff --git a/sqlx-postgres/src/types/geometry/mod.rs b/sqlx-postgres/src/types/geometry/mod.rs new file mode 100644 index 0000000000..a199ff7517 --- /dev/null +++ b/sqlx-postgres/src/types/geometry/mod.rs @@ -0,0 +1 @@ +pub mod point; diff --git a/sqlx-postgres/src/types/geometry/point.rs b/sqlx-postgres/src/types/geometry/point.rs new file mode 100644 index 0000000000..cc10672950 --- /dev/null +++ b/sqlx-postgres/src/types/geometry/point.rs @@ -0,0 +1,138 @@ +use crate::decode::Decode; +use crate::encode::{Encode, IsNull}; +use crate::error::BoxDynError; +use crate::types::Type; +use crate::{PgArgumentBuffer, PgHasArrayType, PgTypeInfo, PgValueFormat, PgValueRef, Postgres}; +use sqlx_core::bytes::Buf; +use sqlx_core::Error; +use std::str::FromStr; + +/// ## Postgres Geometric Point type +/// +/// Description: Point on a plane +/// Representation: `(x, y)` +/// +/// Points are the fundamental two-dimensional building block for geometric types. Values of type point are specified using either of the following syntaxes: +/// ```text +/// ( x , y ) +/// x , y +/// ```` +/// where x and y are the respective coordinates, as floating-point numbers. +/// +/// See https://www.postgresql.org/docs/16/datatype-geometric.html#DATATYPE-GEOMETRIC-POINTS +#[derive(Debug, Clone, PartialEq)] +pub struct PgPoint { + pub x: f64, + pub y: f64, +} + +impl Type for PgPoint { + fn type_info() -> PgTypeInfo { + PgTypeInfo::with_name("point") + } +} + +impl PgHasArrayType for PgPoint { + fn array_type_info() -> PgTypeInfo { + PgTypeInfo::with_name("_point") + } +} + +impl<'r> Decode<'r, Postgres> for PgPoint { + fn decode(value: PgValueRef<'r>) -> Result> { + match value.format() { + PgValueFormat::Text => Ok(PgPoint::from_str(value.as_str()?)?), + PgValueFormat::Binary => Ok(PgPoint::from_bytes(value.as_bytes()?)?), + } + } +} + +impl<'q> Encode<'q, Postgres> for PgPoint { + fn produces(&self) -> Option { + Some(PgTypeInfo::with_name("point")) + } + + fn encode_by_ref(&self, buf: &mut PgArgumentBuffer) -> Result { + self.serialize(buf)?; + Ok(IsNull::No) + } +} + +fn parse_float_from_str(s: &str, error_msg: &str) -> Result { + s.trim() + .parse() + .map_err(|_| Error::Decode(error_msg.into())) +} + +impl FromStr for PgPoint { + type Err = BoxDynError; + + fn from_str(s: &str) -> Result { + let (x_str, y_str) = s + .trim_matches(|c| c == '(' || c == ')' || c == ' ') + .split_once(',') + .ok_or_else(|| format!("error decoding POINT: could not get x and y from {}", s))?; + + let x = parse_float_from_str(x_str, "error decoding POINT: could not get x")?; + let y = parse_float_from_str(y_str, "error decoding POINT: could not get x")?; + + Ok(PgPoint { x, y }) + } +} + +impl PgPoint { + fn from_bytes(mut bytes: &[u8]) -> Result { + let x = bytes.get_f64(); + let y = bytes.get_f64(); + Ok(PgPoint { x, y }) + } + + fn serialize(&self, buff: &mut PgArgumentBuffer) -> Result<(), BoxDynError> { + buff.extend_from_slice(&self.x.to_be_bytes()); + buff.extend_from_slice(&self.y.to_be_bytes()); + Ok(()) + } + + #[cfg(test)] + fn serialize_to_vec(&self) -> Vec { + let mut buff = PgArgumentBuffer::default(); + self.serialize(&mut buff).unwrap(); + buff.to_vec() + } +} + +#[cfg(test)] +mod point_tests { + + use std::str::FromStr; + + use super::PgPoint; + + const POINT_BYTES: &[u8] = &[ + 64, 0, 204, 204, 204, 204, 204, 205, 64, 20, 204, 204, 204, 204, 204, 205, + ]; + + #[test] + fn can_deserialise_point_type_bytes() { + let point = PgPoint::from_bytes(POINT_BYTES).unwrap(); + assert_eq!(point, PgPoint { x: 2.1, y: 5.2 }) + } + + #[test] + fn can_deserialise_point_type_str() { + let point = PgPoint::from_str("(2, 3)").unwrap(); + assert_eq!(point, PgPoint { x: 2., y: 3. }); + } + + #[test] + fn can_deserialise_point_type_str_float() { + let point = PgPoint::from_str("(2.5, 3.4)").unwrap(); + assert_eq!(point, PgPoint { x: 2.5, y: 3.4 }); + } + + #[test] + fn can_serialise_point_type() { + let point = PgPoint { x: 2.1, y: 5.2 }; + assert_eq!(point.serialize_to_vec(), POINT_BYTES,) + } +} diff --git a/sqlx-postgres/src/types/mod.rs b/sqlx-postgres/src/types/mod.rs index 846f1b731d..2a571de265 100644 --- a/sqlx-postgres/src/types/mod.rs +++ b/sqlx-postgres/src/types/mod.rs @@ -21,6 +21,7 @@ //! | [`PgLQuery`] | LQUERY | //! | [`PgCiText`] | CITEXT1 | //! | [`PgCube`] | CUBE | +//! | [`PgPoint] | POINT | //! | [`PgHstore`] | HSTORE | //! //! 1 SQLx generally considers `CITEXT` to be compatible with `String`, `&str`, etc., @@ -212,6 +213,8 @@ mod bigdecimal; mod cube; +mod geometry; + #[cfg(any(feature = "bigdecimal", feature = "rust_decimal"))] mod numeric; @@ -242,6 +245,7 @@ mod bit_vec; pub use array::PgHasArrayType; pub use citext::PgCiText; pub use cube::PgCube; +pub use geometry::point::PgPoint; pub use hstore::PgHstore; pub use interval::PgInterval; pub use lquery::PgLQuery; diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index 5ba0f6323f..304492e695 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -51,6 +51,12 @@ macro_rules! test_type { } }; + ($name:ident<$ty:ty>($db:ident, $($text:literal @= $value:expr),+ $(,)?)) => { + paste::item! { + $crate::__test_prepared_type!($name<$ty>($db, $crate::[< $db _query_for_test_prepared_geometric_type >]!(), $($text == $value),+)); + } + }; + ($name:ident($db:ident, $($text:literal == $value:expr),+ $(,)?)) => { $crate::test_type!($name<$name>($db, $($text == $value),+)); }; @@ -82,6 +88,7 @@ macro_rules! test_prepared_type { } }; + ($name:ident($db:ident, $($text:literal == $value:expr),+ $(,)?)) => { $crate::__test_prepared_type!($name<$name>($db, $($text == $value),+)); }; @@ -223,3 +230,10 @@ macro_rules! Postgres_query_for_test_prepared_type { "SELECT ({0} is not distinct from $1)::int4, {0}, $2" }; } + +#[macro_export] +macro_rules! Postgres_query_for_test_prepared_geometric_type { + () => { + "SELECT ({0}::text is not distinct from $1::text)::int4, {0}, $2" + }; +} diff --git a/tests/postgres/types.rs b/tests/postgres/types.rs index 4912339dc2..64a41eddd5 100644 --- a/tests/postgres/types.rs +++ b/tests/postgres/types.rs @@ -492,6 +492,17 @@ test_type!(_cube>(Postgres, "array[cube(2.2,-3.4)]" == vec![sqlx::postgres::types::PgCube::OneDimensionInterval(2.2, -3.4)], )); +#[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] +test_type!(point(Postgres, + "point(2.2,-3.4)" @= sqlx::postgres::types::PgPoint { x: 2.2, y:-3.4 }, +)); + +#[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] +test_type!(_point>(Postgres, + "array[point(2,3),point(2.1,3.4)]" @= vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], + "array[point(2.2,-3.4)]" @= vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], +)); + #[cfg(feature = "rust_decimal")] test_type!(decimal(Postgres, "0::numeric" == sqlx::types::Decimal::from_str("0").unwrap(), From 42f58a4d8f0c14b3a7c6e2859d79413e768bf111 Mon Sep 17 00:00:00 2001 From: James Holman Date: Tue, 5 Nov 2024 18:54:04 +1100 Subject: [PATCH 02/12] test: try if eq operator works for arrays of geometries --- tests/postgres/types.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/postgres/types.rs b/tests/postgres/types.rs index 64a41eddd5..87ca11ba47 100644 --- a/tests/postgres/types.rs +++ b/tests/postgres/types.rs @@ -494,13 +494,13 @@ test_type!(_cube>(Postgres, #[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] test_type!(point(Postgres, - "point(2.2,-3.4)" @= sqlx::postgres::types::PgPoint { x: 2.2, y:-3.4 }, + "point(2.2,-3.4)" == sqlx::postgres::types::PgPoint { x: 2.2, y:-3.4 }, )); #[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] test_type!(_point>(Postgres, - "array[point(2,3),point(2.1,3.4)]" @= vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], - "array[point(2.2,-3.4)]" @= vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], + "array[point(2,3),point(2.1,3.4)]" == vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], + "array[point(2.2,-3.4)]" == vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], )); #[cfg(feature = "rust_decimal")] From 82a21c3e5a220ec810f0bfe3b9995334e9dfc8ea Mon Sep 17 00:00:00 2001 From: James Holman Date: Tue, 5 Nov 2024 19:21:32 +1100 Subject: [PATCH 03/12] fix: re-introduce comparison --- tests/postgres/types.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/postgres/types.rs b/tests/postgres/types.rs index 87ca11ba47..64a41eddd5 100644 --- a/tests/postgres/types.rs +++ b/tests/postgres/types.rs @@ -494,13 +494,13 @@ test_type!(_cube>(Postgres, #[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] test_type!(point(Postgres, - "point(2.2,-3.4)" == sqlx::postgres::types::PgPoint { x: 2.2, y:-3.4 }, + "point(2.2,-3.4)" @= sqlx::postgres::types::PgPoint { x: 2.2, y:-3.4 }, )); #[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] test_type!(_point>(Postgres, - "array[point(2,3),point(2.1,3.4)]" == vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], - "array[point(2.2,-3.4)]" == vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], + "array[point(2,3),point(2.1,3.4)]" @= vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], + "array[point(2.2,-3.4)]" @= vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], )); #[cfg(feature = "rust_decimal")] From ea3975e600f5ea6ea84fb9878f1e2a054d4f34df Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 18:14:10 +1100 Subject: [PATCH 04/12] fix: test other geometry comparison --- sqlx-test/src/lib.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index 304492e695..7312381587 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -234,6 +234,6 @@ macro_rules! Postgres_query_for_test_prepared_type { #[macro_export] macro_rules! Postgres_query_for_test_prepared_geometric_type { () => { - "SELECT ({0}::text is not distinct from $1::text)::int4, {0}, $2" + "SELECT ({0} ~= $1)::int4, {0}, $2" }; } From 83dcf2a5611353b7917fe70a066f8e323d988b3c Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 18:22:29 +1100 Subject: [PATCH 05/12] test: geometry array equality check --- sqlx-test/src/lib.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index 7312381587..dbc503529b 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -234,6 +234,6 @@ macro_rules! Postgres_query_for_test_prepared_type { #[macro_export] macro_rules! Postgres_query_for_test_prepared_geometric_type { () => { - "SELECT ({0} ~= $1)::int4, {0}, $2" + "SELECT ({0} = $1)::int4, {0}, $2" }; } From ece19befc14760e50b666f5cbb5961b24d86c9bc Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 18:32:24 +1100 Subject: [PATCH 06/12] test: array match for geo arrays geo match for geo only --- sqlx-test/src/lib.rs | 15 ++++++++++++++- tests/postgres/types.rs | 6 +++--- 2 files changed, 17 insertions(+), 4 deletions(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index dbc503529b..fe9296c012 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -51,11 +51,17 @@ macro_rules! test_type { } }; - ($name:ident<$ty:ty>($db:ident, $($text:literal @= $value:expr),+ $(,)?)) => { + ($name:ident<$ty:ty>($db:ident, $($text:literal ~= $value:expr),+ $(,)?)) => { paste::item! { $crate::__test_prepared_type!($name<$ty>($db, $crate::[< $db _query_for_test_prepared_geometric_type >]!(), $($text == $value),+)); } }; + ($name:ident<$ty:ty>($db:ident, $($text:literal = $value:expr),+ $(,)?)) => { + paste::item! { + $crate::__test_prepared_type!($name<$ty>($db, $crate::[< $db _query_for_test_prepared_geometric_type >]!(), $($text == $value),+)); + } + }; + ($name:ident($db:ident, $($text:literal == $value:expr),+ $(,)?)) => { $crate::test_type!($name<$name>($db, $($text == $value),+)); @@ -233,6 +239,13 @@ macro_rules! Postgres_query_for_test_prepared_type { #[macro_export] macro_rules! Postgres_query_for_test_prepared_geometric_type { + () => { + "SELECT ({0} ~= $1)::int4, {0}, $2" + }; +} + +#[macro_export] +macro_rules! Postgres_query_for_test_prepared_geometric_array_type { () => { "SELECT ({0} = $1)::int4, {0}, $2" }; diff --git a/tests/postgres/types.rs b/tests/postgres/types.rs index 64a41eddd5..4a75bec57c 100644 --- a/tests/postgres/types.rs +++ b/tests/postgres/types.rs @@ -494,13 +494,13 @@ test_type!(_cube>(Postgres, #[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] test_type!(point(Postgres, - "point(2.2,-3.4)" @= sqlx::postgres::types::PgPoint { x: 2.2, y:-3.4 }, + "point(2.2,-3.4)" ~= sqlx::postgres::types::PgPoint { x: 2.2, y:-3.4 }, )); #[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] test_type!(_point>(Postgres, - "array[point(2,3),point(2.1,3.4)]" @= vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], - "array[point(2.2,-3.4)]" @= vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], + "array[point(2,3),point(2.1,3.4)]" = vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], + "array[point(2.2,-3.4)]" = vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], )); #[cfg(feature = "rust_decimal")] From a88cf4fd387167aa26ee52632086ec48da246628 Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 18:39:40 +1100 Subject: [PATCH 07/12] fix: prepare geometric array type --- sqlx-test/src/lib.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index fe9296c012..b8c448673e 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -58,7 +58,7 @@ macro_rules! test_type { }; ($name:ident<$ty:ty>($db:ident, $($text:literal = $value:expr),+ $(,)?)) => { paste::item! { - $crate::__test_prepared_type!($name<$ty>($db, $crate::[< $db _query_for_test_prepared_geometric_type >]!(), $($text == $value),+)); + $crate::__test_prepared_type!($name<$ty>($db, $crate::[< $db _query_for_test_prepared_geometric_array_type >]!(), $($text == $value),+)); } }; From caea709454e2b34f14732c79b1d054ba4caa6f07 Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 18:49:33 +1100 Subject: [PATCH 08/12] fix: update array comparison --- sqlx-test/src/lib.rs | 4 ++-- tests/postgres/types.rs | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index b8c448673e..e5081ac5ae 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -56,7 +56,7 @@ macro_rules! test_type { $crate::__test_prepared_type!($name<$ty>($db, $crate::[< $db _query_for_test_prepared_geometric_type >]!(), $($text == $value),+)); } }; - ($name:ident<$ty:ty>($db:ident, $($text:literal = $value:expr),+ $(,)?)) => { + ($name:ident<$ty:ty>($db:ident, $($text:literal @= $value:expr),+ $(,)?)) => { paste::item! { $crate::__test_prepared_type!($name<$ty>($db, $crate::[< $db _query_for_test_prepared_geometric_array_type >]!(), $($text == $value),+)); } @@ -247,6 +247,6 @@ macro_rules! Postgres_query_for_test_prepared_geometric_type { #[macro_export] macro_rules! Postgres_query_for_test_prepared_geometric_array_type { () => { - "SELECT ({0} = $1)::int4, {0}, $2" + "SELECT ({0} @= $1)::int4, {0}, $2" }; } diff --git a/tests/postgres/types.rs b/tests/postgres/types.rs index 4a75bec57c..4d10d66d8f 100644 --- a/tests/postgres/types.rs +++ b/tests/postgres/types.rs @@ -499,8 +499,8 @@ test_type!(point(Postgres, #[cfg(any(postgres_12, postgres_13, postgres_14, postgres_15))] test_type!(_point>(Postgres, - "array[point(2,3),point(2.1,3.4)]" = vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], - "array[point(2.2,-3.4)]" = vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], + "array[point(2,3),point(2.1,3.4)]" @= vec![sqlx::postgres::types::PgPoint { x:2., y: 3. }, sqlx::postgres::types::PgPoint { x:2.1, y: 3.4 }], + "array[point(2.2,-3.4)]" @= vec![sqlx::postgres::types::PgPoint { x: 2.2, y: -3.4 }], )); #[cfg(feature = "rust_decimal")] From 7f6df9f1ab0306316e58ffd97b5ed1ce351aa8ce Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 18:56:54 +1100 Subject: [PATCH 09/12] fix: try another method of geometric array comparison --- sqlx-test/src/lib.rs | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index e5081ac5ae..da97fc03d0 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -247,6 +247,10 @@ macro_rules! Postgres_query_for_test_prepared_geometric_type { #[macro_export] macro_rules! Postgres_query_for_test_prepared_geometric_array_type { () => { - "SELECT ({0} @= $1)::int4, {0}, $2" + "SELECT ( + SELECT bool_and(geo1 ~= geo2) + FROM unnest({0}) as geo1, + unnest($1) as geo2 + )::int4, {0}, $2" }; } From fe99e4884c0b8def07565b870d730830d60b944a Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 19:04:32 +1100 Subject: [PATCH 10/12] fix: one more geometry match tests --- sqlx-test/src/lib.rs | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index da97fc03d0..5934cf4814 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -247,10 +247,8 @@ macro_rules! Postgres_query_for_test_prepared_geometric_type { #[macro_export] macro_rules! Postgres_query_for_test_prepared_geometric_array_type { () => { - "SELECT ( - SELECT bool_and(geo1 ~= geo2) - FROM unnest({0}) as geo1, - unnest($1) as geo2 - )::int4, {0}, $2" + "SELECT bool_and(geo1.geometry ~= geo2.geometry)::int4 + FROM unnest({0}) WITH ORDINALITY AS geo1(geometry, idx) + JOIN unnest($1) WITH ORDINALITY AS geo2(geometry, idx) ON geo1.idx = geo2.idx;" }; } From 6a0548bd42c16f081957487f951c05b5e9cf1edc Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 19:12:57 +1100 Subject: [PATCH 11/12] fix: correct query syntax --- sqlx-test/src/lib.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index 5934cf4814..7d6081ac6c 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -249,6 +249,6 @@ macro_rules! Postgres_query_for_test_prepared_geometric_array_type { () => { "SELECT bool_and(geo1.geometry ~= geo2.geometry)::int4 FROM unnest({0}) WITH ORDINALITY AS geo1(geometry, idx) - JOIN unnest($1) WITH ORDINALITY AS geo2(geometry, idx) ON geo1.idx = geo2.idx;" + JOIN unnest($1) WITH ORDINALITY AS geo2(geometry, idx) ON geo1.idx = geo2.idx, {0}, $2" }; } From 184a0ef271010878a1deec3ae9d804b302211648 Mon Sep 17 00:00:00 2001 From: James Holman Date: Wed, 6 Nov 2024 19:42:24 +1100 Subject: [PATCH 12/12] test: geometry test further --- sqlx-test/src/lib.rs | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/sqlx-test/src/lib.rs b/sqlx-test/src/lib.rs index 7d6081ac6c..cc77f38dba 100644 --- a/sqlx-test/src/lib.rs +++ b/sqlx-test/src/lib.rs @@ -247,8 +247,6 @@ macro_rules! Postgres_query_for_test_prepared_geometric_type { #[macro_export] macro_rules! Postgres_query_for_test_prepared_geometric_array_type { () => { - "SELECT bool_and(geo1.geometry ~= geo2.geometry)::int4 - FROM unnest({0}) WITH ORDINALITY AS geo1(geometry, idx) - JOIN unnest($1) WITH ORDINALITY AS geo2(geometry, idx) ON geo1.idx = geo2.idx, {0}, $2" + "SELECT (SELECT bool_and(geo1.geometry ~= geo2.geometry) FROM unnest({0}) WITH ORDINALITY AS geo1(geometry, idx) JOIN unnest($1) WITH ORDINALITY AS geo2(geometry, idx) ON geo1.idx = geo2.idx)::int4, {0}, $2" }; }