fix: detect the correct base type of recursive domains in schema cache for tables and views
In OpenAPI it shows the correct base type in properties' definitions (including enums).
This commit is contained in:
+1
-7
@@ -5,16 +5,10 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||
|
||||
## Unreleased
|
||||
|
||||
### Added
|
||||
|
||||
- Improve the `PGRST106` error when the requested schema is invalid by @laurenceisla in #4089
|
||||
+ It now shows the invalid schema in the `message` field.
|
||||
+ The exposed schemas are now listed in the `hint` instead of the `message` field.
|
||||
- Improve error details of `PGRST301` error by @taimoorzaeem in #4051
|
||||
|
||||
### Fixed
|
||||
|
||||
- Fix `max-affected` preference not failing with RPC when `handling=strict` by @taimoorzaeem in #4100
|
||||
- Fix a property definition's type in OpenAPI not showing the correct base type of a recursive domain by @laurenceisla in #4136
|
||||
|
||||
## [13.0.2] - 2025-06-02
|
||||
|
||||
|
||||
@@ -375,32 +375,40 @@ accessibleFuncs = SQL.Statement sql params decodeFuncs
|
||||
(snd >$< arrayParam HE.text)
|
||||
sql = funcsSqlQuery <> " AND has_function_privilege(p.oid, 'execute')"
|
||||
|
||||
funcsSqlQuery :: SqlQuery
|
||||
funcsSqlQuery = encodeUtf8 [trimming|
|
||||
-- Recursively get the base types of domains
|
||||
WITH
|
||||
baseTypesCte :: Text
|
||||
baseTypesCte = [trimming|
|
||||
-- Recursively get the base types of domains
|
||||
base_types AS (
|
||||
WITH RECURSIVE
|
||||
recurse AS (
|
||||
SELECT
|
||||
oid,
|
||||
typbasetype,
|
||||
COALESCE(NULLIF(typbasetype, 0), oid) AS base
|
||||
typnamespace AS base_namespace,
|
||||
COALESCE(NULLIF(typbasetype, 0), oid) AS base_type
|
||||
FROM pg_type
|
||||
UNION
|
||||
SELECT
|
||||
t.oid,
|
||||
b.typbasetype,
|
||||
COALESCE(NULLIF(b.typbasetype, 0), b.oid) AS base
|
||||
b.typnamespace AS base_namespace,
|
||||
COALESCE(NULLIF(b.typbasetype, 0), b.oid) AS base_type
|
||||
FROM recurse t
|
||||
JOIN pg_type b ON t.typbasetype = b.oid
|
||||
)
|
||||
SELECT
|
||||
oid,
|
||||
base
|
||||
base_namespace,
|
||||
base_type
|
||||
FROM recurse
|
||||
WHERE typbasetype = 0
|
||||
),
|
||||
)
|
||||
|]
|
||||
|
||||
funcsSqlQuery :: SqlQuery
|
||||
funcsSqlQuery = encodeUtf8 [trimming|
|
||||
WITH
|
||||
$baseTypesCte,
|
||||
arguments AS (
|
||||
SELECT
|
||||
oid,
|
||||
@@ -440,7 +448,7 @@ funcsSqlQuery = encodeUtf8 [trimming|
|
||||
-- if any TABLE, INOUT or OUT arguments present, treat as composite
|
||||
or COALESCE(proargmodes::text[] && '{t,b,o}', false)
|
||||
) AS rettype_is_composite,
|
||||
bt.oid <> bt.base as rettype_is_composite_alias,
|
||||
bt.oid <> bt.base_type as rettype_is_composite_alias,
|
||||
p.provolatile,
|
||||
p.provariadic > 0 as hasvariadic,
|
||||
lower((regexp_split_to_array((regexp_split_to_array(iso_config, '='))[2], ','))[1]) AS transaction_isolation_level,
|
||||
@@ -449,7 +457,7 @@ funcsSqlQuery = encodeUtf8 [trimming|
|
||||
LEFT JOIN arguments a ON a.oid = p.oid
|
||||
JOIN pg_namespace pn ON pn.oid = p.pronamespace
|
||||
JOIN base_types bt ON bt.oid = p.prorettype
|
||||
JOIN pg_type t ON t.oid = bt.base
|
||||
JOIN pg_type t ON t.oid = bt.base_type
|
||||
JOIN pg_namespace tn ON tn.oid = t.typnamespace
|
||||
LEFT JOIN pg_class comp ON comp.oid = t.typrelid
|
||||
LEFT JOIN pg_description as d ON d.objoid = p.oid AND d.classoid = 'pg_proc'::regclass
|
||||
@@ -615,6 +623,7 @@ tablesSqlQuery =
|
||||
-- generated columns are only available from pg >= 10 but the query is agnostic to versions. dep.deptype = 'i' is done because there are other 'a' dependencies on PKs
|
||||
encodeUtf8 [trimming|
|
||||
WITH
|
||||
$baseTypesCte,
|
||||
columns AS (
|
||||
SELECT
|
||||
c.oid AS relid,
|
||||
@@ -631,7 +640,7 @@ tablesSqlQuery =
|
||||
CASE
|
||||
WHEN t.typtype = 'd' THEN
|
||||
CASE
|
||||
WHEN bt.typnamespace = 'pg_catalog'::regnamespace THEN format_type(t.typbasetype, NULL::integer)
|
||||
WHEN bt.base_namespace = 'pg_catalog'::regnamespace THEN format_type(bt.base_type, NULL::integer)
|
||||
ELSE format_type(a.atttypid, a.atttypmod)
|
||||
END
|
||||
ELSE
|
||||
@@ -645,7 +654,7 @@ tablesSqlQuery =
|
||||
information_schema._pg_truetypid(a.*, t.*),
|
||||
information_schema._pg_truetypmod(a.*, t.*)
|
||||
)::integer AS character_maximum_length,
|
||||
COALESCE(bt.oid, t.oid) AS base_type,
|
||||
bt.base_type,
|
||||
a.attnum::integer AS position
|
||||
FROM pg_attribute a
|
||||
LEFT JOIN pg_description AS d
|
||||
@@ -656,8 +665,8 @@ tablesSqlQuery =
|
||||
ON a.attrelid = c.oid
|
||||
JOIN pg_type t
|
||||
ON a.atttypid = t.oid
|
||||
LEFT JOIN pg_type bt
|
||||
ON t.typtype = 'd' AND t.typbasetype = bt.oid
|
||||
LEFT JOIN base_types bt
|
||||
ON t.oid = bt.oid
|
||||
LEFT JOIN pg_depend seq
|
||||
ON seq.refobjid = a.attrelid and seq.refobjsubid = a.attnum and seq.deptype = 'i'
|
||||
WHERE
|
||||
|
||||
Reference in New Issue
Block a user