mirror of
https://github.com/zhigang1992/graphql-engine.git
synced 2026-06-19 18:03:29 +08:00
Instead of 'WITH some_alias (SELECT * from some_func()) SELECT <rows> FROM some_alias' for SQL function queries, Use 'SELECT <rows> FROM some_func() AS some_alias'
This commit is contained in:
committed by
Alexis King
parent
3f8a1d9ebf
commit
9fe6070663
@@ -108,7 +108,7 @@ fromSelSet fldTy flds =
|
||||
colMapping = riMapping relInfo
|
||||
rn = riName relInfo
|
||||
if isAgg then do
|
||||
aggSel <- fromAggField relTN colGNameMap tableFilter tableLimit fld
|
||||
aggSel <- fromAggField (RS.FromTable relTN) colGNameMap tableFilter tableLimit fld
|
||||
return $ RS.FArr $ RS.ASAgg $ RS.AnnRelG rn colMapping aggSel
|
||||
else do
|
||||
annSel <- fromField (RS.FromTable relTN) colGNameMap tableFilter tableLimit fld
|
||||
@@ -423,20 +423,19 @@ fromAggField
|
||||
:: ( MonadReusability m, MonadError QErr m, MonadReader r m, Has FieldMap r
|
||||
, Has OrdByCtx r, Has SQLGenCtx r
|
||||
)
|
||||
=> QualifiedTable
|
||||
=> RS.SelectFromG UnresolvedVal
|
||||
-> PGColGNameMap
|
||||
-> AnnBoolExpPartialSQL
|
||||
-> Maybe Int
|
||||
-> Field -> m AnnAggSel
|
||||
fromAggField tn colGNameMap permFilter permLimit fld = fieldAsPath fld $ do
|
||||
fromAggField selectFrom colGNameMap permFilter permLimit fld = fieldAsPath fld $ do
|
||||
tableArgs <- parseTableArgs colGNameMap args
|
||||
aggSelFlds <- fromAggSelSet colGNameMap (_fType fld) (_fSelSet fld)
|
||||
let unresolvedPermFltr =
|
||||
fmapAnnBoolExp partialSQLExpToUnresolvedVal permFilter
|
||||
let tabFrom = RS.FromTable tn
|
||||
tabPerm = RS.TablePerm unresolvedPermFltr permLimit
|
||||
let tabPerm = RS.TablePerm unresolvedPermFltr permLimit
|
||||
strfyNum <- stringifyNum <$> asks getter
|
||||
return $ RS.AnnSelG aggSelFlds tabFrom tabPerm tableArgs strfyNum
|
||||
return $ RS.AnnSelG aggSelFlds selectFrom tabPerm tableArgs strfyNum
|
||||
where
|
||||
args = _fArguments fld
|
||||
|
||||
@@ -447,7 +446,7 @@ convertAggSelect
|
||||
=> SelOpCtx -> Field -> m QueryRootFldUnresolved
|
||||
convertAggSelect opCtx fld =
|
||||
withPathK "selectionSet" $ QRFAgg <$>
|
||||
fromAggField qt colGNameMap permFilter permLimit fld
|
||||
fromAggField (RS.FromTable qt) colGNameMap permFilter permLimit fld
|
||||
-- return $ RS.selectAggQuerySQL selData
|
||||
where
|
||||
SelOpCtx qt _ colGNameMap permFilter permLimit = opCtx
|
||||
@@ -483,17 +482,16 @@ parseFunctionArgs argSeq argFn val = flip withObject val $ \_ obj -> do
|
||||
throw400 NotSupported "Non default arguments cannot be omitted"
|
||||
else pure Nothing
|
||||
|
||||
fromFuncQueryField
|
||||
makeFunctionSelectFrom
|
||||
:: (MonadReusability m, MonadError QErr m)
|
||||
=> (Field -> m s)
|
||||
-> QualifiedFunction
|
||||
=> QualifiedFunction
|
||||
-> FunctionArgSeq
|
||||
-> Field
|
||||
-> m (RS.AnnFnSelG s UnresolvedVal)
|
||||
fromFuncQueryField fn qf argSeq fld = fieldAsPath fld $ do
|
||||
-> m (RS.SelectFromG UnresolvedVal)
|
||||
makeFunctionSelectFrom qf argSeq fld = do
|
||||
funcArgsM <- withArgM (_fArguments fld) "args" $ parseFunctionArgs argSeq argFn
|
||||
let funcArgs = fromMaybe RS.emptyFunctionArgsExp funcArgsM
|
||||
RS.AnnFnSel qf funcArgs <$> fn fld
|
||||
let funcArgs = RS.AEInput <$> fromMaybe RS.emptyFunctionArgsExp funcArgsM
|
||||
pure $ RS.FromFunction qf funcArgs
|
||||
where
|
||||
argFn (IAUserProvided val) = IFAUnknown val
|
||||
argFn (IASessionVariables argName) = IFAKnown argName UVSession
|
||||
@@ -508,10 +506,11 @@ convertFuncQuerySimple
|
||||
)
|
||||
=> FuncQOpCtx -> Field -> m QueryRootFldUnresolved
|
||||
convertFuncQuerySimple funcOpCtx fld =
|
||||
withPathK "selectionSet" $ QRFFnSimple <$> fromFuncQueryField
|
||||
(fromField (RS.FromTable qt) colGNameMap permFilter permLimit) qf argSeq fld
|
||||
withPathK "selectionSet" $ fieldAsPath fld $ do
|
||||
selectFrom <- makeFunctionSelectFrom qf argSeq fld
|
||||
QRFSimple <$> fromField selectFrom colGNameMap permFilter permLimit fld
|
||||
where
|
||||
FuncQOpCtx qt _ colGNameMap permFilter permLimit qf argSeq = funcOpCtx
|
||||
FuncQOpCtx qf argSeq _ colGNameMap permFilter permLimit = funcOpCtx
|
||||
|
||||
convertFuncQueryAgg
|
||||
:: ( MonadReusability m
|
||||
@@ -523,17 +522,16 @@ convertFuncQueryAgg
|
||||
)
|
||||
=> FuncQOpCtx -> Field -> m QueryRootFldUnresolved
|
||||
convertFuncQueryAgg funcOpCtx fld =
|
||||
withPathK "selectionSet" $ QRFFnAgg <$> fromFuncQueryField
|
||||
(fromAggField qt colGNameMap permFilter permLimit) qf argSeq fld
|
||||
withPathK "selectionSet" $ fieldAsPath fld $ do
|
||||
selectFrom <- makeFunctionSelectFrom qf argSeq fld
|
||||
QRFAgg <$> fromAggField selectFrom colGNameMap permFilter permLimit fld
|
||||
where
|
||||
FuncQOpCtx qt _ colGNameMap permFilter permLimit qf argSeq = funcOpCtx
|
||||
FuncQOpCtx qf argSeq _ colGNameMap permFilter permLimit = funcOpCtx
|
||||
|
||||
data QueryRootFldAST v
|
||||
= QRFPk !(RS.AnnSimpleSelG v)
|
||||
| QRFSimple !(RS.AnnSimpleSelG v)
|
||||
| QRFAgg !(RS.AnnAggSelG v)
|
||||
| QRFFnSimple !(RS.AnnFnSelSimpleG v)
|
||||
| QRFFnAgg !(RS.AnnFnSelAggG v)
|
||||
deriving (Show, Eq)
|
||||
|
||||
type QueryRootFldUnresolved = QueryRootFldAST UnresolvedVal
|
||||
@@ -548,13 +546,9 @@ traverseQueryRootFldAST f = \case
|
||||
QRFPk s -> QRFPk <$> RS.traverseAnnSimpleSel f s
|
||||
QRFSimple s -> QRFSimple <$> RS.traverseAnnSimpleSel f s
|
||||
QRFAgg s -> QRFAgg <$> RS.traverseAnnAggSel f s
|
||||
QRFFnSimple s -> QRFFnSimple <$> RS.traverseAnnFnSimple f s
|
||||
QRFFnAgg s -> QRFFnAgg <$> RS.traverseAnnFnAgg f s
|
||||
|
||||
toPGQuery :: QueryRootFldResolved -> Q.Query
|
||||
toPGQuery = \case
|
||||
QRFPk s -> RS.selectQuerySQL True s
|
||||
QRFSimple s -> RS.selectQuerySQL False s
|
||||
QRFAgg s -> RS.selectAggQuerySQL s
|
||||
QRFFnSimple s -> RS.mkFuncSelectSimple s
|
||||
QRFFnAgg s -> RS.mkFuncSelectAgg s
|
||||
|
||||
@@ -69,13 +69,12 @@ type FunctionArgSeq = Seq.Seq (InputArgument FunctionArgItem)
|
||||
|
||||
data FuncQOpCtx
|
||||
= FuncQOpCtx
|
||||
{ _fqocTable :: !QualifiedTable
|
||||
{ _fqocFunction :: !QualifiedFunction
|
||||
, _fqocArgs :: !FunctionArgSeq
|
||||
, _fqocHeaders :: ![T.Text]
|
||||
, _fqocAllCols :: !PGColGNameMap
|
||||
, _fqocFilter :: !AnnBoolExpPartialSQL
|
||||
, _fqocLimit :: !(Maybe Int)
|
||||
, _fqocFunction :: !QualifiedFunction
|
||||
, _fqocArgs :: !FunctionArgSeq
|
||||
} deriving (Show, Eq)
|
||||
|
||||
data UpdOpCtx
|
||||
|
||||
@@ -414,8 +414,7 @@ getRootFldsRole' tn primCols constraints fields funcs insM
|
||||
|
||||
funcFldHelper f g pFltr pLimit hdrs =
|
||||
flip map funcs $ \fi ->
|
||||
( f $ FuncQOpCtx tn hdrs colGNameMap pFltr pLimit
|
||||
(fiName fi) (mkFuncArgItemSeq fi)
|
||||
( f $ FuncQOpCtx (fiName fi) (mkFuncArgItemSeq fi) hdrs colGNameMap pFltr pLimit
|
||||
, g fi $ fiDescription fi
|
||||
)
|
||||
|
||||
|
||||
@@ -2,8 +2,6 @@ module Hasura.RQL.DML.Select
|
||||
( selectP2
|
||||
, selectQuerySQL
|
||||
, selectAggQuerySQL
|
||||
, mkFuncSelectSimple
|
||||
, mkFuncSelectAgg
|
||||
, convSelectQuery
|
||||
, asSingleRowJsonResp
|
||||
, module Hasura.RQL.DML.Select.Internal
|
||||
@@ -269,20 +267,6 @@ convSelectQuery sessVarBldr prepArgBuilder (DMLQuery qt selQ) = do
|
||||
convSelectQ (_tiFieldInfoMap tabInfo) selPermInfo
|
||||
extSelQ sessVarBldr prepArgBuilder
|
||||
|
||||
mkFuncSelectSimple
|
||||
:: AnnFnSelSimple
|
||||
-> Q.Query
|
||||
mkFuncSelectSimple annFnSel =
|
||||
Q.fromBuilder $ toSQL $
|
||||
mkFuncSelectWith (mkSQLSelect False) annFnSel
|
||||
|
||||
mkFuncSelectAgg
|
||||
:: AnnFnSelAgg
|
||||
-> Q.Query
|
||||
mkFuncSelectAgg annFnSel =
|
||||
Q.fromBuilder $ toSQL $
|
||||
mkFuncSelectWith mkAggSelect annFnSel
|
||||
|
||||
selectP2 :: Bool -> (AnnSimpleSel, DS.Seq Q.PrepArg) -> Q.TxE QErr EncJSON
|
||||
selectP2 asSingleObject (sel, p) =
|
||||
encJFromBS . runIdentity . Q.getRow
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
module Hasura.RQL.DML.Select.Internal
|
||||
( mkSQLSelect
|
||||
, mkAggSelect
|
||||
, mkFuncSelectWith
|
||||
, module Hasura.RQL.DML.Select.Types
|
||||
)
|
||||
where
|
||||
@@ -773,30 +772,3 @@ mkSQLSelect isSingleObject annSel =
|
||||
baseNode = annSelToBaseNode False rootPrefix rootFldName annSel
|
||||
rootFldName = FieldName "root"
|
||||
rootFldAls = S.Alias $ toIden rootFldName
|
||||
|
||||
mkFuncSelectWith
|
||||
:: (AnnSelG a S.SQLExp -> S.Select)
|
||||
-> AnnFnSelG (AnnSelG a S.SQLExp) S.SQLExp
|
||||
-> S.SelectWith
|
||||
mkFuncSelectWith f annFn =
|
||||
S.SelectWith [(funcAls, S.CTESelect funcSel)] $
|
||||
-- we'll need to modify the table from of the underlying
|
||||
-- select to the alias of the select from function
|
||||
f annSel { _asnFrom = newSelFrom }
|
||||
where
|
||||
AnnFnSel qf fnArgs annSel = annFn
|
||||
|
||||
-- SELECT * FROM function_name(args)
|
||||
funcSel = S.mkSelect { S.selFrom = Just $ S.FromExp [frmItem]
|
||||
, S.selExtr = [S.Extractor S.SEStar Nothing]
|
||||
}
|
||||
frmItem = S.mkFuncFromItem qf $ mkSQLFunctionArgs fnArgs
|
||||
|
||||
mkSQLFunctionArgs (FunctionArgsExp positional named) =
|
||||
S.FunctionArgs positional named
|
||||
|
||||
newSelFrom = FromIden $ toIden funcAls
|
||||
|
||||
QualifiedObject sn fn = qf
|
||||
funcAls = S.Alias $ Iden $
|
||||
getSchemaTxt sn <> "_" <> getFunctionTxt fn <> "__result"
|
||||
|
||||
@@ -353,40 +353,6 @@ insertFunctionArg argName index value (FunctionArgsExp positional named) =
|
||||
where
|
||||
insertAt i a = toList . Seq.insertAt i a . Seq.fromList
|
||||
|
||||
data AnnFnSelG s v
|
||||
= AnnFnSel
|
||||
{ _afFn :: !QualifiedFunction
|
||||
, _afFnArgs :: !(FunctionArgsExpG v)
|
||||
, _afSelect :: !s
|
||||
} deriving (Show, Eq)
|
||||
|
||||
traverseAnnFnSel
|
||||
:: (Applicative f)
|
||||
=> (a -> f b) -> (v -> f w)
|
||||
-> AnnFnSelG a v -> f (AnnFnSelG b w)
|
||||
traverseAnnFnSel fs fv (AnnFnSel fn fnArgs s) =
|
||||
AnnFnSel fn <$> traverse fv fnArgs <*> fs s
|
||||
|
||||
type AnnFnSelSimpleG v = AnnFnSelG (AnnSimpleSelG v) v
|
||||
type AnnFnSelSimple = AnnFnSelSimpleG S.SQLExp
|
||||
|
||||
traverseAnnFnSimple
|
||||
:: (Applicative f)
|
||||
=> (a -> f b)
|
||||
-> AnnFnSelSimpleG a -> f (AnnFnSelSimpleG b)
|
||||
traverseAnnFnSimple f =
|
||||
traverseAnnFnSel (traverseAnnSimpleSel f) f
|
||||
|
||||
type AnnFnSelAggG v = AnnFnSelG (AnnAggSelG v) v
|
||||
type AnnFnSelAgg = AnnFnSelAggG S.SQLExp
|
||||
|
||||
traverseAnnFnAgg
|
||||
:: (Applicative f)
|
||||
=> (a -> f b)
|
||||
-> AnnFnSelAggG a -> f (AnnFnSelAggG b)
|
||||
traverseAnnFnAgg f =
|
||||
traverseAnnFnSel (traverseAnnAggSel f) f
|
||||
|
||||
data BaseNode
|
||||
= BaseNode
|
||||
{ _bnPrefix :: !Iden
|
||||
|
||||
Reference in New Issue
Block a user