]> Git — Sourcephile - gargantext.git/blob - src/Gargantext/Database/Flow/Pairing.hs
[Database] Refactor functions accessing the database
[gargantext.git] / src / Gargantext / Database / Flow / Pairing.hs
1 {-|
2 Module : Gargantext.Database.Flow
3 Description : Database Flow
4 Copyright : (c) CNRS, 2017-Present
5 License : AGPL + CECILL v3
6 Maintainer : team@gargantext.org
7 Stability : experimental
8 Portability : POSIX
9
10 -}
11
12 {-# LANGUAGE QuasiQuotes #-}
13 {-# LANGUAGE NoImplicitPrelude #-}
14 {-# LANGUAGE OverloadedStrings #-}
15 {-# LANGUAGE RankNTypes #-}
16 -- {-# LANGUAGE Arrows #-}
17
18 module Gargantext.Database.Flow.Pairing
19 where
20
21 --import Debug.Trace (trace)
22 import Control.Lens (_Just,view)
23 import Database.PostgreSQL.Simple.SqlQQ (sql)
24 -- import Opaleye
25 -- import Opaleye.Aggregate
26 -- import Control.Arrow (returnA)
27 import Data.Maybe (catMaybes)
28 import Data.Map (Map, fromList)
29 import Safe (lastMay)
30 import qualified Data.Map as DM
31 import Data.Text (Text, toLower)
32 import qualified Data.Text as DT
33 import Gargantext.Prelude hiding (sum)
34 import Gargantext.Database.Schema.Ngrams -- (NgramsType(..))
35 --import Gargantext.Database.Node.Contact -- (HyperdataContact(..))
36 --import Gargantext.Database.Types.Node -- (Hyperdata(..))
37 import Gargantext.Database.Node.Contact
38 import Gargantext.Database.Flow.Utils
39 import Gargantext.Database.Utils (Cmd, runPGSQuery)
40 import Gargantext.Database.Node.Children
41 import Gargantext.Core.Types.Main
42 import Gargantext.Core.Types (NodeType(..))
43
44 -- TODO mv this type in Types Main
45 type Terms = Text
46
47 -- | TODO : add paring policy as parameter
48 pairing :: AnnuaireId -> CorpusId -> Cmd err Int
49 pairing aId cId = do
50 contacts' <- getContacts aId (Just NodeContact)
51 let contactsMap = pairingPolicyToMap toLower $ toMaps extractNgramsT contacts'
52
53 ngramsMap' <- getNgramsTindexed cId Authors
54 let ngramsMap = pairingPolicyToMap lastName ngramsMap'
55
56 let indexedNgrams = pairMaps contactsMap ngramsMap
57
58 insertToNodeNgrams indexedNgrams
59 -- TODO add List
60
61 lastName :: Terms -> Terms
62 lastName texte = DT.toLower $ maybe texte (\x -> if DT.length x > 3 then x else texte) (lastName' texte)
63 where
64 lastName' = lastMay . DT.splitOn " "
65
66 -- TODO: this methods is dangerous (maybe equalities of the result are not taken into account
67 -- emergency demo plan...
68 pairingPolicyToMap :: (Terms -> Terms)
69 -> Map (NgramsT Ngrams) a -> Map (NgramsT Ngrams) a
70 pairingPolicyToMap f = DM.mapKeys (pairingPolicy f)
71
72 pairingPolicy :: (Terms -> Terms) -> NgramsT Ngrams -> NgramsT Ngrams
73 pairingPolicy f (NgramsT nt (Ngrams ng _)) = (NgramsT nt (Ngrams (f ng) 1))
74
75 -- | TODO : use Occurrences in place of Int
76 extractNgramsT :: HyperdataContact -> Map (NgramsT Ngrams) Int
77 extractNgramsT contact = fromList [(NgramsT Authors a' , 1)| a' <- authors ]
78 where
79 authors = map text2ngrams $ catMaybes [view (hc_who . _Just . cw_lastName) contact]
80 --}
81
82
83 pairMaps :: Map (NgramsT Ngrams) (Map ContactId Int)
84 -> Map (NgramsT Ngrams) NgramsId
85 -> Map (NgramsT NgramsIndexed) (Map ContactId Int)
86 pairMaps m1 m2 = DM.fromList $ catMaybes $ map (\(k,n) -> (,) <$> lookup' k m2 <*> Just n) $ DM.toList m1
87 where
88 lookup' k@(NgramsT nt ng) m = case DM.lookup k m of
89 Nothing -> Nothing
90 Just nId -> Just $ NgramsT nt (NgramsIndexed ng nId)
91
92
93 -----------------------------------------------------------------------
94 getNgramsTindexed:: CorpusId -> NgramsType -> Cmd err (Map (NgramsT Ngrams) NgramsId)
95 getNgramsTindexed corpusId ngramsType' = fromList
96 <$> map (\(ngramsId',t,n) -> (NgramsT ngramsType' (Ngrams t n),ngramsId'))
97 <$> selectNgramsTindexed corpusId ngramsType'
98
99 selectNgramsTindexed :: CorpusId -> NgramsType -> Cmd err [(NgramsId, Terms, Int)]
100 selectNgramsTindexed corpusId ngramsType'' = runPGSQuery selectQuery (corpusId, ngramsTypeId ngramsType'')
101 where
102 selectQuery = [sql| SELECT n.id,n.terms,n.n from ngrams n
103 JOIN nodes_ngrams occ ON occ.ngram_id = n.id
104 JOIN nodes_nodes nn ON nn.node2_id = occ.node_id
105
106 WHERE nn.node1_id = ?
107 AND occ.ngrams_type = ?
108 AND occ.node_id = nn.node2_id
109 GROUP BY n.id;
110 |]
111
112 {- | TODO more typed SQL queries
113 selectNgramsTindexed :: CorpusId -> NgramsType -> Query NgramsRead
114 selectNgramsTindexed corpusId ngramsType = proc () -> do
115 nodeNode <- queryNodeNodeTable -< ()
116 nodeNgrams <- queryNodesNgramsTable -< ()
117 ngrams <- queryNgramsTable -< ()
118
119 restrict -< node1_id nodeNode .== pgInt4 corpusId
120 restrict -< node2_id nodeNode .== node_id nodeNgrams
121 restrict -< ngrams_id ngrams .== node_ngrams nodeNgrams
122
123 result <- aggregate groupBy (ngrams_id ngrams)
124 returnA -< result
125 --}
126
127