{-# LANGUAGE DataKinds #-}
{-# LANGUAGE DuplicateRecordFields #-}
{-# LANGUAGE LambdaCase #-}
{-# LANGUAGE NamedFieldPuns #-}
{-# LANGUAGE OverloadedStrings #-}

module Simplex.Chat.Delivery where

import Data.ByteString.Char8 (ByteString)
import Data.Int (Int64)
import Data.Maybe (fromMaybe)
import Data.Time.Clock (UTCTime)
import Simplex.Chat.Messages (GroupChatScopeInfo (..), MessageId)
import Simplex.Chat.Options.DB (FromField (..), ToField (..))
import Simplex.Chat.Protocol
import Simplex.Chat.Types
import Simplex.Chat.Types.Shared
import Simplex.Messaging.Agent.Store.DB (fromTextField_)
import Simplex.Messaging.Encoding.String

type DeliveryWorkerKey = (GroupId, DeliveryWorkerScope)

data DeliveryWorkerScope
  = DWSGroup
  | DWSMemberSupport
  -- | DWSMemberProfileUpdate
  deriving (DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
(DeliveryWorkerScope -> DeliveryWorkerScope -> Bool)
-> (DeliveryWorkerScope -> DeliveryWorkerScope -> Bool)
-> Eq DeliveryWorkerScope
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
== :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
$c/= :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
/= :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
Eq, Eq DeliveryWorkerScope
Eq DeliveryWorkerScope =>
(DeliveryWorkerScope -> DeliveryWorkerScope -> Ordering)
-> (DeliveryWorkerScope -> DeliveryWorkerScope -> Bool)
-> (DeliveryWorkerScope -> DeliveryWorkerScope -> Bool)
-> (DeliveryWorkerScope -> DeliveryWorkerScope -> Bool)
-> (DeliveryWorkerScope -> DeliveryWorkerScope -> Bool)
-> (DeliveryWorkerScope
    -> DeliveryWorkerScope -> DeliveryWorkerScope)
-> (DeliveryWorkerScope
    -> DeliveryWorkerScope -> DeliveryWorkerScope)
-> Ord DeliveryWorkerScope
DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
DeliveryWorkerScope -> DeliveryWorkerScope -> Ordering
DeliveryWorkerScope -> DeliveryWorkerScope -> DeliveryWorkerScope
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: DeliveryWorkerScope -> DeliveryWorkerScope -> Ordering
compare :: DeliveryWorkerScope -> DeliveryWorkerScope -> Ordering
$c< :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
< :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
$c<= :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
<= :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
$c> :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
> :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
$c>= :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
>= :: DeliveryWorkerScope -> DeliveryWorkerScope -> Bool
$cmax :: DeliveryWorkerScope -> DeliveryWorkerScope -> DeliveryWorkerScope
max :: DeliveryWorkerScope -> DeliveryWorkerScope -> DeliveryWorkerScope
$cmin :: DeliveryWorkerScope -> DeliveryWorkerScope -> DeliveryWorkerScope
min :: DeliveryWorkerScope -> DeliveryWorkerScope -> DeliveryWorkerScope
Ord, Int -> DeliveryWorkerScope -> ShowS
[DeliveryWorkerScope] -> ShowS
DeliveryWorkerScope -> String
(Int -> DeliveryWorkerScope -> ShowS)
-> (DeliveryWorkerScope -> String)
-> ([DeliveryWorkerScope] -> ShowS)
-> Show DeliveryWorkerScope
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DeliveryWorkerScope -> ShowS
showsPrec :: Int -> DeliveryWorkerScope -> ShowS
$cshow :: DeliveryWorkerScope -> String
show :: DeliveryWorkerScope -> String
$cshowList :: [DeliveryWorkerScope] -> ShowS
showList :: [DeliveryWorkerScope] -> ShowS
Show)

instance FromField DeliveryWorkerScope where fromField :: FieldParser DeliveryWorkerScope
fromField = (Text -> Maybe DeliveryWorkerScope)
-> FieldParser DeliveryWorkerScope
forall a. Typeable a => (Text -> Maybe a) -> Field -> Ok a
fromTextField_ Text -> Maybe DeliveryWorkerScope
forall a. TextEncoding a => Text -> Maybe a
textDecode

instance ToField DeliveryWorkerScope where toField :: DeliveryWorkerScope -> SQLData
toField = Text -> SQLData
forall a. ToField a => a -> SQLData
toField (Text -> SQLData)
-> (DeliveryWorkerScope -> Text) -> DeliveryWorkerScope -> SQLData
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DeliveryWorkerScope -> Text
forall a. TextEncoding a => a -> Text
textEncode

instance TextEncoding DeliveryWorkerScope where
  textDecode :: Text -> Maybe DeliveryWorkerScope
textDecode = \case
    Text
"group" -> DeliveryWorkerScope -> Maybe DeliveryWorkerScope
forall a. a -> Maybe a
Just DeliveryWorkerScope
DWSGroup
    Text
"member_support" -> DeliveryWorkerScope -> Maybe DeliveryWorkerScope
forall a. a -> Maybe a
Just DeliveryWorkerScope
DWSMemberSupport
    -- "member_profile_update" -> Just DWSMemberProfileUpdate
    Text
_ -> Maybe DeliveryWorkerScope
forall a. Maybe a
Nothing
  textEncode :: DeliveryWorkerScope -> Text
textEncode = \case
    DeliveryWorkerScope
DWSGroup -> Text
"group"
    DeliveryWorkerScope
DWSMemberSupport -> Text
"member_support"
    -- DWSMemberProfileUpdate -> "member_profile_update"

data DeliveryJobScope
  = DJSGroup {DeliveryJobScope -> DeliveryJobSpec
jobSpec :: DeliveryJobSpec}
  | DJSMemberSupport {DeliveryJobScope -> GroupMemberId
supportGMId :: GroupMemberId}
  -- | DJSMemberProfileUpdate
  deriving (Int -> DeliveryJobScope -> ShowS
[DeliveryJobScope] -> ShowS
DeliveryJobScope -> String
(Int -> DeliveryJobScope -> ShowS)
-> (DeliveryJobScope -> String)
-> ([DeliveryJobScope] -> ShowS)
-> Show DeliveryJobScope
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DeliveryJobScope -> ShowS
showsPrec :: Int -> DeliveryJobScope -> ShowS
$cshow :: DeliveryJobScope -> String
show :: DeliveryJobScope -> String
$cshowList :: [DeliveryJobScope] -> ShowS
showList :: [DeliveryJobScope] -> ShowS
Show)

data DeliveryJobSpec
  = DJDeliveryJob {DeliveryJobSpec -> Bool
includePending :: Bool}
  | DJRelayRemoved
  deriving (Int -> DeliveryJobSpec -> ShowS
[DeliveryJobSpec] -> ShowS
DeliveryJobSpec -> String
(Int -> DeliveryJobSpec -> ShowS)
-> (DeliveryJobSpec -> String)
-> ([DeliveryJobSpec] -> ShowS)
-> Show DeliveryJobSpec
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DeliveryJobSpec -> ShowS
showsPrec :: Int -> DeliveryJobSpec -> ShowS
$cshow :: DeliveryJobSpec -> String
show :: DeliveryJobSpec -> String
$cshowList :: [DeliveryJobSpec] -> ShowS
showList :: [DeliveryJobSpec] -> ShowS
Show)

data DeliveryJobSpecTag
  = DJSTDeliveryJob
  | DJSTRelayRemoved
  deriving (Int -> DeliveryJobSpecTag -> ShowS
[DeliveryJobSpecTag] -> ShowS
DeliveryJobSpecTag -> String
(Int -> DeliveryJobSpecTag -> ShowS)
-> (DeliveryJobSpecTag -> String)
-> ([DeliveryJobSpecTag] -> ShowS)
-> Show DeliveryJobSpecTag
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DeliveryJobSpecTag -> ShowS
showsPrec :: Int -> DeliveryJobSpecTag -> ShowS
$cshow :: DeliveryJobSpecTag -> String
show :: DeliveryJobSpecTag -> String
$cshowList :: [DeliveryJobSpecTag] -> ShowS
showList :: [DeliveryJobSpecTag] -> ShowS
Show)

instance FromField DeliveryJobSpecTag where fromField :: FieldParser DeliveryJobSpecTag
fromField = (Text -> Maybe DeliveryJobSpecTag)
-> FieldParser DeliveryJobSpecTag
forall a. Typeable a => (Text -> Maybe a) -> Field -> Ok a
fromTextField_ Text -> Maybe DeliveryJobSpecTag
forall a. TextEncoding a => Text -> Maybe a
textDecode

instance ToField DeliveryJobSpecTag where toField :: DeliveryJobSpecTag -> SQLData
toField = Text -> SQLData
forall a. ToField a => a -> SQLData
toField (Text -> SQLData)
-> (DeliveryJobSpecTag -> Text) -> DeliveryJobSpecTag -> SQLData
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DeliveryJobSpecTag -> Text
forall a. TextEncoding a => a -> Text
textEncode

instance TextEncoding DeliveryJobSpecTag where
  textDecode :: Text -> Maybe DeliveryJobSpecTag
textDecode = \case
    Text
"delivery_job" -> DeliveryJobSpecTag -> Maybe DeliveryJobSpecTag
forall a. a -> Maybe a
Just DeliveryJobSpecTag
DJSTDeliveryJob
    Text
"relay_removed" -> DeliveryJobSpecTag -> Maybe DeliveryJobSpecTag
forall a. a -> Maybe a
Just DeliveryJobSpecTag
DJSTRelayRemoved
    Text
_ -> Maybe DeliveryJobSpecTag
forall a. Maybe a
Nothing
  textEncode :: DeliveryJobSpecTag -> Text
textEncode = \case
    DeliveryJobSpecTag
DJSTDeliveryJob -> Text
"delivery_job"
    DeliveryJobSpecTag
DJSTRelayRemoved -> Text
"relay_removed"

toWorkerScope :: DeliveryJobScope -> DeliveryWorkerScope
toWorkerScope :: DeliveryJobScope -> DeliveryWorkerScope
toWorkerScope = \case
  DJSGroup DeliveryJobSpec
_ -> DeliveryWorkerScope
DWSGroup
  DJSMemberSupport GroupMemberId
_ -> DeliveryWorkerScope
DWSMemberSupport
  -- DJSMemberProfileUpdate -> DWSMemberProfileUpdate

isRelayRemoved :: DeliveryJobScope -> Bool
isRelayRemoved :: DeliveryJobScope -> Bool
isRelayRemoved = \case
  DJSGroup {DeliveryJobSpec
jobSpec :: DeliveryJobScope -> DeliveryJobSpec
jobSpec :: DeliveryJobSpec
jobSpec} -> case DeliveryJobSpec
jobSpec of
    DeliveryJobSpec
DJRelayRemoved -> Bool
True
    DeliveryJobSpec
_ -> Bool
False
  DeliveryJobScope
_ -> Bool
False

jobScopeImpliedSpec :: DeliveryJobScope -> DeliveryJobSpec
jobScopeImpliedSpec :: DeliveryJobScope -> DeliveryJobSpec
jobScopeImpliedSpec = \case
  DJSGroup {DeliveryJobSpec
jobSpec :: DeliveryJobScope -> DeliveryJobSpec
jobSpec :: DeliveryJobSpec
jobSpec} -> DeliveryJobSpec
jobSpec
  DJSMemberSupport {} -> DJDeliveryJob {includePending :: Bool
includePending = Bool
False}

jobSpecImpliedPending :: DeliveryJobSpec -> Bool
jobSpecImpliedPending :: DeliveryJobSpec -> Bool
jobSpecImpliedPending = \case
  DJDeliveryJob {Bool
includePending :: DeliveryJobSpec -> Bool
includePending :: Bool
includePending} -> Bool
includePending
  DeliveryJobSpec
DJRelayRemoved -> Bool
True

infoToDeliveryScope :: GroupInfo -> Maybe GroupChatScopeInfo -> DeliveryJobScope
infoToDeliveryScope :: GroupInfo -> Maybe GroupChatScopeInfo -> DeliveryJobScope
infoToDeliveryScope GroupInfo {GroupMember
membership :: GroupMember
membership :: GroupInfo -> GroupMember
membership} = \case
  Maybe GroupChatScopeInfo
Nothing -> DJSGroup {jobSpec :: DeliveryJobSpec
jobSpec = DJDeliveryJob {includePending :: Bool
includePending = Bool
False}}
  Just GCSIMemberSupport {Maybe GroupMember
groupMember_ :: Maybe GroupMember
groupMember_ :: GroupChatScopeInfo -> Maybe GroupMember
groupMember_} ->
    let supportGMId :: GroupMemberId
supportGMId = GroupMember -> GroupMemberId
groupMemberId' (GroupMember -> GroupMemberId) -> GroupMember -> GroupMemberId
forall a b. (a -> b) -> a -> b
$ GroupMember -> Maybe GroupMember -> GroupMember
forall a. a -> Maybe a -> a
fromMaybe GroupMember
membership Maybe GroupMember
groupMember_
     in DJSMemberSupport {GroupMemberId
supportGMId :: GroupMemberId
supportGMId :: GroupMemberId
supportGMId}

memberEventDeliveryScope :: GroupMember -> Maybe DeliveryJobScope
memberEventDeliveryScope :: GroupMember -> Maybe DeliveryJobScope
memberEventDeliveryScope m :: GroupMember
m@GroupMember {GroupMemberRole
memberRole :: GroupMemberRole
memberRole :: GroupMember -> GroupMemberRole
memberRole, GroupMemberStatus
memberStatus :: GroupMemberStatus
memberStatus :: GroupMember -> GroupMemberStatus
memberStatus}
  | GroupMemberStatus
memberStatus GroupMemberStatus -> GroupMemberStatus -> Bool
forall a. Eq a => a -> a -> Bool
== GroupMemberStatus
GSMemPendingApproval = Maybe DeliveryJobScope
forall a. Maybe a
Nothing
  | GroupMemberStatus
memberStatus GroupMemberStatus -> GroupMemberStatus -> Bool
forall a. Eq a => a -> a -> Bool
== GroupMemberStatus
GSMemPendingReview = DeliveryJobScope -> Maybe DeliveryJobScope
forall a. a -> Maybe a
Just (DeliveryJobScope -> Maybe DeliveryJobScope)
-> DeliveryJobScope -> Maybe DeliveryJobScope
forall a b. (a -> b) -> a -> b
$ DJSMemberSupport {supportGMId :: GroupMemberId
supportGMId = GroupMember -> GroupMemberId
groupMemberId' GroupMember
m}
  | GroupMemberRole
memberRole GroupMemberRole -> GroupMemberRole -> Bool
forall a. Ord a => a -> a -> Bool
>= GroupMemberRole
GRModerator = DeliveryJobScope -> Maybe DeliveryJobScope
forall a. a -> Maybe a
Just DJSGroup {jobSpec :: DeliveryJobSpec
jobSpec = DJDeliveryJob {includePending :: Bool
includePending = Bool
True}}
  | Bool
otherwise = DeliveryJobScope -> Maybe DeliveryJobScope
forall a. a -> Maybe a
Just DJSGroup {jobSpec :: DeliveryJobSpec
jobSpec = DJDeliveryJob {includePending :: Bool
includePending = Bool
False}}

data NewMessageDeliveryTask = NewMessageDeliveryTask
  { NewMessageDeliveryTask -> GroupMemberId
messageId :: MessageId,
    NewMessageDeliveryTask -> DeliveryJobScope
jobScope :: DeliveryJobScope,
    NewMessageDeliveryTask -> Bool
messageFromChannel :: MessageFromChannel
  }
  deriving (Int -> NewMessageDeliveryTask -> ShowS
[NewMessageDeliveryTask] -> ShowS
NewMessageDeliveryTask -> String
(Int -> NewMessageDeliveryTask -> ShowS)
-> (NewMessageDeliveryTask -> String)
-> ([NewMessageDeliveryTask] -> ShowS)
-> Show NewMessageDeliveryTask
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> NewMessageDeliveryTask -> ShowS
showsPrec :: Int -> NewMessageDeliveryTask -> ShowS
$cshow :: NewMessageDeliveryTask -> String
show :: NewMessageDeliveryTask -> String
$cshowList :: [NewMessageDeliveryTask] -> ShowS
showList :: [NewMessageDeliveryTask] -> ShowS
Show)

data MessageDeliveryTask = MessageDeliveryTask
  { MessageDeliveryTask -> GroupMemberId
taskId :: Int64,
    MessageDeliveryTask -> DeliveryJobScope
jobScope :: DeliveryJobScope,
    MessageDeliveryTask -> GroupMemberId
senderGMId :: GroupMemberId,
    MessageDeliveryTask -> MemberId
senderMemberId :: MemberId,
    MessageDeliveryTask -> Text
senderMemberName :: ContactName,
    MessageDeliveryTask -> UTCTime
brokerTs :: UTCTime,
    MessageDeliveryTask -> ChatMessage 'Json
chatMessage :: ChatMessage 'Json,
    MessageDeliveryTask -> Bool
messageFromChannel :: MessageFromChannel
  }
  deriving (Int -> MessageDeliveryTask -> ShowS
[MessageDeliveryTask] -> ShowS
MessageDeliveryTask -> String
(Int -> MessageDeliveryTask -> ShowS)
-> (MessageDeliveryTask -> String)
-> ([MessageDeliveryTask] -> ShowS)
-> Show MessageDeliveryTask
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> MessageDeliveryTask -> ShowS
showsPrec :: Int -> MessageDeliveryTask -> ShowS
$cshow :: MessageDeliveryTask -> String
show :: MessageDeliveryTask -> String
$cshowList :: [MessageDeliveryTask] -> ShowS
showList :: [MessageDeliveryTask] -> ShowS
Show)

deliveryTaskId :: MessageDeliveryTask -> Int64
deliveryTaskId :: MessageDeliveryTask -> GroupMemberId
deliveryTaskId = MessageDeliveryTask -> GroupMemberId
taskId

data DeliveryTaskStatus
  = DTSNew -- created for delivery task worker to pick up and convert into a delivery job
  | DTSProcessed -- processed by delivery task worker, delivery job created, task can be deleted
  | DTSError -- permanent error
  deriving (Int -> DeliveryTaskStatus -> ShowS
[DeliveryTaskStatus] -> ShowS
DeliveryTaskStatus -> String
(Int -> DeliveryTaskStatus -> ShowS)
-> (DeliveryTaskStatus -> String)
-> ([DeliveryTaskStatus] -> ShowS)
-> Show DeliveryTaskStatus
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DeliveryTaskStatus -> ShowS
showsPrec :: Int -> DeliveryTaskStatus -> ShowS
$cshow :: DeliveryTaskStatus -> String
show :: DeliveryTaskStatus -> String
$cshowList :: [DeliveryTaskStatus] -> ShowS
showList :: [DeliveryTaskStatus] -> ShowS
Show)

instance FromField DeliveryTaskStatus where fromField :: FieldParser DeliveryTaskStatus
fromField = (Text -> Maybe DeliveryTaskStatus)
-> FieldParser DeliveryTaskStatus
forall a. Typeable a => (Text -> Maybe a) -> Field -> Ok a
fromTextField_ Text -> Maybe DeliveryTaskStatus
forall a. TextEncoding a => Text -> Maybe a
textDecode

instance ToField DeliveryTaskStatus where toField :: DeliveryTaskStatus -> SQLData
toField = Text -> SQLData
forall a. ToField a => a -> SQLData
toField (Text -> SQLData)
-> (DeliveryTaskStatus -> Text) -> DeliveryTaskStatus -> SQLData
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DeliveryTaskStatus -> Text
forall a. TextEncoding a => a -> Text
textEncode

instance TextEncoding DeliveryTaskStatus where
  textDecode :: Text -> Maybe DeliveryTaskStatus
textDecode = \case
    Text
"new" -> DeliveryTaskStatus -> Maybe DeliveryTaskStatus
forall a. a -> Maybe a
Just DeliveryTaskStatus
DTSNew
    Text
"processed" -> DeliveryTaskStatus -> Maybe DeliveryTaskStatus
forall a. a -> Maybe a
Just DeliveryTaskStatus
DTSProcessed
    Text
"error" -> DeliveryTaskStatus -> Maybe DeliveryTaskStatus
forall a. a -> Maybe a
Just DeliveryTaskStatus
DTSError
    Text
_ -> Maybe DeliveryTaskStatus
forall a. Maybe a
Nothing
  textEncode :: DeliveryTaskStatus -> Text
textEncode = \case
    DeliveryTaskStatus
DTSNew -> Text
"new"
    DeliveryTaskStatus
DTSProcessed -> Text
"processed"
    DeliveryTaskStatus
DTSError -> Text
"error"

data MessageDeliveryJob = MessageDeliveryJob
  { MessageDeliveryJob -> GroupMemberId
jobId :: Int64,
    MessageDeliveryJob -> DeliveryJobScope
jobScope :: DeliveryJobScope,
    MessageDeliveryJob -> Maybe GroupMemberId
singleSenderGMId_ :: Maybe GroupMemberId, -- Just for single-sender deliveries, Nothing for multi-sender deliveries
    MessageDeliveryJob -> ByteString
body :: ByteString,
    MessageDeliveryJob -> Maybe GroupMemberId
cursorGMId_ :: Maybe GroupMemberId
  }
  deriving (Int -> MessageDeliveryJob -> ShowS
[MessageDeliveryJob] -> ShowS
MessageDeliveryJob -> String
(Int -> MessageDeliveryJob -> ShowS)
-> (MessageDeliveryJob -> String)
-> ([MessageDeliveryJob] -> ShowS)
-> Show MessageDeliveryJob
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> MessageDeliveryJob -> ShowS
showsPrec :: Int -> MessageDeliveryJob -> ShowS
$cshow :: MessageDeliveryJob -> String
show :: MessageDeliveryJob -> String
$cshowList :: [MessageDeliveryJob] -> ShowS
showList :: [MessageDeliveryJob] -> ShowS
Show)

deliveryJobId :: MessageDeliveryJob -> Int64
deliveryJobId :: MessageDeliveryJob -> GroupMemberId
deliveryJobId = MessageDeliveryJob -> GroupMemberId
jobId

data DeliveryJobStatus
  = DJSPending -- created for delivery job worker to pick up
  | DJSComplete -- complete by delivery job worker, job can be deleted
  | DJSError -- permanent error
  deriving (Int -> DeliveryJobStatus -> ShowS
[DeliveryJobStatus] -> ShowS
DeliveryJobStatus -> String
(Int -> DeliveryJobStatus -> ShowS)
-> (DeliveryJobStatus -> String)
-> ([DeliveryJobStatus] -> ShowS)
-> Show DeliveryJobStatus
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DeliveryJobStatus -> ShowS
showsPrec :: Int -> DeliveryJobStatus -> ShowS
$cshow :: DeliveryJobStatus -> String
show :: DeliveryJobStatus -> String
$cshowList :: [DeliveryJobStatus] -> ShowS
showList :: [DeliveryJobStatus] -> ShowS
Show)

instance FromField DeliveryJobStatus where fromField :: FieldParser DeliveryJobStatus
fromField = (Text -> Maybe DeliveryJobStatus) -> FieldParser DeliveryJobStatus
forall a. Typeable a => (Text -> Maybe a) -> Field -> Ok a
fromTextField_ Text -> Maybe DeliveryJobStatus
forall a. TextEncoding a => Text -> Maybe a
textDecode

instance ToField DeliveryJobStatus where toField :: DeliveryJobStatus -> SQLData
toField = Text -> SQLData
forall a. ToField a => a -> SQLData
toField (Text -> SQLData)
-> (DeliveryJobStatus -> Text) -> DeliveryJobStatus -> SQLData
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DeliveryJobStatus -> Text
forall a. TextEncoding a => a -> Text
textEncode

instance TextEncoding DeliveryJobStatus where
  textDecode :: Text -> Maybe DeliveryJobStatus
textDecode = \case
    Text
"pending" -> DeliveryJobStatus -> Maybe DeliveryJobStatus
forall a. a -> Maybe a
Just DeliveryJobStatus
DJSPending
    Text
"complete" -> DeliveryJobStatus -> Maybe DeliveryJobStatus
forall a. a -> Maybe a
Just DeliveryJobStatus
DJSComplete
    Text
"error" -> DeliveryJobStatus -> Maybe DeliveryJobStatus
forall a. a -> Maybe a
Just DeliveryJobStatus
DJSError
    Text
_ -> Maybe DeliveryJobStatus
forall a. Maybe a
Nothing
  textEncode :: DeliveryJobStatus -> Text
textEncode = \case
    DeliveryJobStatus
DJSPending -> Text
"pending"
    DeliveryJobStatus
DJSComplete -> Text
"complete"
    DeliveryJobStatus
DJSError -> Text
"error"

-- data MemberProfileUpdateTask = undefined

-- data MemberProfileUpdateJob = undefined