2021-07-15 15:44:26 +03:00
|
|
|
{-# OPTIONS_GHC -fno-warn-orphans #-}
|
|
|
|
|
|
|
|
module Hasura.Backends.MySQL.Instances.Execute where
|
|
|
|
|
2021-09-24 01:56:37 +03:00
|
|
|
import Data.Aeson qualified as J
|
|
|
|
import Data.String (IsString (..))
|
|
|
|
import Hasura.Backends.MySQL.Connection (runJSONPathQuery)
|
|
|
|
import Hasura.Backends.MySQL.Plan (planQuery)
|
|
|
|
import Hasura.Backends.MySQL.ToQuery (Printer, fromSelect, toQueryFlat, toQueryPretty)
|
|
|
|
import Hasura.Backends.MySQL.Types qualified as MySQL
|
|
|
|
import Hasura.Base.Error (QErr, throw500)
|
|
|
|
import Hasura.EncJSON (encJFromText)
|
|
|
|
import Hasura.GraphQL.Execute.Backend
|
|
|
|
( BackendExecute (..),
|
|
|
|
DBStepInfo (..),
|
|
|
|
PreparedQuery,
|
|
|
|
)
|
|
|
|
import Hasura.GraphQL.Parser (UnpreparedValue)
|
|
|
|
import Hasura.Prelude
|
|
|
|
import Hasura.RQL.IR (QueryDB, SourceRelationshipSelection)
|
|
|
|
import Hasura.RQL.Types (BackendType (MySQL), SourceConfig, SourceName)
|
|
|
|
import Hasura.RQL.Types qualified as RQLTypes
|
|
|
|
import Hasura.Session (UserInfo (..))
|
2021-07-15 15:44:26 +03:00
|
|
|
|
|
|
|
instance BackendExecute 'MySQL where
|
2021-09-24 01:56:37 +03:00
|
|
|
type PreparedQuery 'MySQL = Text
|
2021-07-15 15:44:26 +03:00
|
|
|
type MultiplexedQuery 'MySQL = Void
|
2021-09-24 01:56:37 +03:00
|
|
|
type ExecutionMonad 'MySQL = ExceptT QErr IO
|
|
|
|
mkDBQueryPlan = mysqlDBQueryPlan
|
|
|
|
mkDBMutationPlan = error "mkDBMutationPlan: MySQL backend does not support this operation yet."
|
2021-08-04 14:42:24 +03:00
|
|
|
mkDBSubscriptionPlan _ _ _ _ = error "mkDBSubscriptionPlan: MySQL backend does not support this operation yet."
|
2021-09-24 01:56:37 +03:00
|
|
|
mkDBQueryExplain = error "mkDBQueryExplain: MySQL backend does not support this operation yet."
|
|
|
|
mkLiveQueryExplain _ = error "mkLiveQueryExplain: MySQL backend does not support this operation yet."
|
2021-08-04 14:42:24 +03:00
|
|
|
|
2021-09-22 13:43:05 +03:00
|
|
|
-- NOTE: Currently unimplemented!.
|
|
|
|
--
|
|
|
|
-- This function is just a stub for future implementation; for now it just
|
|
|
|
-- throws a 500 error.
|
|
|
|
mkDBRemoteRelationshipPlan =
|
|
|
|
mysqlDBRemoteRelationshipPlan
|
|
|
|
|
2021-09-24 01:56:37 +03:00
|
|
|
mysqlDBQueryPlan ::
|
|
|
|
forall m.
|
|
|
|
( MonadError QErr m
|
|
|
|
) =>
|
|
|
|
UserInfo ->
|
|
|
|
RQLTypes.SourceName ->
|
|
|
|
RQLTypes.SourceConfig 'MySQL ->
|
|
|
|
QueryDB 'MySQL (Const Void) (UnpreparedValue 'MySQL) ->
|
|
|
|
m (DBStepInfo 'MySQL)
|
2021-09-23 15:37:56 +03:00
|
|
|
mysqlDBQueryPlan userInfo sourceName sourceConfig qrf = do
|
2021-08-04 14:42:24 +03:00
|
|
|
let sessionVariables = _uiSession userInfo
|
|
|
|
statement :: MySQL.Select <- planQuery sessionVariables qrf
|
|
|
|
let printer :: Printer = fromSelect statement
|
|
|
|
queryString = toQueryPretty printer
|
2021-09-24 01:56:37 +03:00
|
|
|
pool = MySQL.scConnectionPool sourceConfig
|
2021-08-04 14:42:24 +03:00
|
|
|
mysqlQuery = encJFromText <$> runJSONPathQuery pool (toQueryFlat printer)
|
|
|
|
pure $ DBStepInfo @'MySQL sourceName sourceConfig (Just $ fromString $ show queryString) mysqlQuery
|
2021-09-22 13:43:05 +03:00
|
|
|
|
|
|
|
--------------------------------------------------------------------------------
|
|
|
|
-- Remote Relationships (e.g. DB-to-DB Joins, remote schema joins, etc.)
|
|
|
|
--------------------------------------------------------------------------------
|
|
|
|
|
|
|
|
-- | Construct an action (i.e. 'DBStepInfo') which can marshal some remote
|
|
|
|
-- relationship information into a form that MySQL can query against.
|
|
|
|
--
|
|
|
|
-- XXX: Currently unimplemented; the Postgres implementation uses
|
|
|
|
-- @jsonb_to_recordset@ to query the remote relationship, however this
|
|
|
|
-- functionality doesn't exist in MYSQL.
|
|
|
|
--
|
|
|
|
-- NOTE: The following typeclass constraints will be necessary when implementing
|
|
|
|
-- this function for real:
|
|
|
|
--
|
|
|
|
-- @
|
|
|
|
-- MonadQueryTags m
|
|
|
|
-- Backend 'MySQL
|
|
|
|
-- @
|
2021-09-24 01:56:37 +03:00
|
|
|
mysqlDBRemoteRelationshipPlan ::
|
|
|
|
forall m.
|
|
|
|
( MonadError QErr m
|
|
|
|
) =>
|
|
|
|
UserInfo ->
|
|
|
|
SourceName ->
|
|
|
|
SourceConfig 'MySQL ->
|
2021-09-22 13:43:05 +03:00
|
|
|
-- | List of json objects, each of which becomes a row of the table.
|
2021-09-24 01:56:37 +03:00
|
|
|
NonEmpty J.Object ->
|
2021-09-22 13:43:05 +03:00
|
|
|
-- | The above objects have this schema
|
|
|
|
--
|
|
|
|
-- XXX: What is this for/what does this mean?
|
2021-09-24 01:56:37 +03:00
|
|
|
HashMap RQLTypes.FieldName (RQLTypes.Column 'MySQL, RQLTypes.ScalarType 'MySQL) ->
|
2021-09-22 13:43:05 +03:00
|
|
|
-- | This is a field name from the lhs that *has* to be selected in the
|
|
|
|
-- response along with the relationship.
|
2021-09-24 01:56:37 +03:00
|
|
|
RQLTypes.FieldName ->
|
|
|
|
(RQLTypes.FieldName, SourceRelationshipSelection 'MySQL (Const Void) UnpreparedValue) ->
|
|
|
|
m (DBStepInfo 'MySQL)
|
2021-09-22 13:43:05 +03:00
|
|
|
mysqlDBRemoteRelationshipPlan _userInfo _sourceName _sourceConfig _lhs _lhsSchema _argumentId _relationship = do
|
|
|
|
throw500 "mkDBRemoteRelationshipPlan: MySQL does not currently support generalized joins."
|