Maintain backward compatibility on GUC headers feature
If pg version >= 9.6 is detected the feature is enabled, also all of the 9.6 dependent tests are moved to their own spec.
This commit is contained in:
committed by
Steve Chávez
parent
b9a591aecb
commit
188f947437
@@ -84,12 +84,9 @@ postgrest conf refDbStructure pool worker =
|
||||
(iTarget apiRequest) (iAction apiRequest)
|
||||
response <- P.use pool $ HT.transaction HT.ReadCommitted txMode handleReq
|
||||
return $ either (pgError authed) identity response
|
||||
when (isResponse503 response) worker
|
||||
when (responseStatus response == status503) worker
|
||||
respond response
|
||||
|
||||
isResponse503 :: Response -> Bool
|
||||
isResponse503 resp = statusCode (responseStatus resp) == 503
|
||||
|
||||
transactionMode :: DbStructure -> Target -> Action -> H.Mode
|
||||
transactionMode structure target action =
|
||||
case action of
|
||||
@@ -252,6 +249,7 @@ app dbStructure conf apiRequest =
|
||||
singular paramsAsSingleObject
|
||||
(contentType == CTTextCSV)
|
||||
(contentType == CTOctetStream) _isReadOnly bField
|
||||
(pgVersion dbStructure)
|
||||
let (tableTotal, queryTotal, body, jsonHeaders) =
|
||||
fromMaybe (Just 0, 0, "[]", "[]") row
|
||||
(status, contentRange) = rangeHeader queryTotal tableTotal
|
||||
|
||||
@@ -19,11 +19,12 @@ module PostgREST.Config ( prettyVersion
|
||||
, readOptions
|
||||
, corsPolicy
|
||||
, minimumPgVersion
|
||||
, PgVersion (..)
|
||||
, pgVersion96
|
||||
, AppConfig (..)
|
||||
)
|
||||
where
|
||||
|
||||
import PostgREST.Types (PgVersion(..))
|
||||
import Control.Applicative
|
||||
import Control.Monad (fail)
|
||||
import Control.Lens (preview)
|
||||
@@ -211,11 +212,9 @@ pathParser =
|
||||
metavar "FILENAME" <>
|
||||
help "Path to configuration file"
|
||||
|
||||
data PgVersion = PgVersion {
|
||||
pgvNum :: Int32
|
||||
, pgvName :: Text
|
||||
}
|
||||
|
||||
-- | Tells the minimum PostgreSQL version required by this version of PostgREST
|
||||
minimumPgVersion :: PgVersion
|
||||
minimumPgVersion = PgVersion 90300 "9.3"
|
||||
|
||||
pgVersion96 :: PgVersion
|
||||
pgVersion96 = PgVersion 90600 "9.6"
|
||||
|
||||
@@ -8,6 +8,7 @@ module PostgREST.DbStructure (
|
||||
, accessibleTables
|
||||
, accessibleProcs
|
||||
, schemaDescription
|
||||
, getPgVersion
|
||||
) where
|
||||
|
||||
import qualified Hasql.Decoders as HD
|
||||
@@ -29,8 +30,8 @@ import GHC.Exts (groupWith)
|
||||
import Protolude
|
||||
import Unsafe (unsafeHead)
|
||||
|
||||
getDbStructure :: Schema -> H.Session DbStructure
|
||||
getDbStructure schema = do
|
||||
getDbStructure :: Schema -> PgVersion -> H.Session DbStructure
|
||||
getDbStructure schema pgVer = do
|
||||
tabs <- H.query () allTables
|
||||
cols <- H.query () $ allColumns tabs
|
||||
syns <- H.query () $ allSynonyms cols
|
||||
@@ -48,6 +49,7 @@ getDbStructure schema = do
|
||||
, dbRelations = rels'
|
||||
, dbPrimaryKeys = keys'
|
||||
, dbProcs = procs
|
||||
, pgVersion = pgVer
|
||||
}
|
||||
|
||||
decodeTables :: HD.Result [Table]
|
||||
@@ -706,3 +708,9 @@ synonymFromRow allCols (s1,t1,c1,s2,t2,c2) = (,) <$> col1 <*> col2
|
||||
col1 = findCol s1 t1 c1
|
||||
col2 = findCol s2 t2 c2
|
||||
findCol s t c = find (\col -> (tableSchema . colTable) col == s && (tableName . colTable) col == t && colName col == c) allCols
|
||||
|
||||
getPgVersion :: H.Session PgVersion
|
||||
getPgVersion = H.query () $ H.statement sql HE.unit versionRow False
|
||||
where
|
||||
sql = "SELECT current_setting('server_version_num')::integer, current_setting('server_version')"
|
||||
versionRow = HD.singleRow $ PgVersion <$> HD.value HD.int4 <*> HD.value HD.text
|
||||
|
||||
@@ -31,6 +31,7 @@ import qualified Hasql.Decoders as HD
|
||||
|
||||
import qualified Data.Aeson as JSON
|
||||
|
||||
import PostgREST.Config (pgVersion96)
|
||||
import PostgREST.RangeQuery (NonnegRange, rangeLimit, rangeOffset, allRange)
|
||||
import Data.Functor.Contravariant (contramap)
|
||||
import qualified Data.HashMap.Strict as HM
|
||||
@@ -143,9 +144,9 @@ createWriteStatement selectQuery mutateQuery wantSingle wantHdrs asCsv rep pKeys
|
||||
| otherwise = asJsonF
|
||||
|
||||
type ProcResults = (Maybe Int64, Int64, ByteString, ByteString)
|
||||
callProc :: QualifiedIdentifier -> JSON.Object -> Bool -> SqlQuery -> SqlQuery ->
|
||||
Bool -> Bool -> Bool -> Bool -> Bool -> Bool -> Maybe FieldName -> H.Query () (Maybe ProcResults)
|
||||
callProc qi params returnsScalar selectQuery countQuery countTotal isSingle paramsAsJson asCsv asBinary isReadOnly binaryField =
|
||||
callProc :: QualifiedIdentifier -> JSON.Object -> Bool -> SqlQuery -> SqlQuery -> Bool ->
|
||||
Bool -> Bool -> Bool -> Bool -> Bool -> Maybe FieldName -> PgVersion -> H.Query () (Maybe ProcResults)
|
||||
callProc qi params returnsScalar selectQuery countQuery countTotal isSingle paramsAsJson asCsv asBinary isReadOnly binaryField pgVer =
|
||||
unicodeStatement sql HE.unit decodeProc True
|
||||
where
|
||||
sql =
|
||||
@@ -155,7 +156,7 @@ callProc qi params returnsScalar selectQuery countQuery countTotal isSingle para
|
||||
{countResultF} AS total_result_set,
|
||||
1 AS page_total,
|
||||
{scalarBodyF} AS body,
|
||||
{responseHeaders} AS headers
|
||||
{responseHeaders} AS response_headers
|
||||
FROM ({selectQuery}) _postgrest_t;|]
|
||||
else [qc|
|
||||
WITH {sourceCTEName} AS (select * from {fromQi qi}({_args}))
|
||||
@@ -163,7 +164,7 @@ callProc qi params returnsScalar selectQuery countQuery countTotal isSingle para
|
||||
{countResultF} AS total_result_set,
|
||||
pg_catalog.count(_postgrest_t) AS page_total,
|
||||
{bodyF} AS body,
|
||||
{responseHeaders} AS headers
|
||||
{responseHeaders} AS response_headers
|
||||
FROM ({selectQuery}) _postgrest_t;|]
|
||||
|
||||
countResultF = if countTotal then "( "<> countQuery <> ")" else "null::bigint" :: Text
|
||||
@@ -172,7 +173,10 @@ callProc qi params returnsScalar selectQuery countQuery countTotal isSingle para
|
||||
else intercalate "," $ map _assignment (HM.toList params)
|
||||
_procName = qiName qi
|
||||
_assignment (n,v) = pgFmtIdent n <> ":=" <> insertableValue v
|
||||
responseHeaders = "coalesce(nullif(current_setting('response.headers', true), ''), '[]')" :: Text -- nullif is used because of https://gist.github.com/steve-chavez/8d7033ea5655096903f3b52f8ed09a15
|
||||
responseHeaders =
|
||||
if pgVer >= pgVersion96
|
||||
then "coalesce(nullif(current_setting('response.headers', true), ''), '[]')" :: Text -- nullif is used because of https://gist.github.com/steve-chavez/8d7033ea5655096903f3b52f8ed09a15
|
||||
else "'[]'" :: Text
|
||||
decodeProc = HD.maybeRow procRow
|
||||
procRow = (,,,) <$> HD.nullableValue HD.int8 <*> HD.value HD.int8
|
||||
<*> HD.value HD.bytea <*> HD.value HD.bytea
|
||||
|
||||
@@ -31,6 +31,7 @@ data DbStructure = DbStructure {
|
||||
, dbRelations :: [Relation]
|
||||
, dbPrimaryKeys :: [PrimaryKey]
|
||||
, dbProcs :: M.HashMap Text ProcDescription
|
||||
, pgVersion :: PgVersion
|
||||
} deriving (Show, Eq)
|
||||
|
||||
data PgArg = PgArg {
|
||||
@@ -271,3 +272,8 @@ toMime CTSingularJSON = "application/vnd.pgrst.object+json"
|
||||
toMime CTOctetStream = "application/octet-stream"
|
||||
toMime CTAny = "*/*"
|
||||
toMime (CTOther ct) = ct
|
||||
|
||||
data PgVersion = PgVersion {
|
||||
pgvNum :: Int32
|
||||
, pgvName :: Text
|
||||
} deriving (Eq, Ord, Show)
|
||||
|
||||
Reference in New Issue
Block a user