{-# LANGUAGE OverloadedStrings #-}

-- This file is part of the Wire Server implementation.
--
-- Copyright (C) 2022 Wire Swiss GmbH <opensource@wire.com>
--
-- This program is free software: you can redistribute it and/or modify it under
-- the terms of the GNU Affero General Public License as published by the Free
-- Software Foundation, either version 3 of the License, or (at your option) any
-- later version.
--
-- This program is distributed in the hope that it will be useful, but WITHOUT
-- ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
-- FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more
-- details.
--
-- You should have received a copy of the GNU Affero General Public License along
-- with this program. If not, see <https://www.gnu.org/licenses/>.

module Wire.API.Team.LegalHold.Internal
  ( LegalHoldService (..),
    legalHoldService,
    viewLegalHoldService,
    LegalHoldClientRequest (..),
  )
where

import Data.Aeson
import Data.Id
import Data.Json.Util
import Data.Misc
import Data.OpenApi qualified as Swagger
import Data.Schema qualified as Schema
import Imports
import Wire.API.Provider
import Wire.API.Provider.Service
import Wire.API.Team.LegalHold
import Wire.API.User.Client.Prekey

data LegalHoldService = LegalHoldService
  { LegalHoldService -> TeamId
legalHoldServiceTeam :: !TeamId,
    LegalHoldService -> HttpsUrl
legalHoldServiceUrl :: !HttpsUrl,
    LegalHoldService -> Fingerprint Rsa
legalHoldServiceFingerprint :: !(Fingerprint Rsa),
    LegalHoldService -> ServiceToken
legalHoldServiceToken :: !ServiceToken,
    LegalHoldService -> ServiceKey
legalHoldServiceKey :: !ServiceKey
  }
  deriving stock (LegalHoldService -> LegalHoldService -> Bool
(LegalHoldService -> LegalHoldService -> Bool)
-> (LegalHoldService -> LegalHoldService -> Bool)
-> Eq LegalHoldService
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: LegalHoldService -> LegalHoldService -> Bool
== :: LegalHoldService -> LegalHoldService -> Bool
$c/= :: LegalHoldService -> LegalHoldService -> Bool
/= :: LegalHoldService -> LegalHoldService -> Bool
Eq, Int -> LegalHoldService -> ShowS
[LegalHoldService] -> ShowS
LegalHoldService -> String
(Int -> LegalHoldService -> ShowS)
-> (LegalHoldService -> String)
-> ([LegalHoldService] -> ShowS)
-> Show LegalHoldService
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> LegalHoldService -> ShowS
showsPrec :: Int -> LegalHoldService -> ShowS
$cshow :: LegalHoldService -> String
show :: LegalHoldService -> String
$cshowList :: [LegalHoldService] -> ShowS
showList :: [LegalHoldService] -> ShowS
Show, (forall x. LegalHoldService -> Rep LegalHoldService x)
-> (forall x. Rep LegalHoldService x -> LegalHoldService)
-> Generic LegalHoldService
forall x. Rep LegalHoldService x -> LegalHoldService
forall x. LegalHoldService -> Rep LegalHoldService x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. LegalHoldService -> Rep LegalHoldService x
from :: forall x. LegalHoldService -> Rep LegalHoldService x
$cto :: forall x. Rep LegalHoldService x -> LegalHoldService
to :: forall x. Rep LegalHoldService x -> LegalHoldService
Generic)

instance ToJSON LegalHoldService where
  toJSON :: LegalHoldService -> Value
toJSON LegalHoldService
s =
    [Pair] -> Value
object ([Pair] -> Value) -> [Pair] -> Value
forall a b. (a -> b) -> a -> b
$
      Key
"team_id"
        Key -> TeamId -> Pair
forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
forall v. ToJSON v => Key -> v -> Pair
.= LegalHoldService -> TeamId
legalHoldServiceTeam LegalHoldService
s
        # "base_url"
        .= legalHoldServiceUrl s
        # "fingerprint"
        .= legalHoldServiceFingerprint s
        # "auth_token"
        .= legalHoldServiceToken s
        # "public_key"
        .= legalHoldServiceKey s
        # []

instance FromJSON LegalHoldService where
  parseJSON :: Value -> Parser LegalHoldService
parseJSON = String
-> (Object -> Parser LegalHoldService)
-> Value
-> Parser LegalHoldService
forall a. String -> (Object -> Parser a) -> Value -> Parser a
withObject String
"LegalHoldService" ((Object -> Parser LegalHoldService)
 -> Value -> Parser LegalHoldService)
-> (Object -> Parser LegalHoldService)
-> Value
-> Parser LegalHoldService
forall a b. (a -> b) -> a -> b
$ \Object
o ->
    TeamId
-> HttpsUrl
-> Fingerprint Rsa
-> ServiceToken
-> ServiceKey
-> LegalHoldService
LegalHoldService
      (TeamId
 -> HttpsUrl
 -> Fingerprint Rsa
 -> ServiceToken
 -> ServiceKey
 -> LegalHoldService)
-> Parser TeamId
-> Parser
     (HttpsUrl
      -> Fingerprint Rsa
      -> ServiceToken
      -> ServiceKey
      -> LegalHoldService)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Object
o
        Object -> Key -> Parser TeamId
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"team_id"
      Parser
  (HttpsUrl
   -> Fingerprint Rsa
   -> ServiceToken
   -> ServiceKey
   -> LegalHoldService)
-> Parser HttpsUrl
-> Parser
     (Fingerprint Rsa -> ServiceToken -> ServiceKey -> LegalHoldService)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
o
        Object -> Key -> Parser HttpsUrl
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"base_url"
      Parser
  (Fingerprint Rsa -> ServiceToken -> ServiceKey -> LegalHoldService)
-> Parser (Fingerprint Rsa)
-> Parser (ServiceToken -> ServiceKey -> LegalHoldService)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
o
        Object -> Key -> Parser (Fingerprint Rsa)
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"fingerprint"
      Parser (ServiceToken -> ServiceKey -> LegalHoldService)
-> Parser ServiceToken -> Parser (ServiceKey -> LegalHoldService)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
o
        Object -> Key -> Parser ServiceToken
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"auth_token"
      Parser (ServiceKey -> LegalHoldService)
-> Parser ServiceKey -> Parser LegalHoldService
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
o
        Object -> Key -> Parser ServiceKey
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"public_key"

legalHoldService :: TeamId -> Fingerprint Rsa -> NewLegalHoldService -> ServiceKey -> LegalHoldService
legalHoldService :: TeamId
-> Fingerprint Rsa
-> NewLegalHoldService
-> ServiceKey
-> LegalHoldService
legalHoldService TeamId
tid Fingerprint Rsa
fpr (NewLegalHoldService HttpsUrl
u ServiceKeyPEM
_ ServiceToken
t) = TeamId
-> HttpsUrl
-> Fingerprint Rsa
-> ServiceToken
-> ServiceKey
-> LegalHoldService
LegalHoldService TeamId
tid HttpsUrl
u Fingerprint Rsa
fpr ServiceToken
t

viewLegalHoldService :: LegalHoldService -> ViewLegalHoldService
viewLegalHoldService :: LegalHoldService -> ViewLegalHoldService
viewLegalHoldService (LegalHoldService TeamId
tid HttpsUrl
u Fingerprint Rsa
fpr ServiceToken
t ServiceKey
k) =
  ViewLegalHoldServiceInfo -> ViewLegalHoldService
ViewLegalHoldService (ViewLegalHoldServiceInfo -> ViewLegalHoldService)
-> ViewLegalHoldServiceInfo -> ViewLegalHoldService
forall a b. (a -> b) -> a -> b
$ TeamId
-> HttpsUrl
-> Fingerprint Rsa
-> ServiceToken
-> ServiceKeyPEM
-> ViewLegalHoldServiceInfo
ViewLegalHoldServiceInfo TeamId
tid HttpsUrl
u Fingerprint Rsa
fpr ServiceToken
t (ServiceKey -> ServiceKeyPEM
serviceKeyPEM ServiceKey
k)

-- | This request is used by Galley to notify Brig that a LegalHold client was requested.
data LegalHoldClientRequest = LegalHoldClientRequest
  { LegalHoldClientRequest -> UserId
lhcrRequester :: !UserId,
    LegalHoldClientRequest -> LastPrekey
lhcrLastPrekey :: !LastPrekey
  }
  deriving stock (LegalHoldClientRequest -> LegalHoldClientRequest -> Bool
(LegalHoldClientRequest -> LegalHoldClientRequest -> Bool)
-> (LegalHoldClientRequest -> LegalHoldClientRequest -> Bool)
-> Eq LegalHoldClientRequest
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: LegalHoldClientRequest -> LegalHoldClientRequest -> Bool
== :: LegalHoldClientRequest -> LegalHoldClientRequest -> Bool
$c/= :: LegalHoldClientRequest -> LegalHoldClientRequest -> Bool
/= :: LegalHoldClientRequest -> LegalHoldClientRequest -> Bool
Eq, Int -> LegalHoldClientRequest -> ShowS
[LegalHoldClientRequest] -> ShowS
LegalHoldClientRequest -> String
(Int -> LegalHoldClientRequest -> ShowS)
-> (LegalHoldClientRequest -> String)
-> ([LegalHoldClientRequest] -> ShowS)
-> Show LegalHoldClientRequest
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> LegalHoldClientRequest -> ShowS
showsPrec :: Int -> LegalHoldClientRequest -> ShowS
$cshow :: LegalHoldClientRequest -> String
show :: LegalHoldClientRequest -> String
$cshowList :: [LegalHoldClientRequest] -> ShowS
showList :: [LegalHoldClientRequest] -> ShowS
Show, (forall x. LegalHoldClientRequest -> Rep LegalHoldClientRequest x)
-> (forall x.
    Rep LegalHoldClientRequest x -> LegalHoldClientRequest)
-> Generic LegalHoldClientRequest
forall x. Rep LegalHoldClientRequest x -> LegalHoldClientRequest
forall x. LegalHoldClientRequest -> Rep LegalHoldClientRequest x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. LegalHoldClientRequest -> Rep LegalHoldClientRequest x
from :: forall x. LegalHoldClientRequest -> Rep LegalHoldClientRequest x
$cto :: forall x. Rep LegalHoldClientRequest x -> LegalHoldClientRequest
to :: forall x. Rep LegalHoldClientRequest x -> LegalHoldClientRequest
Generic)
  deriving (Typeable LegalHoldClientRequest
Typeable LegalHoldClientRequest =>
(Proxy LegalHoldClientRequest
 -> Declare (Definitions Schema) NamedSchema)
-> ToSchema LegalHoldClientRequest
Proxy LegalHoldClientRequest
-> Declare (Definitions Schema) NamedSchema
forall a.
Typeable a =>
(Proxy a -> Declare (Definitions Schema) NamedSchema) -> ToSchema a
$cdeclareNamedSchema :: Proxy LegalHoldClientRequest
-> Declare (Definitions Schema) NamedSchema
declareNamedSchema :: Proxy LegalHoldClientRequest
-> Declare (Definitions Schema) NamedSchema
Swagger.ToSchema, Value -> Parser [LegalHoldClientRequest]
Value -> Parser LegalHoldClientRequest
(Value -> Parser LegalHoldClientRequest)
-> (Value -> Parser [LegalHoldClientRequest])
-> FromJSON LegalHoldClientRequest
forall a.
(Value -> Parser a) -> (Value -> Parser [a]) -> FromJSON a
$cparseJSON :: Value -> Parser LegalHoldClientRequest
parseJSON :: Value -> Parser LegalHoldClientRequest
$cparseJSONList :: Value -> Parser [LegalHoldClientRequest]
parseJSONList :: Value -> Parser [LegalHoldClientRequest]
FromJSON, [LegalHoldClientRequest] -> Value
[LegalHoldClientRequest] -> Encoding
LegalHoldClientRequest -> Value
LegalHoldClientRequest -> Encoding
(LegalHoldClientRequest -> Value)
-> (LegalHoldClientRequest -> Encoding)
-> ([LegalHoldClientRequest] -> Value)
-> ([LegalHoldClientRequest] -> Encoding)
-> ToJSON LegalHoldClientRequest
forall a.
(a -> Value)
-> (a -> Encoding)
-> ([a] -> Value)
-> ([a] -> Encoding)
-> ToJSON a
$ctoJSON :: LegalHoldClientRequest -> Value
toJSON :: LegalHoldClientRequest -> Value
$ctoEncoding :: LegalHoldClientRequest -> Encoding
toEncoding :: LegalHoldClientRequest -> Encoding
$ctoJSONList :: [LegalHoldClientRequest] -> Value
toJSONList :: [LegalHoldClientRequest] -> Value
$ctoEncodingList :: [LegalHoldClientRequest] -> Encoding
toEncodingList :: [LegalHoldClientRequest] -> Encoding
ToJSON) via Schema.Schema LegalHoldClientRequest

instance Schema.ToSchema LegalHoldClientRequest where
  schema :: ValueSchema NamedSwaggerDoc LegalHoldClientRequest
schema =
    Text
-> SchemaP
     SwaggerDoc
     Object
     [Pair]
     LegalHoldClientRequest
     LegalHoldClientRequest
-> ValueSchema NamedSwaggerDoc LegalHoldClientRequest
forall doc doc' a b.
HasObject doc doc' =>
Text
-> SchemaP doc Object [Pair] a b -> SchemaP doc' Value Value a b
Schema.object
      Text
"LegalHoldClientRequest"
      (SchemaP
   SwaggerDoc
   Object
   [Pair]
   LegalHoldClientRequest
   LegalHoldClientRequest
 -> ValueSchema NamedSwaggerDoc LegalHoldClientRequest)
-> SchemaP
     SwaggerDoc
     Object
     [Pair]
     LegalHoldClientRequest
     LegalHoldClientRequest
-> ValueSchema NamedSwaggerDoc LegalHoldClientRequest
forall a b. (a -> b) -> a -> b
$ UserId -> LastPrekey -> LegalHoldClientRequest
LegalHoldClientRequest
        (UserId -> LastPrekey -> LegalHoldClientRequest)
-> SchemaP SwaggerDoc Object [Pair] LegalHoldClientRequest UserId
-> SchemaP
     SwaggerDoc
     Object
     [Pair]
     LegalHoldClientRequest
     (LastPrekey -> LegalHoldClientRequest)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> LegalHoldClientRequest -> UserId
lhcrRequester (LegalHoldClientRequest -> UserId)
-> SchemaP SwaggerDoc Object [Pair] UserId UserId
-> SchemaP SwaggerDoc Object [Pair] LegalHoldClientRequest UserId
forall (p :: * -> * -> *) a a' b.
Profunctor p =>
(a -> a') -> p a' b -> p a b
Schema..= Text
-> SchemaP NamedSwaggerDoc Value Value UserId UserId
-> SchemaP SwaggerDoc Object [Pair] UserId UserId
forall doc' doc a b.
HasField doc' doc =>
Text
-> SchemaP doc' Value Value a b -> SchemaP doc Object [Pair] a b
Schema.field Text
"requester" SchemaP NamedSwaggerDoc Value Value UserId UserId
forall a. ToSchema a => ValueSchema NamedSwaggerDoc a
Schema.schema
        SchemaP
  SwaggerDoc
  Object
  [Pair]
  LegalHoldClientRequest
  (LastPrekey -> LegalHoldClientRequest)
-> SchemaP
     SwaggerDoc Object [Pair] LegalHoldClientRequest LastPrekey
-> SchemaP
     SwaggerDoc
     Object
     [Pair]
     LegalHoldClientRequest
     LegalHoldClientRequest
forall a b.
SchemaP SwaggerDoc Object [Pair] LegalHoldClientRequest (a -> b)
-> SchemaP SwaggerDoc Object [Pair] LegalHoldClientRequest a
-> SchemaP SwaggerDoc Object [Pair] LegalHoldClientRequest b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> LegalHoldClientRequest -> LastPrekey
lhcrLastPrekey (LegalHoldClientRequest -> LastPrekey)
-> SchemaP SwaggerDoc Object [Pair] LastPrekey LastPrekey
-> SchemaP
     SwaggerDoc Object [Pair] LegalHoldClientRequest LastPrekey
forall (p :: * -> * -> *) a a' b.
Profunctor p =>
(a -> a') -> p a' b -> p a b
Schema..= Text
-> SchemaP NamedSwaggerDoc Value Value LastPrekey LastPrekey
-> SchemaP SwaggerDoc Object [Pair] LastPrekey LastPrekey
forall doc' doc a b.
HasField doc' doc =>
Text
-> SchemaP doc' Value Value a b -> SchemaP doc Object [Pair] a b
Schema.field Text
"last_prekey" SchemaP NamedSwaggerDoc Value Value LastPrekey LastPrekey
forall a. ToSchema a => ValueSchema NamedSwaggerDoc a
Schema.schema