Add the missing 'get' path item for RPCs to the OpenAPI output
This commit is contained in:
@@ -21,6 +21,10 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
||||
+ Allows using or across related tables conditions
|
||||
- #1100, Customizable OpenAPI title - @AnthonyFisi
|
||||
|
||||
### Fixed
|
||||
|
||||
- #2651, Add the missing `get` path item for RPCs to the OpenAPI output - @laurenceisla
|
||||
|
||||
## [10.1.2] - 2023-02-01
|
||||
|
||||
### Fixed
|
||||
|
||||
@@ -73,9 +73,15 @@ toSwaggerType colType = case T.takeEnd 2 colType of
|
||||
"[]" -> Just SwaggerArray
|
||||
_ -> Just SwaggerString
|
||||
|
||||
makeSwaggerItemType :: Maybe (SwaggerType t) -> Text -> Maybe (Referenced Schema)
|
||||
makeSwaggerItemType itemType colType = case itemType of
|
||||
Just SwaggerArray -> Just $ Inline (mempty & type_ .~ toSwaggerType (T.dropEnd 2 colType))
|
||||
typeFromArray :: Text -> Text
|
||||
typeFromArray = T.dropEnd 2
|
||||
|
||||
toSwaggerTypeFromArray :: Text -> Maybe (SwaggerType t)
|
||||
toSwaggerTypeFromArray arrType = toSwaggerType $ typeFromArray arrType
|
||||
|
||||
makePropertyItems :: Text -> Maybe (Referenced Schema)
|
||||
makePropertyItems arrType = case toSwaggerType arrType of
|
||||
Just SwaggerArray -> Just $ Inline (mempty & type_ .~ toSwaggerTypeFromArray arrType)
|
||||
_ -> Nothing
|
||||
|
||||
parseDefault :: Text -> Text -> Text
|
||||
@@ -129,7 +135,6 @@ makeProperty tbl rels col = (colName col, Inline s)
|
||||
Just $ T.append (maybe "" (`T.append` "\n\n") $ colDescription col) (T.intercalate "\n" n)
|
||||
else
|
||||
colDescription col
|
||||
pType = toSwaggerType (colType col)
|
||||
s =
|
||||
(mempty :: Schema)
|
||||
& default_ .~ (JSON.decode . toUtf8Lazy . parseDefault (colType col) =<< colDefault col)
|
||||
@@ -137,8 +142,8 @@ makeProperty tbl rels col = (colName col, Inline s)
|
||||
& enum_ .~ e
|
||||
& format ?~ colType col
|
||||
& maxLength .~ (fromIntegral <$> colMaxLen col)
|
||||
& type_ .~ pType
|
||||
& items .~ (SwaggerItemsObject <$> makeSwaggerItemType pType (colType col))
|
||||
& type_ .~ toSwaggerType (colType col)
|
||||
& items .~ (SwaggerItemsObject <$> makePropertyItems (colType col))
|
||||
|
||||
makeProcSchema :: ProcDescription -> Schema
|
||||
makeProcSchema pd =
|
||||
@@ -153,7 +158,7 @@ makeProcProperty (ProcParam n t _ _) = (n, Inline s)
|
||||
where
|
||||
s = (mempty :: Schema)
|
||||
& type_ .~ toSwaggerType t
|
||||
& items .~ (SwaggerItemsObject <$> makeSwaggerItemType (toSwaggerType t) t)
|
||||
& items .~ (SwaggerItemsObject <$> makePropertyItems t)
|
||||
& format ?~ t
|
||||
|
||||
makePreferParam :: [Text] -> Param
|
||||
@@ -175,8 +180,37 @@ makePreferParam ts =
|
||||
"resolution" -> ["resolution=ignore-duplicates", "resolution=merge-duplicates"]
|
||||
_ -> []
|
||||
|
||||
makeProcParam :: ProcDescription -> [Referenced Param]
|
||||
makeProcParam pd =
|
||||
makeProcGetParam :: ProcParam -> Referenced Param
|
||||
makeProcGetParam (ProcParam n t r v) =
|
||||
Inline $ (mempty :: Param)
|
||||
& name .~ n
|
||||
& required ?~ r
|
||||
& schema .~ ParamOther fullSchema
|
||||
where
|
||||
fullSchema = if v then schemaMulti else schemaNotMulti
|
||||
baseSchema = (mempty :: ParamOtherSchema)
|
||||
& in_ .~ ParamQuery
|
||||
schemaNotMulti = baseSchema
|
||||
& format ?~ t
|
||||
& type_ ?~ toParamType (toSwaggerType t)
|
||||
schemaMulti = baseSchema
|
||||
& type_ ?~ fromMaybe SwaggerString (toSwaggerType t)
|
||||
& items ?~ SwaggerItemsPrimitive (Just CollectionMulti)
|
||||
((mempty :: ParamSchema x)
|
||||
& type_ .~ toSwaggerTypeFromArray t
|
||||
& format ?~ typeFromArray t)
|
||||
toParamType paramType = case paramType of
|
||||
-- Array uses {} in query params
|
||||
Just SwaggerArray -> SwaggerString
|
||||
-- Type must be specified in query params
|
||||
Nothing -> SwaggerString
|
||||
_ -> fromJust paramType
|
||||
|
||||
makeProcGetParams :: [ProcParam] -> [Referenced Param]
|
||||
makeProcGetParams = fmap makeProcGetParam
|
||||
|
||||
makeProcPostParams :: ProcDescription -> [Referenced Param]
|
||||
makeProcPostParams pd =
|
||||
[ Inline $ (mempty :: Param)
|
||||
& name .~ "args"
|
||||
& required ?~ True
|
||||
@@ -313,14 +347,19 @@ makeProcPathItem pd = ("/rpc/" ++ toS (pdName pd), pe)
|
||||
-- We strip leading newlines from description so that users can include a blank line between summary and description
|
||||
(pSum, pDesc) = fmap fst &&& fmap (T.dropWhile (=='\n') . snd) $
|
||||
T.breakOn "\n" <$> pdDescription pd
|
||||
postOp = (mempty :: Operation)
|
||||
procOp = (mempty :: Operation)
|
||||
& summary .~ pSum
|
||||
& description .~ mfilter (/="") pDesc
|
||||
& parameters .~ makeProcParam pd
|
||||
& tags .~ Set.fromList ["(rpc) " <> pdName pd]
|
||||
& produces ?~ makeMimeList [MTApplicationJSON, MTSingularJSON]
|
||||
& at 200 ?~ "OK"
|
||||
pe = (mempty :: PathItem) & post ?~ postOp
|
||||
getOp = procOp
|
||||
& parameters .~ makeProcGetParams (pdParams pd)
|
||||
postOp = procOp
|
||||
& parameters .~ makeProcPostParams pd
|
||||
pe = (mempty :: PathItem)
|
||||
& get ?~ getOp
|
||||
& post ?~ postOp
|
||||
|
||||
makeRootPathItem :: (FilePath, PathItem)
|
||||
makeRootPathItem = ("/", p)
|
||||
|
||||
@@ -708,7 +708,153 @@ spec actualPgVersion = describe "OpenAPI" $ do
|
||||
|
||||
describe "RPC" $ do
|
||||
|
||||
it "includes function summary/description and body schema for arguments" $ do
|
||||
it "includes function summary/description and query parameters for arguments in the get path item" $ do
|
||||
r <- simpleBody <$> get "/"
|
||||
|
||||
let method s = key "paths" . key "/rpc/varied_arguments_openapi" . key s
|
||||
args = r ^? method "get" . key "parameters"
|
||||
summary = r ^? method "get" . key "summary"
|
||||
description = r ^? method "get" . key "description"
|
||||
|
||||
liftIO $ do
|
||||
|
||||
summary `shouldBe` Just "An RPC function"
|
||||
|
||||
description `shouldBe` Just "Just a test for RPC function arguments"
|
||||
|
||||
args `shouldBe` Just
|
||||
[aesonQQ|
|
||||
[
|
||||
{
|
||||
"format": "double precision",
|
||||
"in": "query",
|
||||
"name": "double",
|
||||
"required": true,
|
||||
"type": "number"
|
||||
},
|
||||
{
|
||||
"format": "character varying",
|
||||
"in": "query",
|
||||
"name": "varchar",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "boolean",
|
||||
"in": "query",
|
||||
"name": "boolean",
|
||||
"required": true,
|
||||
"type": "boolean"
|
||||
},
|
||||
{
|
||||
"format": "date",
|
||||
"in": "query",
|
||||
"name": "date",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "money",
|
||||
"in": "query",
|
||||
"name": "money",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "enum_menagerie_type",
|
||||
"in": "query",
|
||||
"name": "enum",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "text[]",
|
||||
"in": "query",
|
||||
"name": "text_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "integer[]",
|
||||
"in": "query",
|
||||
"name": "int_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "boolean[]",
|
||||
"in": "query",
|
||||
"name": "bool_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "character[]",
|
||||
"in": "query",
|
||||
"name": "char_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "character varying[]",
|
||||
"in": "query",
|
||||
"name": "varchar_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "bigint[]",
|
||||
"in": "query",
|
||||
"name": "bigint_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "numeric[]",
|
||||
"in": "query",
|
||||
"name": "numeric_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "json[]",
|
||||
"in": "query",
|
||||
"name": "json_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "jsonb[]",
|
||||
"in": "query",
|
||||
"name": "jsonb_arr",
|
||||
"required": true,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "integer",
|
||||
"in": "query",
|
||||
"name": "integer",
|
||||
"required": false,
|
||||
"type": "integer"
|
||||
},
|
||||
{
|
||||
"format": "json",
|
||||
"in": "query",
|
||||
"name": "json",
|
||||
"required": false,
|
||||
"type": "string"
|
||||
},
|
||||
{
|
||||
"format": "jsonb",
|
||||
"in": "query",
|
||||
"name": "jsonb",
|
||||
"required": false,
|
||||
"type": "string"
|
||||
}
|
||||
]
|
||||
|]
|
||||
|
||||
it "includes function summary/description and body schema for arguments in the post path item" $ do
|
||||
r <- simpleBody <$> get "/"
|
||||
|
||||
let method s = key "paths" . key "/rpc/varied_arguments_openapi" . key s
|
||||
@@ -873,6 +1019,26 @@ spec actualPgVersion = describe "OpenAPI" $ do
|
||||
|
||||
liftIO $ params `shouldBe` Just [aesonQQ|["num", "str"]|]
|
||||
|
||||
it "uses a multi collection format when the function has a VARIADIC parameter" $ do
|
||||
r <- simpleBody <$> get "/"
|
||||
let param = r ^? key "paths" . key "/rpc/variadic_param"
|
||||
. key "get" . key "parameters" . nth 0
|
||||
|
||||
liftIO $ param `shouldBe` Just
|
||||
[aesonQQ|
|
||||
{
|
||||
"collectionFormat": "multi",
|
||||
"in": "query",
|
||||
"items": {
|
||||
"format": "text",
|
||||
"type": "string"
|
||||
},
|
||||
"name": "v",
|
||||
"required": false,
|
||||
"type": "array"
|
||||
}
|
||||
|]
|
||||
|
||||
describe "Security" $
|
||||
it "does not include security or security definitions by default" $ do
|
||||
r <- simpleBody <$> get "/"
|
||||
|
||||
Reference in New Issue
Block a user