{-# LANGUAGE TemplateHaskell #-}

-- | Types for shards
module Calamity.Gateway.Types (
  ShardC,
  ShardMsg (..),
  ReceivedDiscordMessage (..),
  SentDiscordMessage (..),
  DispatchType (..),
  IdentifyData (..),
  StatusUpdateData (..),
  ResumeData (..),
  RequestGuildMembersData (..),
  IdentifyProps (..),
  ControlMessage (..),
  ShardFlowControl (..),
  Shard (..),
  ShardState (..),
) where

import Calamity.Gateway.DispatchEvents
import Calamity.Gateway.Intents
import Calamity.Internal.Utils (CalamityToJSON (..), CalamityToJSON' (..), (.=), (.?=))
import Calamity.Metrics.Eff
import Calamity.Types.LogEff
import Calamity.Types.Model.Guild.Guild
import Calamity.Types.Model.Presence.Activity
import Calamity.Types.Model.User
import Calamity.Types.Model.Voice
import Calamity.Types.Snowflake
import Control.Concurrent.Async
import Control.Concurrent.Chan.Unagi
import qualified Data.Aeson as Aeson
import Data.Aeson.Optics
import Data.Aeson.Types (parseMaybe)
import qualified Data.Aeson.Types as AT
import Data.Text (Text)
import GHC.Generics
import Network.WebSockets.Connection (Connection)
import Optics
import qualified Polysemy as P
import qualified Polysemy.Async as P
import qualified Polysemy.AtomicState as P

type ShardC r =
  ( P.Members
      '[ LogEff
       , P.AtomicState ShardState
       , P.Embed IO
       , P.Final IO
       , P.Async
       , MetricEff
       ]
      r
  )

data ShardMsg
  = Discord ReceivedDiscordMessage
  | Control ControlMessage
  deriving (Int -> ShardMsg -> ShowS
[ShardMsg] -> ShowS
ShardMsg -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ShardMsg] -> ShowS
$cshowList :: [ShardMsg] -> ShowS
show :: ShardMsg -> String
$cshow :: ShardMsg -> String
showsPrec :: Int -> ShardMsg -> ShowS
$cshowsPrec :: Int -> ShardMsg -> ShowS
Show)

data ReceivedDiscordMessage
  = EvtDispatch Int !DispatchData
  | HeartBeatReq
  | Reconnect
  | InvalidSession Bool
  | Hello Int
  | HeartBeatAck
  deriving (Int -> ReceivedDiscordMessage -> ShowS
[ReceivedDiscordMessage] -> ShowS
ReceivedDiscordMessage -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ReceivedDiscordMessage] -> ShowS
$cshowList :: [ReceivedDiscordMessage] -> ShowS
show :: ReceivedDiscordMessage -> String
$cshow :: ReceivedDiscordMessage -> String
showsPrec :: Int -> ReceivedDiscordMessage -> ShowS
$cshowsPrec :: Int -> ReceivedDiscordMessage -> ShowS
Show)

instance Aeson.FromJSON ReceivedDiscordMessage where
  parseJSON :: Value -> Parser ReceivedDiscordMessage
parseJSON = forall a. String -> (Object -> Parser a) -> Value -> Parser a
Aeson.withObject String
"ReceivedDiscordMessage" forall a b. (a -> b) -> a -> b
$ \Object
v -> do
    Int
op :: Int <- Object
v forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"op"
    case Int
op of
      Int
0 -> do
        Value
d <- Object
v forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"d"
        DispatchType
t <- Object
v forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"t"
        Int
s <- Object
v forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"s"
        Int -> DispatchData -> ReceivedDiscordMessage
EvtDispatch Int
s forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> DispatchType -> Value -> Parser DispatchData
parseDispatchData DispatchType
t Value
d
      Int
1 -> forall (f :: * -> *) a. Applicative f => a -> f a
pure ReceivedDiscordMessage
HeartBeatReq
      Int
7 -> forall (f :: * -> *) a. Applicative f => a -> f a
pure ReceivedDiscordMessage
Reconnect
      Int
9 -> Bool -> ReceivedDiscordMessage
InvalidSession forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Object
v forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"d"
      Int
10 ->
        Int -> ReceivedDiscordMessage
Hello forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> do
          Object
d <- Object
v forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"d"
          Object
d forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"heartbeat_interval"
      Int
11 -> forall (f :: * -> *) a. Applicative f => a -> f a
pure ReceivedDiscordMessage
HeartBeatAck
      Int
