packages feed

hasbolt-extras 0.0.0.15 → 0.0.0.16

raw patch · 6 files changed

+85/−67 lines, 6 filesPVP: major bump suggested

API removals or changes: PVP suggests a major version bump

API changes (from Hackage documentation)

- Database.Bolt.Extras.Graph: GetRequestA :: GetRequestA
- Database.Bolt.Extras.Graph: GetRequestB :: GetRequestB
- Database.Bolt.Extras.Graph: PutRequestB :: PutRequestB
- Database.Bolt.Extras.Graph: data GetRequestA
- Database.Bolt.Extras.Graph: data GetRequestB
- Database.Bolt.Extras.Graph: data PutRequestB
- Database.Bolt.Extras.Graph: type GraphGetResponseA = Graph NodeName NodeResult RelResult
- Database.Bolt.Extras.Graph: type GraphGetResponseB = Graph NodeName Node URelationship
+ Database.Bolt.Extras.Graph: GetRequest :: GetRequest
+ Database.Bolt.Extras.Graph: PutRequest :: PutRequest
+ Database.Bolt.Extras.Graph: data GetRequest
+ Database.Bolt.Extras.Graph: data PutRequest
+ Database.Bolt.Extras.Graph: extractNode :: NodeLike a => NodeName -> GraphGetResponse -> a
+ Database.Bolt.Extras.Graph: extractNodeAeson :: NodeName -> GraphGetResponse -> NodeResult
+ Database.Bolt.Extras.Graph: extractNodeId :: NodeName -> GraphGetResponse -> BoltId
+ Database.Bolt.Extras.Graph: extractRelation :: URelationLike a => NodeName -> NodeName -> GraphGetResponse -> a
+ Database.Bolt.Extras.Graph: extractRelationAeson :: NodeName -> NodeName -> GraphGetResponse -> RelResult
+ Database.Bolt.Extras.Graph: extractRelationId :: NodeName -> NodeName -> GraphGetResponse -> BoltId
+ Database.Bolt.Extras.Graph: type GraphGetResponse = Graph NodeName NodeResult RelResult

Files

