1 {-# LANGUAGE DeriveAnyClass #-}
2 {-# LANGUAGE DuplicateRecordFields #-}
4 module Gargantext.API.GraphQL.UserInfo where
7 import Data.Maybe (fromMaybe)
8 import Data.Morpheus.Types
16 import Data.Text (Text)
17 import qualified Data.Text as T
18 import Gargantext.API.Prelude (GargM, GargError)
19 import Gargantext.Database.Admin.Types.Hyperdata
24 import Gargantext.Database.Admin.Types.Hyperdata.Contact
42 import Gargantext.Database.Prelude (CmdCommon)
43 import Gargantext.Database.Query.Table.Node.UpdateOpaleye (updateHyperdata)
44 import Gargantext.Database.Query.Table.User (getUsersWithHyperdata, getUsersWithNodeHyperdata, updateUserEmail)
45 import Gargantext.Database.Schema.User (UserLight(..))
46 import Gargantext.Database.Schema.Node (node_id, node_hyperdata, NodePoly (Node, _node_id))
47 import Gargantext.Prelude
48 import GHC.Generics (Generic)
49 import Gargantext.API.GraphQL.Utils (AuthStatus(Invalid, Valid), authUser)
50 import Gargantext.API.Admin.Types (HasSettings)
52 data UserInfo = UserInfo
56 , ui_title :: Maybe Text
57 , ui_source :: Maybe Text
58 , ui_cwFirstName :: Maybe Text
59 , ui_cwLastName :: Maybe Text
60 , ui_cwCity :: Maybe Text
61 , ui_cwCountry :: Maybe Text
62 , ui_cwOrganization :: [Text]
63 , ui_cwLabTeamDepts :: [Text]
64 , ui_cwOffice :: Maybe Text
65 , ui_cwRole :: Maybe Text
66 , ui_cwTouchPhone :: Maybe Text
67 , ui_cwTouchMail :: Maybe Text -- TODO: Remove. userLight_email should be used instead
68 , ui_cwDescription :: Maybe Text
70 deriving (Generic, Show)
71 instance GQLType UserInfo where
72 description = const $ Just "provides user info"
74 -- | Arguments to the "user info" query.
78 } deriving (Generic, GQLType)
80 -- | Arguments to the "user info" mutation,
85 , ui_username :: Maybe Text
86 , ui_email :: Maybe Text
87 , ui_title :: Maybe Text
88 , ui_source :: Maybe Text
89 , ui_cwFirstName :: Maybe Text
90 , ui_cwLastName :: Maybe Text
91 , ui_cwCity :: Maybe Text
92 , ui_cwCountry :: Maybe Text
93 , ui_cwOrganization :: Maybe [Text]
94 , ui_cwLabTeamDepts :: Maybe [Text]
95 , ui_cwOffice :: Maybe Text
96 , ui_cwRole :: Maybe Text
97 , ui_cwTouchPhone :: Maybe Text
98 , ui_cwTouchMail :: Maybe Text
99 , ui_cwDescription :: Maybe Text
100 } deriving (Generic, GQLType)
102 type GqlM e env = Resolver QUERY e (GargM env GargError)
103 type GqlM' e env err = ResolverM e (GargM env err) Int
105 -- | Function to resolve user from a query.
108 => UserInfoArgs -> GqlM e env [UserInfo]
109 resolveUserInfos UserInfoArgs { user_id } = dbUsers user_id
111 -- | Mutation for user info
113 :: (CmdCommon env, HasSettings env)
114 -- => UserInfoMArgs -> ResolverM e (GargM env err) Int
115 => UserInfoMArgs -> GqlM' e env err
116 updateUserInfo (UserInfoMArgs { ui_id, .. }) = do
117 -- lift $ printDebug "[updateUserInfo] ui_id" ui_id
118 users <- lift (getUsersWithNodeHyperdata ui_id)
120 [] -> panic $ "[updateUserInfo] User with id " <> (T.pack $ show ui_id) <> " doesn't exist."
121 ((UserLight { .. }, node_u):_) -> do
122 testAuthUser <- lift $ authUser (nId node_u) token
124 Invalid -> panic "[updateUserInfo] failed to validate user"
126 let u_hyperdata = node_u ^. node_hyperdata
127 -- lift $ printDebug "[updateUserInfo] u" u
128 let u_hyperdata' = uh ui_titleL ui_title $
129 uh ui_sourceL ui_source $
130 uh ui_cwFirstNameL ui_cwFirstName $
131 uh ui_cwLastNameL ui_cwLastName $
132 uh ui_cwCityL ui_cwCity $
133 uh ui_cwCountryL ui_cwCountry $
134 uh' ui_cwLabTeamDeptsL ui_cwLabTeamDepts $
135 uh' ui_cwOrganizationL ui_cwOrganization $
136 uh ui_cwOfficeL ui_cwOffice $
137 uh ui_cwRoleL ui_cwRole $
138 uh ui_cwTouchMailL ui_cwTouchMail $
139 uh ui_cwTouchPhoneL ui_cwTouchPhone $
140 uh ui_cwDescriptionL ui_cwDescription
142 -- NOTE: We have 1 username and 2 emails: userLight_email and ui_cwTouchMail
143 -- The userLight_email is more important: it is used for login and sending mail.
144 -- Therefore we update ui_cwTouchMail and userLight_email.
145 -- ui_cwTouchMail is to be removed in the future.
146 let u' = UserLight { userLight_email = fromMaybe userLight_email $ view ui_cwTouchMailL u_hyperdata'
148 -- lift $ printDebug "[updateUserInfo] with firstName" u_hyperdata'
149 _ <- lift $ updateHyperdata (node_u ^. node_id) u_hyperdata'
150 _ <- lift $ updateUserEmail u'
151 --let _newUser = toUser (u, u_hyperdata')
154 uh _ Nothing u_hyperdata = u_hyperdata
155 uh lens' (Just val) u_hyperdata = u_hyperdata & lens' ?~ val
156 uh' _ Nothing u_hyperdata = u_hyperdata
157 uh' lens' (Just val) u_hyperdata = u_hyperdata & lens' .~ val
158 nId Node {_node_id} = _node_id
160 -- | Inner function to fetch the user from DB.
163 => Int -> GqlM e env [UserInfo]
165 -- lift $ printDebug "[dbUsers]" user_id
166 -- user <- getUsersWithId user_id
167 -- hyperdata <- getUserHyperdata user_id
168 -- lift (map toUser <$> zip user hyperdata)
169 lift (map toUser <$> (getUsersWithHyperdata user_id))
171 toUser :: (UserLight, HyperdataUser) -> UserInfo
172 toUser (UserLight { .. }, u_hyperdata) =
173 UserInfo { ui_id = userLight_id
174 , ui_username = userLight_username
175 , ui_email = userLight_email
176 , ui_title = u_hyperdata ^. ui_titleL
177 , ui_source = u_hyperdata ^. ui_sourceL
178 , ui_cwFirstName = u_hyperdata ^. ui_cwFirstNameL
179 , ui_cwLastName = u_hyperdata ^. ui_cwLastNameL
180 , ui_cwCity = u_hyperdata ^. ui_cwCityL
181 , ui_cwCountry = u_hyperdata ^. ui_cwCountryL
182 , ui_cwLabTeamDepts = u_hyperdata ^. ui_cwLabTeamDeptsL
183 , ui_cwOrganization = u_hyperdata ^. ui_cwOrganizationL
184 , ui_cwOffice = u_hyperdata ^. ui_cwOfficeL
185 , ui_cwRole = u_hyperdata ^. ui_cwRoleL
186 --, ui_cwTouchMail = u_hyperdata ^. ui_cwTouchMailL
187 , ui_cwTouchMail = Just userLight_email
188 , ui_cwTouchPhone = u_hyperdata ^. ui_cwTouchPhoneL
189 , ui_cwDescription = u_hyperdata ^. ui_cwDescriptionL }
191 sharedL :: Traversal' HyperdataUser HyperdataContact
192 sharedL = hu_shared . _Just
193 ui_titleL :: Traversal' HyperdataUser (Maybe Text)
194 ui_titleL = sharedL . hc_title
195 ui_sourceL :: Traversal' HyperdataUser (Maybe Text)
196 ui_sourceL = sharedL . hc_source
197 contactWhoL :: Traversal' HyperdataUser ContactWho
198 contactWhoL = sharedL . hc_who . _Just
199 ui_cwFirstNameL :: Traversal' HyperdataUser (Maybe Text)
200 ui_cwFirstNameL = contactWhoL . cw_firstName
201 ui_cwLastNameL :: Traversal' HyperdataUser (Maybe Text)
202 ui_cwLastNameL = contactWhoL . cw_lastName
203 contactWhereL :: Traversal' HyperdataUser ContactWhere
204 contactWhereL = sharedL . hc_where . (ix 0)
205 ui_cwCityL :: Traversal' HyperdataUser (Maybe Text)
206 ui_cwCityL = contactWhereL . cw_city
207 ui_cwCountryL :: Traversal' HyperdataUser (Maybe Text)
208 ui_cwCountryL = contactWhereL . cw_country
209 ui_cwLabTeamDeptsL :: Traversal' HyperdataUser [Text]
210 ui_cwLabTeamDeptsL = hu_shared . _Just . (hc_where . (ix 0) . cw_labTeamDepts)
211 ui_cwOrganizationL :: Traversal' HyperdataUser [Text]
212 ui_cwOrganizationL = hu_shared . _Just . (hc_where . (ix 0) . cw_organization)
213 ui_cwOfficeL :: Traversal' HyperdataUser (Maybe Text)
214 ui_cwOfficeL = contactWhereL . cw_office
215 ui_cwRoleL :: Traversal' HyperdataUser (Maybe Text)
216 ui_cwRoleL = contactWhereL . cw_role
217 ui_cwTouchMailL :: Traversal' HyperdataUser (Maybe Text)
218 ui_cwTouchMailL = hu_shared . _Just . (hc_where . (ix 0) . cw_touch . _Just . ct_mail)
219 --ui_cwTouchMailL = contactWhereL . cw_touch . _Just . ct_mail
220 ui_cwTouchPhoneL :: Traversal' HyperdataUser (Maybe Text)
221 ui_cwTouchPhoneL = hu_shared . _Just . (hc_where . (ix 0) . cw_touch . _Just . ct_phone)
222 --ui_cwTouchPhoneL = contactWhereL . cw_touch . _Just . ct_phone
223 ui_cwDescriptionL :: Traversal' HyperdataUser (Maybe Text)
224 ui_cwDescriptionL = contactWhoL . cw_description