_ -> forall (m :: * -> *) a. MonadFail m => String -> m a
fail forall a b. (a -> b) -> a -> b
$ String
"invalid opcode: " forall a. Semigroup a => a -> a -> a
<> forall a. Show a => a -> String
show Int
op

parseDispatchData :: DispatchType -> Aeson.Value -> AT.Parser DispatchData
parseDispatchData :: DispatchType -> Value -> Parser DispatchData
parseDispatchData DispatchType
READY Value
data' = ReadyData -> DispatchData
Ready forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
RESUMED Value
_ = forall (f :: * -> *) a. Applicative f => a -> f a
pure DispatchData
Resumed
parseDispatchData DispatchType
CHANNEL_CREATE Value
data' = Channel -> DispatchData
ChannelCreate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
CHANNEL_UPDATE Value
data' = Channel -> DispatchData
ChannelUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
CHANNEL_DELETE Value
data' = Channel -> DispatchData
ChannelDelete forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
CHANNEL_PINS_UPDATE Value
data' = ChannelPinsUpdateData -> DispatchData
ChannelPinsUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_CREATE Value
data' = Guild -> DispatchData
GuildCreate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_UPDATE Value
data' = UpdatedGuild -> DispatchData
GuildUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_DELETE Value
data' = UnavailableGuild -> DispatchData
GuildDelete forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_BAN_ADD Value
data' = BanData -> DispatchData
GuildBanAdd forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_BAN_REMOVE Value
data' = BanData -> DispatchData
GuildBanRemove forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_EMOJIS_UPDATE Value
data' = GuildEmojisUpdateData -> DispatchData
GuildEmojisUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_INTEGRATIONS_UPDATE Value
data' = GuildIntegrationsUpdateData -> DispatchData
GuildIntegrationsUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_MEMBER_ADD Value
data' = do
  Snowflake Guild
guildID <- forall a. String -> (Object -> Parser a) -> Value -> Parser a
Aeson.withObject String
"GuildMemberAdd.guild_id" (forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"guild_id") Value
data'
  Snowflake Guild -> Member -> DispatchData
GuildMemberAdd Snowflake Guild
guildID forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_MEMBER_REMOVE Value
data' = GuildMemberRemoveData -> DispatchData
GuildMemberRemove forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_MEMBER_UPDATE Value
data' = GuildMemberUpdateData -> DispatchData
GuildMemberUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_MEMBERS_CHUNK Value
data' = GuildMembersChunkData -> DispatchData
GuildMembersChunk forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_ROLE_CREATE Value
data' = GuildRoleData -> DispatchData
GuildRoleCreate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_ROLE_UPDATE Value
data' = GuildRoleData -> DispatchData
GuildRoleUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
GUILD_ROLE_DELETE Value
data' = GuildRoleDeleteData -> DispatchData
GuildRoleDelete forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
INVITE_CREATE Value
data' = InviteCreateData -> DispatchData
InviteCreate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
INVITE_DELETE Value
data' = InviteDeleteData -> DispatchData
InviteDelete forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
MESSAGE_CREATE Value
data' = do
  Message
message <- forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
  let member :: Maybe Member
member =
        forall a b. (a -> Parser b) -> a -> Maybe b
parseMaybe
          ( forall a. String -> (Object -> Parser a) -> Value -> Parser a
Aeson.withObject String
"MessageCreate.member" forall a b. (a -> b) -> a -> b
$ \Object
o -> do
              Object
userObject :: Aeson.Object <- Object
o forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"author"
              Object
memberObject :: Aeson.Object <- Object
o forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"member"
              forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON forall a b. (a -> b) -> a -> b
$ Object -> Value
Aeson.Object (Object
memberObject forall a. Semigroup a => a -> a -> a
<> Key
"user" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= Object
userObject)
          )
          Value
data'

  let user :: Maybe User
user = forall a b. (a -> Parser b) -> a -> Maybe b
parseMaybe forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Value
data' forall k s (is :: IxList) a.
Is k An_AffineFold =>
s -> Optic' k is s a -> Maybe a
^? forall t. AsValue t => Prism' t Object
_Object forall k l m (is :: IxList) (js :: IxList) (ks :: IxList) s t u v a
       b.
(JoinKinds k l m, AppendIndices is js ks) =>
Optic k is s t u v -> Optic l js u v a b -> Optic m ks s t a b
% forall m. Ixed m => Index m -> Optic' (IxKind m) NoIx m (IxValue m)
ix Key
"author"
  forall (f :: * -> *) a. Applicative f => a -> f a