CHANGELOG.md view
@@ -6,6 +6,10 @@  ## [Unreleased] +## [0.0.0.16] - 2019-02-01+### Changed+- Optimized query, easy way to extract entities from result graph.+ ## [0.0.0.15] - 2019-01-22 ### Changed - Ability to choose whether to return entity or not in graphs.
example/Main.hs view
@@ -11,7 +11,6 @@ import           Data.Aeson                    (encode) import qualified Data.ByteString.Lazy.Char8    as B (putStrLn) import           Data.Default                  (def)-import           Data.Map.Strict               ((!)) import           Data.Text                     (Text) import           Database.Bolt                 (BoltActionT, BoltCfg (..),                                                 Value (..), close, connect, run)@@ -105,7 +104,7 @@ -- putGraph :: IO () putGraph = do-    putGraphR <- runQueryDB $ makeRequest @PutRequestB [] examplePutGraph+    putGraphR <- runQueryDB $ makeRequest @PutRequest [] examplePutGraph     putStrLn "Uploaded graph: "     print putGraphR @@ -113,8 +112,8 @@ -- getGraphB :: IO () getGraphB = do-    getGraphsR                  <- runQueryDB $ makeRequest @GetRequestB [] exampleGetGraphB-    let nodesA :: [ExampleNode] = fromNode . (! exNodeAVar) . _vertices <$> getGraphsR+    getGraphsR                  <- runQueryDB $ makeRequest @GetRequest [] exampleGetGraphB+    let nodesA :: [ExampleNode] = extractNode exNodeAVar <$> getGraphsR     putStrLn "Downloaded graph and converted to Haskell object: "     print nodesA @@ -122,8 +121,8 @@ -- getGraphA :: IO () getGraphA = do-    getGraphsR <- runQueryDB $ makeRequest @GetRequestA [] exampleGetGraphA-    let nodesA = (! exNodeAVar) . _vertices <$> getGraphsR+    getGraphsR <- runQueryDB $ makeRequest @GetRequest [] exampleGetGraphA+    let nodesA = extractNodeAeson exNodeAVar <$> getGraphsR     putStrLn "Downloaded graph and converted to JSON: "     B.putStrLn . encode $ nodesA 
hasbolt-extras.cabal view
@@ -1,5 +1,5 @@ name:           hasbolt-extras-version:        0.0.0.15+version:        0.0.0.16 synopsis:       Extras for hasbolt library description:    Extras for hasbolt library homepage:       https://github.com/biocad/hasbolt-extras#readme
src/Database/Bolt/Extras/Graph/Internal/Get.hs view
@@ -6,7 +6,6 @@ {-# LANGUAGE RankNTypes          #-} {-# LANGUAGE RecordWildCards     #-} {-# LANGUAGE ScopedTypeVariables #-}-{-# LANGUAGE TypeApplications    #-} {-# LANGUAGE ViewPatterns        #-} {-# OPTIONS_GHC -fno-warn-orphans #-} @@ -31,10 +30,18 @@   , relationName   -- * Graph types   , GraphGetRequest-  , GraphGetResponseA-  , GraphGetResponseB+  , GraphGetResponse+  -- * Helpers to extract entities from result graph+  , extractNode+  , extractRelation+  , extractNodeId+  , extractRelationId+  , extractNodeAeson+  , extractRelationAeson   ) where +import           Control.Lens                                      (at, non, to,+                                                                    (^.)) import           Control.Monad.IO.Class                            (MonadIO) import           Data.Aeson                                        as A (FromJSON (..),                                                                          Result (..),@@ -60,7 +67,8 @@ import           Data.Monoid                                       ((<>)) import           Data.Text                                         (Text, cons,                                                                     intercalate,-                                                                    pack)+                                                                    pack,+                                                                    unpack) import           Database.Bolt                                     as B (BoltActionT,                                                                          Node (..),                                                                          Record,@@ -73,7 +81,9 @@                                                                     URelationLike (..)) import           Database.Bolt.Extras.Graph.Internal.AbstractGraph (Graph,                                                                     NodeName,-                                                                    relationName)+                                                                    relationName,+                                                                    relations,+                                                                    vertices) import           Database.Bolt.Extras.Graph.Internal.Class         (Extractable (..),                                                                     Requestable (..),                                                                     Returnable (..))@@ -217,8 +227,6 @@ -- RESULT -- ---------------------------------------------------------- --- | AESON FORMAT- -- | Result for node in the Aeson like format. -- data NodeResult = NodeResult { nresId     :: BoltId@@ -261,17 +269,6 @@ instance Extractable RelResult where   extract = extractFromJSON -------------------------------------------------------------- | BOLT FORMAT--instance Extractable Node where-  extract :: forall m. MonadIO m => Text -> [Record] -> BoltActionT m [Node]-  extract t rec = fmap toNode <$> extractFromJSON @ _ @ NodeResult t rec--instance Extractable URelationship where-  extract :: forall m. MonadIO m => Text -> [Record] -> BoltActionT m [URelationship]-  extract t rec = fmap toURelation <$> extractFromJSON @ _ @ RelResult t rec- extractFromJSON :: (MonadIO m, FromJSON a) => Text -> [Record] -> BoltActionT m [a] extractFromJSON var = pure . fmap (\r -> case fromJSON (toJSON (r ! var)) of                                         Success parsed -> parsed@@ -290,19 +287,46 @@   fromURelation URelationship{..} = RelResult     urelIdentity urelType  (toJSON   <$> urelProps)  ------------------------------------------------------------- GRAPH TYPES --+-- GRAPH -- ----------------------------------------------------------  -- | The combinations of 'Getter's to load graph from the database. -- type GraphGetRequest = Graph NodeName NodeGetter RelGetter --- | The graph of 'Node's and 'URelationship's which we got from the database using 'GraphGetRequest',--- converted to the Aeson Value like.+-- | The graph of 'Node's and 'URelationship's which we got from the database using 'GraphGetRequest'. ---type GraphGetResponseA = Graph NodeName NodeResult RelResult+type GraphGetResponse = Graph NodeName NodeResult RelResult --- | The graph of 'Node's and 'URelationship's which we got from the database using 'GraphGetRequest',--- converted to the Bolt Value like.----type GraphGetResponseB = Graph NodeName Node URelationship+-- | Some helpers to extract entities from the result graph.++extractNode :: NodeLike a => NodeName -> GraphGetResponse -> a+extractNode var graph = graph ^. vertices . at var . non (errorForNode var) . to (fromNode . toNode)++extractRelation :: URelationLike a => NodeName -> NodeName -> GraphGetResponse -> a+extractRelation stVar enVar graph = graph ^. relations . at (stVar, enVar)+                                  . non (errorForRelation stVar enVar)+                                  . to (fromURelation . toURelation)++extractNodeId :: NodeName -> GraphGetResponse -> BoltId+extractNodeId var graph = graph ^. vertices . at var . non (errorForNode var) . to nresId++extractRelationId :: NodeName -> NodeName -> GraphGetResponse -> BoltId+extractRelationId stVar enVar graph = graph ^. relations . at (stVar, enVar)+                                    . non (errorForRelation stVar enVar)+                                    . to rresId++extractNodeAeson :: NodeName -> GraphGetResponse -> NodeResult+extractNodeAeson var graph = graph ^. vertices . at var . non (errorForNode var)++extractRelationAeson :: NodeName -> NodeName -> GraphGetResponse -> RelResult+extractRelationAeson stVar enVar graph = graph ^. relations . at (stVar, enVar)+                                       . non (errorForRelation stVar enVar)++errorForNode :: NodeName -> a+errorForNode name = error . unpack $ "node with name " <> name <> " doesn't exist"++errorForRelation :: NodeName -> NodeName -> a+errorForRelation stName enName = error . unpack $ "relation between nodes " <>+                                                  stName <> " and " <> enName <>+                                                  " doesn't exist"
src/Database/Bolt/Extras/Graph/Internal/GraphQuery.hs view
@@ -11,9 +11,8 @@ module Database.Bolt.Extras.Graph.Internal.GraphQuery   (     GraphQuery (..)-  , GetRequestA (..)-  , GetRequestB (..)-  , PutRequestB (..)+  , GetRequest (..)+  , PutRequest (..)   , mergeGraphs   ) where @@ -30,9 +29,7 @@                                                                          null,                                                                          pack) import           Database.Bolt                                     (BoltActionT,-                                                                    Node,                                                                     Record,-                                                                    URelationship,                                                                     query) import           Database.Bolt.Extras                              (BoltId, GetBoltId (..)) import           Database.Bolt.Extras.Graph.Internal.AbstractGraph (Graph (..),@@ -83,10 +80,12 @@             -> Text   formQuery customConds graph = [text|$completeRequest                                       $conditionsQ-                                      RETURN DISTINCT $completeReturn|]+                                      WITH DISTINCT $distinctVars+                                      RETURN $completeReturn|]     where       vertices'        = toList (graph ^. vertices)       relations'       = toList (graph ^. relations)+      distinctVars     = intercalate ", " $ fmap fst vertices' ++ fmap (relationName . fst) relations'        (completeRequest, reqConds) = requestEntities @a vertices' relations' @@ -134,29 +133,16 @@ -- GET -- --------------------------------------------------------------------------------------- --- | Get request with result in Aeson format.--- Easy way to show result graphs.----data GetRequestA = GetRequestA---- | Get request with result in Bolt format.--- Easy way to extract results and convert them to another entities (using 'fromNode').+-- | Get request with graph result. ---data GetRequestB = GetRequestB--instance GraphQuery GetRequestA where-  type NodeReq GetRequestA = NodeGetter-  type RelReq  GetRequestA = RelGetter-  type NodeRes GetRequestA = NodeResult-  type RelRes  GetRequestA = RelResult-  requestEntities          = requestGetters+data GetRequest = GetRequest -instance GraphQuery GetRequestB where-  type NodeReq GetRequestB = NodeGetter-  type RelReq  GetRequestB = RelGetter-  type NodeRes GetRequestB = Node-  type RelRes  GetRequestB = URelationship-  requestEntities          = requestGetters+instance GraphQuery GetRequest where+  type NodeReq GetRequest = NodeGetter+  type RelReq  GetRequest = RelGetter+  type NodeRes GetRequest = NodeResult+  type RelRes  GetRequest = RelResult+  requestEntities         = requestGetters  --------------------------------------------------------------------------------------- -- PUT --@@ -164,13 +150,13 @@  -- | Put request in Bolt format with 'BoltId's of uploaded entities as result. ---data PutRequestB = PutRequestB+data PutRequest = PutRequest -instance GraphQuery PutRequestB where-  type NodeReq PutRequestB = PutNode-  type RelReq  PutRequestB = PutRelationship-  type NodeRes PutRequestB = BoltId-  type RelRes  PutRequestB = BoltId+instance GraphQuery PutRequest where+  type NodeReq PutRequest = PutNode+  type RelReq  PutRequest = PutRelationship+  type NodeRes PutRequest = BoltId+  type RelRes  PutRequest = BoltId   requestEntities          = requestPut  -- | Helper function to merge graphs of results, i.e.
src/Database/Bolt/Extras/Internal/Instances.hs view
@@ -11,9 +11,10 @@ import           Data.Aeson.Types                    (Parser) import           Data.Map.Strict                     (Map) import           Data.Text                           (Text)-import           Database.Bolt                       (Value (..))+import           Database.Bolt                       (Node, Value (..)) import qualified Database.Bolt                       as DB (Structure) import           Database.Bolt.Extras.Internal.Types (FromValue (..),+                                                      NodeLike (..),                                                       ToValue (..)) import           Database.Bolt.Extras.Utils          (currentLoc) import           GHC.Float                           (double2Float,@@ -115,3 +116,7 @@             <|> L <$> (parseJSON v :: Parser [Value])             <|> M <$> (parseJSON v :: Parser (Map Text Value))             <|> error "Database.Bolt.Extras.Internal.Instances: could not convert from json Database.Bolt.Value"++instance NodeLike Node where+  toNode   = id+  fromNode = id