pure forall a b. (a -> b) -> a -> b
$ Message -> Maybe User -> Maybe Member -> DispatchData
MessageCreate Message
message Maybe User
user Maybe Member
member
parseDispatchData DispatchType
MESSAGE_UPDATE Value
data' = do
  UpdatedMessage
message <- forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
  let member :: Maybe Member
member =
        forall a b. (a -> Parser b) -> a -> Maybe b
parseMaybe
          ( forall a. String -> (Object -> Parser a) -> Value -> Parser a
Aeson.withObject String
"MessageCreate.member" forall a b. (a -> b) -> a -> b
$ \Object
o -> do
              Object
userObject :: Aeson.Object <- Object
o forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"author"
              Object
memberObject :: Aeson.Object <- Object
o forall a. FromJSON a => Object -> Key -> Parser a
Aeson..: Key
"member"
              forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON forall a b. (a -> b) -> a -> b
$ Object -> Value
Aeson.Object (Object
memberObject forall a. Semigroup a => a -> a -> a
<> Key
"user" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= Object
userObject)
          )
          Value
data'
  let user :: Maybe User
user = forall a b. (a -> Parser b) -> a -> Maybe b
parseMaybe forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Value
data' forall k s (is :: IxList) a.
Is k An_AffineFold =>
s -> Optic' k is s a -> Maybe a
^? forall t. AsValue t => Prism' t Object
_Object forall k l m (is :: IxList) (js :: IxList) (ks :: IxList) s t u v a
       b.
(JoinKinds k l m, AppendIndices is js ks) =>
Optic k is s t u v -> Optic l js u v a b -> Optic m ks s t a b
% forall m. Ixed m => Index m -> Optic' (IxKind m) NoIx m (IxValue m)
ix Key
"author"
  forall (f :: * -> *) a. Applicative f => a -> f a
pure forall a b. (a -> b) -> a -> b
$ UpdatedMessage -> Maybe User -> Maybe Member -> DispatchData
MessageUpdate UpdatedMessage
message Maybe User
user Maybe Member
member
parseDispatchData DispatchType
MESSAGE_DELETE Value
data' = MessageDeleteData -> DispatchData
MessageDelete forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
MESSAGE_DELETE_BULK Value
data' = MessageDeleteBulkData -> DispatchData
MessageDeleteBulk forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
MESSAGE_REACTION_ADD Value
data' = ReactionEvtData -> DispatchData
MessageReactionAdd forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
MESSAGE_REACTION_REMOVE Value
data' = ReactionEvtData -> DispatchData
MessageReactionRemove forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
MESSAGE_REACTION_REMOVE_ALL Value
data' = MessageReactionRemoveAllData -> DispatchData
MessageReactionRemoveAll forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
PRESENCE_UPDATE Value
data' = PresenceUpdateData -> DispatchData
PresenceUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
TYPING_START Value
data' = TypingStartData -> DispatchData
TypingStart forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
USER_UPDATE Value
data' = User -> DispatchData
UserUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
VOICE_STATE_UPDATE Value
data' = VoiceState -> DispatchData
VoiceStateUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
VOICE_SERVER_UPDATE Value
data' = VoiceServerUpdateData -> DispatchData
VoiceServerUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
WEBHOOKS_UPDATE Value
data' = WebhooksUpdateData -> DispatchData
WebhooksUpdate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'
parseDispatchData DispatchType
INTERACTION_CREATE Value
data' = Interaction -> DispatchData
InteractionCreate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromJSON a => Value -> Parser a
Aeson.parseJSON Value
data'

data SentDiscordMessage
  = StatusUpdate StatusUpdateData
  | Identify IdentifyData
  | HeartBeat (Maybe Int)
  | VoiceStatusUpdate VoiceState
  | Resume ResumeData
  | RequestGuildMembers RequestGuildMembersData
  deriving (Int -> SentDiscordMessage -> ShowS
[SentDiscordMessage] -> ShowS
SentDiscordMessage -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [SentDiscordMessage] -> ShowS
$cshowList :: [SentDiscordMessage] -> ShowS
show :: SentDiscordMessage -> String
$cshow :: SentDiscordMessage -> String
showsPrec :: Int -> SentDiscordMessage -> ShowS
$cshowsPrec :: Int -> SentDiscordMessage -> ShowS
Show)

instance Aeson.ToJSON SentDiscordMessage where
  toJSON :: SentDiscordMessage -> Value
toJSON (HeartBeat Maybe Int
data') = [Pair] -> Value
Aeson.object [Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
1 :: Int), Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= Maybe Int
data']
  toJSON (Identify IdentifyData
data') = [Pair] -> Value
Aeson.object [Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
2 :: Int), Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= IdentifyData
data']
  toJSON (StatusUpdate StatusUpdateData
data') = [Pair] -> Value
Aeson.object [Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
3 :: Int), Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= StatusUpdateData
data']
  toJSON (VoiceStatusUpdate VoiceState
data') = [Pair] -> Value
Aeson.object [Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
4 :: Int), Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= VoiceState
data']
  toJSON (Resume ResumeData
data') = [Pair] -> Value
Aeson.object [Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
6 :: Int), Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= ResumeData
data']
  toJSON (RequestGuildMembers RequestGuildMembersData
data') = [Pair] -> Value
Aeson.object [Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
8 :: Int), Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= RequestGuildMembersData
data']

  toEncoding :: SentDiscordMessage -> Encoding
toEncoding (HeartBeat Maybe Int
data') = Series -> Encoding
Aeson.pairs (Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
1 :: Int) forall a. Semigroup a => a -> a -> a
<> Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= Maybe Int
data')
  toEncoding (Identify IdentifyData
data') = Series -> Encoding
Aeson.pairs (Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
2 :: Int) forall a. Semigroup a => a -> a -> a
<> Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= IdentifyData
data')
  toEncoding (StatusUpdate StatusUpdateData
data') = Series -> Encoding
Aeson.pairs (Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
3 :: Int) forall a. Semigroup a => a -> a -> a
<> Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= StatusUpdateData
data')
  toEncoding (VoiceStatusUpdate VoiceState
data') = Series -> Encoding
Aeson.pairs (Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
4 :: Int) forall a. Semigroup a => a -> a -> a
<> Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= VoiceState
data')
  toEncoding (Resume ResumeData
data') = Series -> Encoding
Aeson.pairs (Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
6 :: Int) forall a. Semigroup a => a -> a -> a
<> Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= ResumeData
data')
  toEncoding (RequestGuildMembers RequestGuildMembersData
data') = Series -> Encoding
Aeson.pairs (Key
"op" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= (Int
8 :: Int) forall a. Semigroup a => a -> a -> a
<> Key
"d" forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Aeson..= RequestGuildMembersData
data')

-- Thanks sbrg:
-- https://github.com/saevarb/haskord/blob/d1bb07bcc4f3dbc29f2dfd3351ff9f16fc100c07/haskord-lib/src/Haskord/Types/Common.hs
data DispatchType
  = READY
  | RESUMED
  | CHANNEL_CREATE
  | CHANNEL_UPDATE
  | CHANNEL_DELETE
  | CHANNEL_PINS_UPDATE
  | GUILD_CREATE
  | GUILD_UPDATE
  | GUILD_DELETE
  | GUILD_BAN_ADD
  | GUILD_BAN_REMOVE
  | GUILD_EMOJIS_UPDATE
  | GUILD_INTEGRATIONS_UPDATE
  | GUILD_MEMBER_ADD
  | GUILD_MEMBER_REMOVE
  | GUILD_MEMBER_UPDATE
  | GUILD_MEMBERS_CHUNK
  | GUILD_ROLE_CREATE
  | GUILD_ROLE_UPDATE
  | GUILD_ROLE_DELETE
  | INVITE_CREATE
  | INVITE_DELETE
  | MESSAGE_CREATE
  | MESSAGE_UPDATE
  | MESSAGE_DELETE
  | MESSAGE_DELETE_BULK
  | MESSAGE_REACTION_ADD
  | MESSAGE_REACTION_REMOVE
  | MESSAGE_REACTION_REMOVE_ALL
  | PRESENCE_UPDATE
  | TYPING_START
  | USER_UPDATE
  | VOICE_STATE_UPDATE
  | VOICE_SERVER_UPDATE
  | WEBHOOKS_UPDATE
  | INTERACTION_CREATE
  deriving (Int -> DispatchType -> ShowS
[DispatchType] -> ShowS
DispatchType -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [DispatchType] -> ShowS
$cshowList :: [DispatchType] -> ShowS
show :: DispatchType -> String
$cshow :: DispatchType -> String
showsPrec :: Int -> DispatchType -> ShowS
$cshowsPrec :: Int -> DispatchType -> ShowS
Show, DispatchType -> DispatchType -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: DispatchType -> DispatchType -> Bool
$c/= :: DispatchType -> DispatchType -> Bool
== :: DispatchType -> DispatchType -> Bool
$c== :: DispatchType -> DispatchType -> Bool
Eq, Int -> DispatchType
DispatchType -> Int
DispatchType -> [DispatchType]
DispatchType -> DispatchType
DispatchType -> DispatchType -> [DispatchType]
DispatchType -> DispatchType -> DispatchType -> [DispatchType]
forall a.
(a -> a)
-> (a -> a)
-> (Int -> a)
-> (a -> Int)
-> (a -> [a])
-> (a -> a -> [a])
-> (a -> a -> [a])
-> (a -> a -> a -> [a])
-> Enum a
enumFromThenTo :: DispatchType -> DispatchType -> DispatchType -> [DispatchType]
$cenumFromThenTo :: DispatchType -> DispatchType -> DispatchType -> [DispatchType]
enumFromTo :: DispatchType -> DispatchType -> [DispatchType]
$cenumFromTo :: DispatchType -> DispatchType -> [DispatchType]
enumFromThen :: DispatchType -> DispatchType -> [DispatchType]
$cenumFromThen :: DispatchType -> DispatchType -> [DispatchType]
enumFrom :: DispatchType -> [DispatchType]
$cenumFrom :: DispatchType -> [DispatchType]
fromEnum :: DispatchType -> Int
$cfromEnum :: DispatchType -> Int
toEnum :: Int -> DispatchType
$ctoEnum :: Int -> DispatchType
pred :: DispatchType -> DispatchType
$cpred :: DispatchType -> DispatchType
succ :: DispatchType -> DispatchType
$csucc :: DispatchType -> DispatchType
Enum, forall x. Rep DispatchType x -> DispatchType
forall x. DispatchType -> Rep DispatchType x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cto :: forall x. Rep DispatchType x -> DispatchType
$cfrom :: forall x. DispatchType -> Rep DispatchType x
Generic)
  deriving ([DispatchType] -> Encoding
[DispatchType] -> Value
DispatchType -> Encoding
DispatchType -> Value
forall a.
(a -> Value)
-> (a -> Encoding)
-> ([a] -> Value)
-> ([a] -> Encoding)
-> ToJSON a
toEncodingList :: [DispatchType] -> Encoding
$ctoEncodingList :: [DispatchType] -> Encoding
toJSONList :: [DispatchType] -> Value
$ctoJSONList :: [DispatchType] -> Value
toEncoding :: DispatchType -> Encoding
$ctoEncoding :: DispatchType -> Encoding
toJSON :: DispatchType -> Value
$ctoJSON :: DispatchType -> Value
Aeson.ToJSON, Value -> Parser [DispatchType]
Value -> Parser DispatchType
forall a.
(Value -> Parser a) -> (Value -> Parser [a]) -> FromJSON a
parseJSONList :: Value -> Parser [DispatchType]
$cparseJSONList :: Value -> Parser [DispatchType]
parseJSON :: Value -> Parser DispatchType
$cparseJSON :: Value -> Parser DispatchType
Aeson.FromJSON)

data IdentifyData = IdentifyData
  { IdentifyData -> Text
token :: Text
  , IdentifyData -> IdentifyProps
properties :: IdentifyProps
  , IdentifyData -> Bool
compress :: Bool
  , IdentifyData -> Maybe Int
largeThreshold :: Maybe Int
  , IdentifyData -> Maybe (Int, Int)
shard :: Maybe (Int, Int)
  , IdentifyData -> Maybe StatusUpdateData
presence :: Maybe StatusUpdateData
  , IdentifyData -> Intents
intents :: Intents
  }
  deriving (Int -> IdentifyData -> ShowS
[IdentifyData] -> ShowS
IdentifyData -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [IdentifyData] -> ShowS
$cshowList :: [IdentifyData] -> ShowS
show :: IdentifyData -> String
$cshow :: IdentifyData -> String
showsPrec :: Int -> IdentifyData -> ShowS
$cshowsPrec :: Int -> IdentifyData -> ShowS
Show)
  deriving ([IdentifyData] -> Encoding
[IdentifyData] -> Value
IdentifyData -> Encoding
IdentifyData -> Value
forall a.
(a -> Value)
-> (a -> Encoding)
-> ([a] -> Value)
-> ([a] -> Encoding)
-> ToJSON a
toEncodingList :: [IdentifyData] -> Encoding
$ctoEncodingList :: [IdentifyData] -> Encoding
toJSONList :: [IdentifyData] -> Value
$ctoJSONList :: [IdentifyData] -> Value
toEncoding :: IdentifyData -> Encoding
$ctoEncoding :: IdentifyData -> Encoding
toJSON :: IdentifyData -> Value
$ctoJSON :: IdentifyData -> Value
Aeson.ToJSON) via CalamityToJSON IdentifyData

instance CalamityToJSON' IdentifyData where
  toPairs :: forall kv. KeyValue kv => IdentifyData -> [Maybe kv]
toPairs IdentifyData {Bool
Maybe Int
Maybe (Int, Int)
Maybe StatusUpdateData
Text
Intents
IdentifyProps
intents :: Intents
presence :: Maybe StatusUpdateData
shard :: Maybe (Int, Int)
largeThreshold :: Maybe Int
compress :: Bool
properties :: IdentifyProps
token :: Text
$sel:intents:IdentifyData :: IdentifyData -> Intents
$sel:presence:IdentifyData :: IdentifyData -> Maybe StatusUpdateData
$sel:shard:IdentifyData :: IdentifyData -> Maybe (Int, Int)
$sel:largeThreshold:IdentifyData :: IdentifyData -> Maybe Int
$sel:compress:IdentifyData :: IdentifyData -> Bool
$sel:properties:IdentifyData :: IdentifyData -> IdentifyProps
$sel:token:IdentifyData :: IdentifyData -> Text
..} =
    [ Key
"token" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Text
token
    , Key
"properties" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= IdentifyProps
properties
    , Key
"compress" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Bool
compress
    , Key
"large_threshold" forall v kv. (ToJSON v, KeyValue kv) => Key -> Maybe v -> Maybe kv
.?= Maybe Int
largeThreshold
    , Key
"shard" forall v kv. (ToJSON v, KeyValue kv) => Key -> Maybe v -> Maybe kv
.?= Maybe (Int, Int)
shard
    , Key
"presence" forall v kv. (ToJSON v, KeyValue kv) => Key -> Maybe v -> Maybe kv
.?= Maybe StatusUpdateData
presence
    , Key
"intents" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Intents
intents
    ]

data StatusUpdateData = StatusUpdateData
  { StatusUpdateData -> Maybe Integer
since :: Maybe Integer
  , StatusUpdateData -> [Activity]
activities :: [Activity]
  , StatusUpdateData -> StatusType
status :: StatusType
  , StatusUpdateData -> Bool
afk :: Bool
  }
  deriving (Int -> StatusUpdateData -> ShowS
[StatusUpdateData] -> ShowS
StatusUpdateData -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [StatusUpdateData] -> ShowS
$cshowList :: [StatusUpdateData] -> ShowS
show :: StatusUpdateData -> String
$cshow :: StatusUpdateData -> String
showsPrec :: Int -> StatusUpdateData -> ShowS
$cshowsPrec :: Int -> StatusUpdateData -> ShowS
Show)
  deriving ([StatusUpdateData] -> Encoding
[StatusUpdateData] -> Value
StatusUpdateData -> Encoding
StatusUpdateData -> Value
forall a.
(a -> Value)
-> (a -> Encoding)
-> ([a] -> Value)
-> ([a] -> Encoding)
-> ToJSON a
toEncodingList :: [StatusUpdateData] -> Encoding
$ctoEncodingList :: [StatusUpdateData] -> Encoding
toJSONList :: [StatusUpdateData] -> Value
$ctoJSONList :: [StatusUpdateData] -> Value
toEncoding :: StatusUpdateData -> Encoding
$ctoEncoding :: StatusUpdateData -> Encoding
toJSON :: StatusUpdateData -> Value
$ctoJSON :: StatusUpdateData -> Value
Aeson.ToJSON) via CalamityToJSON StatusUpdateData

instance CalamityToJSON' StatusUpdateData where
  toPairs :: forall kv. KeyValue kv => StatusUpdateData -> [Maybe kv]
toPairs StatusUpdateData {Bool
[Activity]
Maybe Integer
StatusType
afk :: Bool
status :: StatusType
activities :: [Activity]
since :: Maybe Integer
$sel:afk:StatusUpdateData :: StatusUpdateData -> Bool
$sel:status:StatusUpdateData :: StatusUpdateData -> StatusType
$sel:activities:StatusUpdateData :: StatusUpdateData -> [Activity]
$sel:since:StatusUpdateData :: StatusUpdateData -> Maybe Integer
..} =
    [ Key
"since" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Maybe Integer
since
    , Key
"activities" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= [Activity]
activities
    , Key
"status" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= StatusType
status
    , Key
"afk" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Bool
afk
    ]

data ResumeData = ResumeData
  { ResumeData -> Text
token :: Text
  , ResumeData -> Text
sessionID :: Text
  , ResumeData -> Int
seq :: Int
  }
  deriving (Int -> ResumeData -> ShowS
[ResumeData] -> ShowS
ResumeData -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ResumeData] -> ShowS
$cshowList :: [ResumeData] -> ShowS
show :: ResumeData -> String
$cshow :: ResumeData -> String
showsPrec :: Int -> ResumeData -> ShowS
$cshowsPrec :: Int -> ResumeData -> ShowS
Show)
  deriving ([ResumeData] -> Encoding
[ResumeData] -> Value
ResumeData -> Encoding
ResumeData -> Value
forall a.
(a -> Value)
-> (a -> Encoding)
-> ([a] -> Value)
-> ([a] -> Encoding)
-> ToJSON a
toEncodingList :: [ResumeData] -> Encoding
$ctoEncodingList :: [ResumeData] -> Encoding
toJSONList :: [ResumeData] -> Value
$ctoJSONList :: [ResumeData] -> Value
toEncoding :: ResumeData -> Encoding
$ctoEncoding :: ResumeData -> Encoding
toJSON :: ResumeData -> Value
$ctoJSON :: ResumeData -> Value
Aeson.ToJSON) via CalamityToJSON ResumeData

instance CalamityToJSON' ResumeData where
  toPairs :: forall kv. KeyValue kv => ResumeData -> [Maybe kv]
toPairs ResumeData {Int
Text
seq :: Int
sessionID :: Text
token :: Text
$sel:seq:ResumeData :: ResumeData -> Int
$sel:sessionID:ResumeData :: ResumeData -> Text
$sel:token:ResumeData :: ResumeData -> Text
..} =
    [ Key
"token" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Text
token
    , Key
"session_id" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Text
sessionID
    , Key
"seq" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Int
seq
    ]

data RequestGuildMembersData = RequestGuildMembersData
  { RequestGuildMembersData -> Snowflake Guild
guildID :: Snowflake Guild
  , RequestGuildMembersData -> Maybe Text
query :: Maybe Text
  , RequestGuildMembersData -> Int
limit :: Int
  , RequestGuildMembersData -> Maybe Bool
presences :: Maybe Bool
  , RequestGuildMembersData -> Maybe [Snowflake User]
userIDs :: Maybe [Snowflake User]
  , RequestGuildMembersData -> Maybe Text
nonce :: Maybe Text
  }
  deriving (Int -> RequestGuildMembersData -> ShowS
[RequestGuildMembersData] -> ShowS
RequestGuildMembersData -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [RequestGuildMembersData] -> ShowS
$cshowList :: [RequestGuildMembersData] -> ShowS
show :: RequestGuildMembersData -> String
$cshow :: RequestGuildMembersData -> String
showsPrec :: Int -> RequestGuildMembersData -> ShowS
$cshowsPrec :: Int -> RequestGuildMembersData -> ShowS
Show)
  deriving ([RequestGuildMembersData] -> Encoding
[RequestGuildMembersData] -> Value
RequestGuildMembersData -> Encoding
RequestGuildMembersData -> Value
forall a.
(a -> Value)
-> (a -> Encoding)
-> ([a] -> Value)
-> ([a] -> Encoding)
-> ToJSON a
toEncodingList :: [RequestGuildMembersData] -> Encoding
$ctoEncodingList :: [RequestGuildMembersData] -> Encoding
toJSONList :: [RequestGuildMembersData] -> Value
$ctoJSONList :: [RequestGuildMembersData] -> Value
toEncoding :: RequestGuildMembersData -> Encoding
$ctoEncoding :: RequestGuildMembersData -> Encoding
toJSON :: RequestGuildMembersData -> Value
$ctoJSON :: RequestGuildMembersData -> Value
Aeson.ToJSON) via CalamityToJSON RequestGuildMembersData

instance CalamityToJSON' RequestGuildMembersData where
  toPairs :: forall kv. KeyValue kv => RequestGuildMembersData -> [Maybe kv]
toPairs RequestGuildMembersData {Int
Maybe Bool
Maybe [Snowflake User]
Maybe Text
Snowflake Guild
nonce :: Maybe Text
userIDs :: Maybe [Snowflake User]
presences :: Maybe Bool
limit :: Int
query :: Maybe Text
guildID :: Snowflake Guild
$sel:nonce:RequestGuildMembersData :: RequestGuildMembersData -> Maybe Text
$sel:userIDs:RequestGuildMembersData :: RequestGuildMembersData -> Maybe [Snowflake User]
$sel:presences:RequestGuildMembersData :: RequestGuildMembersData -> Maybe Bool
$sel:limit:RequestGuildMembersData :: RequestGuildMembersData -> Int
$sel:query:RequestGuildMembersData :: RequestGuildMembersData -> Maybe Text
$sel:guildID:RequestGuildMembersData :: RequestGuildMembersData -> Snowflake Guild
..} =
    [ Key
"guild_id" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Snowflake Guild
guildID
    , Key
"query" forall v kv. (ToJSON v, KeyValue kv) => Key -> Maybe v -> Maybe kv
.?= Maybe Text
query
    , Key
"limit" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Int
limit
    , Key
"presences" forall v kv. (ToJSON v, KeyValue kv) => Key -> Maybe v -> Maybe kv
.?= Maybe Bool
presences
    , Key
"user_ids" forall v kv. (ToJSON v, KeyValue kv) => Key -> Maybe v -> Maybe kv
.?= Maybe [Snowflake User]
userIDs
    , Key
"nonce" forall v kv. (ToJSON v, KeyValue kv) => Key -> Maybe v -> Maybe kv
.?= Maybe Text
nonce
    ]

data IdentifyProps = IdentifyProps
  { IdentifyProps -> Text
browser :: Text
  , IdentifyProps -> Text
device :: Text
  }
  deriving (Int -> IdentifyProps -> ShowS
[IdentifyProps] -> ShowS
IdentifyProps -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [IdentifyProps] -> ShowS
$cshowList :: [IdentifyProps] -> ShowS
show :: IdentifyProps -> String
$cshow :: IdentifyProps -> String
showsPrec :: Int -> IdentifyProps -> ShowS
$cshowsPrec :: Int -> IdentifyProps -> ShowS
Show)
  deriving ([IdentifyProps] -> Encoding
[IdentifyProps] -> Value
IdentifyProps -> Encoding
IdentifyProps -> Value
forall a.
(a -> Value)
-> (a -> Encoding)
-> ([a] -> Value)
-> ([a] -> Encoding)
-> ToJSON a
toEncodingList :: [IdentifyProps] -> Encoding
$ctoEncodingList :: [IdentifyProps] -> Encoding
toJSONList :: [IdentifyProps] -> Value
$ctoJSONList :: [IdentifyProps] -> Value
toEncoding :: IdentifyProps -> Encoding
$ctoEncoding :: IdentifyProps -> Encoding
toJSON :: IdentifyProps -> Value
$ctoJSON :: IdentifyProps -> Value
Aeson.ToJSON) via CalamityToJSON IdentifyProps

instance CalamityToJSON' IdentifyProps where
  toPairs :: forall kv. KeyValue kv => IdentifyProps -> [Maybe kv]
toPairs IdentifyProps {Text
device :: Text
browser :: Text
$sel:device:IdentifyProps :: IdentifyProps -> Text
$sel:browser:IdentifyProps :: IdentifyProps -> Text
..} = [Key
"$browser" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Text
browser, Key
"$device" forall v kv. (ToJSON v, KeyValue kv) => Key -> v -> Maybe kv
.= Text
device]

data ControlMessage
  = RestartShard
  | ShutDownShard
  | SendPresence StatusUpdateData
  deriving (Int -> ControlMessage -> ShowS
[ControlMessage] -> ShowS
ControlMessage -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ControlMessage] -> ShowS
$cshowList :: [ControlMessage] -> ShowS
show :: ControlMessage -> String
$cshow :: ControlMessage -> String
showsPrec :: Int -> ControlMessage -> ShowS
$cshowsPrec :: Int -> ControlMessage -> ShowS
Show)

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

data Shard = Shard
  { Shard -> Int
shardID :: Int
  , Shard -> Int
shardCount :: Int
  , Shard -> Text
gateway :: Text
  , Shard -> InChan CalamityEvent
evtIn :: InChan CalamityEvent
  , Shard -> OutChan ControlMessage
cmdOut :: OutChan ControlMessage
  , Shard -> Text
token :: Text
  , Shard -> Maybe StatusUpdateData
initialStatus :: Maybe StatusUpdateData
  , Shard -> Intents
intents :: Intents
  }

data ShardState = ShardState
  { ShardState -> Shard
shardS :: Shard
  , ShardState -> Maybe Int
seqNum :: Maybe Int
  , ShardState -> Maybe (Async (Maybe ()))
hbThread :: Maybe (Async (Maybe ()))
  , ShardState -> Bool
hbResponse :: Bool
  , ShardState -> Maybe Text
wsHost :: Maybe Text
  , ShardState -> Maybe Text
sessionID :: Maybe Text
  , ShardState -> Maybe Connection
wsConn :: Maybe Connection
  }

$(makeFieldLabelsNoPrefix ''Shard)
$(makeFieldLabelsNoPrefix ''ShardState)