This commit is contained in:
SeanOMik 2020-06-23 00:08:25 -05:00
parent 1fe136186d
commit 8a9436f831
No known key found for this signature in database
GPG Key ID: FA4D55AC05268A88
6 changed files with 258 additions and 205 deletions

View File

@ -45,6 +45,6 @@ You can view examples in the [examples](examples) directory.
- [ ] Channel - [ ] Channel
- [ ] Guild - [ ] Guild
- [ ] Misc. - [ ] Misc.
- [ ] Sharding. - [x] Sharding.
- [ ] Audit log. - [ ] Audit log.
- [ ] Voice. - [ ] Voice.

View File

@ -1,4 +1,4 @@
import nimcord, asyncdispatch, streams, os, strutils, options import ../src/nimcord, asyncdispatch, streams, os, strutils, options, websocket
var tokenStream = newFileStream("token.txt", fmRead) var tokenStream = newFileStream("token.txt", fmRead)
var tkn: string var tkn: string
@ -19,37 +19,37 @@ registerEventListener(EventType.evtReady, proc(bEvt: BaseEvent) =
echo "--------------------" echo "--------------------"
let presence = newPresence("with Nimcord", activityTypeGame, clientStatusIdle, false) let presence = newPresence("with Nimcord", activityTypeGame, clientStatusIdle, false)
asyncCheck event.client.updateClientPresence(presence) asyncCheck event.shard.updateClientPresence(presence)
) )
registerEventListener(EventType.evtMessageCreate, proc(bEvt: BaseEvent) = registerEventListener(EventType.evtMessageCreate, proc(bEvt: BaseEvent) =
let event = MessageCreateEvent(bEvt) let event = MessageCreateEvent(bEvt)
if (event.message.content == "?ping"): if (event.message.content == "?ping"):
var channel: Channel = event.message.getMessageChannel(event.client.cache) var channel: Channel = event.message.getMessageChannel(event.shard.client.cache)
if (channel != nil): if (channel != nil):
discard channel.sendMessage("PONG") discard channel.sendMessage("PONG")
elif (event.message.content.startsWith("?modifyChannelTopic")): elif (event.message.content.startsWith("?modifyChannelTopic")):
let modifyTopic = event.message.content.substr(20) let modifyTopic = event.message.content.substr(20)
var channel: Channel = event.message.getMessageChannel(event.client.cache) var channel: Channel = event.message.getMessageChannel(event.shard.client.cache)
if (channel != nil): if (channel != nil):
discard channel.sendMessage("Modifing Channel!") discard channel.sendMessage("Modifing Channel!")
discard channel.modifyChannel(ChannelFields(topic: some(modifyTopic))) discard channel.modifyChannel(ChannelFields(topic: some(modifyTopic)))
elif (event.message.content.startsWith("?deleteChannel")): elif (event.message.content.startsWith("?deleteChannel")):
let channelID = getIDFromJson(event.message.content.substr(15)) let channelID = getIDFromJson(event.message.content.substr(15))
var channel: Channel = event.client.cache.getChannel(channelID) var channel: Channel = event.shard.client.cache.getChannel(channelID)
if (channel != nil): if (channel != nil):
discard channel.sendMessage("Deleting Channel!") discard channel.sendMessage("Deleting Channel!")
discard channel.deleteChannel() discard channel.deleteChannel()
discard channel.sendMessage("Deleted Channel!") discard channel.sendMessage("Deleted Channel!")
elif (event.message.content.startsWith("?getMessages")): elif (event.message.content.startsWith("?getMessages")):
var channel: Channel = event.message.getMessageChannel(event.client.cache) var channel: Channel = event.message.getMessageChannel(event.shard.client.cache)
if (channel != nil): if (channel != nil):
discard channel.getMessages(MessagesGetRequest(limit: some(15), before: some(event.message.id))) discard channel.getMessages(MessagesGetRequest(limit: some(15), before: some(event.message.id)))
elif (event.message.content.startsWith("?bulkDeleteMessages")): elif (event.message.content.startsWith("?bulkDeleteMessages")):
var channel: Channel = event.message.getMessageChannel(event.client.cache) var channel: Channel = event.message.getMessageChannel(event.shard.client.cache)
if (channel != nil): if (channel != nil):
var amount: int = 25 var amount: int = 25
if (event.message.content.len > 19): if (event.message.content.len > 19):
@ -57,13 +57,13 @@ registerEventListener(EventType.evtMessageCreate, proc(bEvt: BaseEvent) =
let messages = channel.getMessages(MessagesGetRequest(limit: some(amount), before: some(event.message.id))) let messages = channel.getMessages(MessagesGetRequest(limit: some(amount), before: some(event.message.id)))
discard channel.bulkDeleteMessages(messages) discard channel.bulkDeleteMessages(messages)
elif (event.message.content.startsWith("?reactToMessage")): elif (event.message.content.startsWith("?reactToMessage")):
var channel: Channel = event.message.getMessageChannel(event.client.cache) var channel: Channel = event.message.getMessageChannel(event.shard.client.cache)
if (channel != nil): if (channel != nil):
let emojis = @[newEmoji("⏮️"), newEmoji("⬅️"), newEmoji("⏹️"), newEmoji("➡️"), newEmoji("⏭️")] let emojis = @[newEmoji("⏮️"), newEmoji("⬅️"), newEmoji("⏹️"), newEmoji("➡️"), newEmoji("⏭️")]
for emoji in emojis: for emoji in emojis:
discard event.message.addReaction(emoji) discard event.message.addReaction(emoji)
elif (event.message.content.startsWith("?testEmbed")): elif (event.message.content.startsWith("?testEmbed")):
var channel: Channel = event.message.getMessageChannel(event.client.cache) var channel: Channel = event.message.getMessageChannel(event.shard.client.cache)
if (channel != nil): if (channel != nil):
var embed = Embed() var embed = Embed()
embed.setTitle("This embed is being sent from Nimcord!") embed.setTitle("This embed is being sent from Nimcord!")
@ -74,7 +74,7 @@ registerEventListener(EventType.evtMessageCreate, proc(bEvt: BaseEvent) =
embed.setColor(0xffb900) embed.setColor(0xffb900)
discard channel.sendMessage("", false, embed) discard channel.sendMessage("", false, embed)
elif (event.message.content.startsWith("?sendFile")): elif (event.message.content.startsWith("?sendFile")):
var channel: Channel = event.message.getMessageChannel(event.client.cache) var channel: Channel = event.message.getMessageChannel(event.shard.client.cache)
if (channel != nil): if (channel != nil):
let filePath = event.message.content.substr(10) let filePath = event.message.content.substr(10)
@ -84,7 +84,7 @@ registerEventListener(EventType.evtMessageCreate, proc(bEvt: BaseEvent) =
let file = DiscordFile(filePath: filePath, fileName: fileName) let file = DiscordFile(filePath: filePath, fileName: fileName)
discard channel.sendMessage("", false, nil, @[file]) discard channel.sendMessage("", false, nil, @[file])
elif (event.message.content.startsWith("?sendImage")): elif (event.message.content.startsWith("?sendImage")):
var channel: Channel = event.message.getMessageChannel(event.client.cache) var channel: Channel = event.message.getMessageChannel(event.shard.client.cache)
if (channel != nil): if (channel != nil):
let filePath = event.message.content.substr(11) let filePath = event.message.content.substr(11)
@ -99,4 +99,4 @@ registerEventListener(EventType.evtMessageCreate, proc(bEvt: BaseEvent) =
discard channel.sendMessage("", false, embed, @[file]) discard channel.sendMessage("", false, embed, @[file])
) )
waitFor bot.startConnection() waitFor bot.startConnection(2)

View File

@ -16,7 +16,7 @@ type
opHello = 10, opHello = 10,
opHeartbeatAck = 11 opHeartbeatAck = 11
proc sendGatewayRequest*(client: DiscordClient, request: JsonNode, msg: string = "") {.async.} = proc sendGatewayRequest*(shard: Shard, request: JsonNode, msg: string = "") {.async.} =
## Send a gateway request. ## Send a gateway request.
## Don't use this unless you know what you're doing! ## Don't use this unless you know what you're doing!
if (msg.len == 0): if (msg.len == 0):
@ -24,50 +24,62 @@ proc sendGatewayRequest*(client: DiscordClient, request: JsonNode, msg: string =
else: else:
echo msg echo msg
await client.ws.sendText($request) await shard.ws.sendText($request)
proc handleHeartbeat(client: DiscordClient) {.async.} = proc handleHeartbeat(shard: Shard) {.async.} =
while true: while true:
var heartbeatPayload: JsonNode var heartbeatPayload: JsonNode
if (client.lastSequence == 0): if (shard.lastSequence == 0):
heartbeatPayload = %* { "d": nil, "op": ord(DiscordOpCode.opHeartbeat) } heartbeatPayload = %* { "d": nil, "op": ord(DiscordOpCode.opHeartbeat) }
else: else:
heartbeatPayload = %* { "d": client.lastSequence, "op": ord(DiscordOpCode.opHeartbeat) } heartbeatPayload = %* { "d": shard.lastSequence, "op": ord(DiscordOpCode.opHeartbeat) }
await client.sendGatewayRequest(heartbeatPayload, fmt("Sending heartbeat payload: {$heartbeatPayload}")) await shard.sendGatewayRequest(heartbeatPayload, fmt("Sending heartbeat payload: {$heartbeatPayload}"))
client.heartbeatAcked = true shard.heartbeatAcked = true
echo "Waiting ", client.heartbeatInterval, " ms until next heartbeat..." echo "Waiting ", shard.heartbeatInterval, " ms until next heartbeat..."
await sleepAsync(client.heartbeatInterval) await sleepAsync(shard.heartbeatInterval)
proc getIdentifyPacket(client: DiscordClient): JsonNode = proc getIdentifyPacket(shard: Shard): JsonNode =
return %* { "op": ord(DiscordOpCode.opIdentify), "d": { "token": client.token, "properties": { "$os": system.hostOS, "$browser": "NimCord", "$device": "NimCord" } } } return %* {
"op": ord(DiscordOpCode.opIdentify),
"d": {
"token": shard.client.token,
"shard": [shard.id, shard.client.shardCount],
"properties": {
"$os": system.hostOS,
"$browser": "NimCord",
"$device": "NimCord"
}
}
}
proc startConnection*(client: DiscordClient) {.async.} # For some reason this shows as an error in VSCode, but it compiles fine.
#proc startConnection*(client: DiscordClient, shardCount: int = 1) {.async.}
proc closeConnection*(client: DiscordClient, code: int = 1000) {.async.} = proc closeConnection*(shard: Shard, code: int = 1000) {.async.} =
echo "Disconnecting with code: ", code echo "Disconnecting with code: ", code
await client.ws.close(code) await shard.ws.close(code)
proc reconnectClient(client: DiscordClient) {.async.} = proc reconnectShard(shard: Shard) {.async.} =
echo "Reconnecting..." echo "Reconnecting..."
client.reconnecting = true shard.reconnecting = true
await client.ws.close(1000) await shard.ws.close(1000)
client.ws = await newAsyncWebsocketClient(client.endpoint[6..client.endpoint.high], Port 443, shard.ws = await newAsyncWebsocketClient(shard.client.endpoint[6..shard.client.endpoint.high], Port 443,
path = "/v=6&encoding=json", true) path = "/v=6&encoding=json", true)
client.reconnecting = false shard.reconnecting = false
client.heartbeatAcked = true shard.heartbeatAcked = true
#waitFor client.startConnection() #waitFor client.startConnection()
# Handle discord disconnect. If it detects that we can reconnect, it will. # Handle discord disconnect. If it detects that we can reconnect, it will.
proc handleDiscordDisconnect(client: DiscordClient, error: string) {.async.} = proc handleGatewayDisconnect(shard: Shard, error: string) {.async.} =
let disconnectData = extractCloseData(error) let disconnectData = extractCloseData(error)
echo "Discord gateway disconnected! Error code: ", disconnectData.code, ", msg: ", disconnectData.reason echo "Discord gateway disconnected! Error code: ", disconnectData.code, ", msg: ", disconnectData.reason
client.heartbeatAcked = false shard.heartbeatAcked = false
# Get the disconnect code # Get the disconnect code
let c = disconnectData.code let c = disconnectData.code
@ -76,22 +88,22 @@ proc handleDiscordDisconnect(client: DiscordClient, error: string) {.async.} =
if ( (c >= 4003 and c <= 4005) or c == 4007 or (c >= 4010 and c <= 4013) ): if ( (c >= 4003 and c <= 4005) or c == 4007 or (c >= 4010 and c <= 4013) ):
echo "The Discord gateway sent a disconnect code that we cannot reconnect to." echo "The Discord gateway sent a disconnect code that we cannot reconnect to."
else: else:
if (not client.reconnecting): if (not shard.reconnecting):
waitFor client.reconnectClient() waitFor shard.reconnectShard()
else: else:
echo "Gateway is cannot reconnect due to already reconnecting..." echo "Gateway is cannot reconnect due to already reconnecting..."
#TODO: Reconnecting may be done, just needs testing. #TODO: Reconnecting may be done, just needs testing.
proc handleWebsocketPacket(client: DiscordClient) {.async.} = proc handleWebsocketPacket(shard: Shard) {.async.} =
while true: while true:
var packet: tuple[opcode: Opcode, data: string] var packet: tuple[opcode: Opcode, data: string]
packet = await client.ws.readData(); packet = await shard.ws.readData();
echo "Received gateway payload: ", packet.data echo "[SHARD ", $shard.id, "] Received gateway payload: ", packet.data
if packet.opcode == Opcode.Close: if packet.opcode == Opcode.Close:
await client.handleDiscordDisconnect(packet.data) await shard.handleGatewayDisconnect(packet.data)
var json: JsonNode var json: JsonNode
@ -103,52 +115,55 @@ proc handleWebsocketPacket(client: DiscordClient) {.async.} =
continue continue
if (json.contains("s")): if (json.contains("s")):
client.lastSequence = json["s"].getInt() shard.lastSequence = json["s"].getInt()
case json["op"].getInt() case json["op"].getInt()
of ord(DiscordOpCode.opHello): of ord(DiscordOpCode.opHello):
if client.reconnecting: if shard.reconnecting:
echo "Reconnected!" echo "Reconnected!"
client.reconnecting = false shard.reconnecting = false
let resume = %* { let resume = %* {
"op": ord(opResume), "op": ord(opResume),
"d": { "d": {
"token": client.token, "token": shard.client.token,
"session_id": client.sessionID, "session_id": shard.sessionID,
"seq": client.lastSequence "seq": shard.lastSequence
} }
} }
await client.sendGatewayRequest(resume) await shard.sendGatewayRequest(resume)
else: else:
client.heartbeatInterval = json["d"]["heartbeat_interval"].getInt() shard.heartbeatInterval = json["d"]["heartbeat_interval"].getInt()
await client.sendGatewayRequest(client.getIdentifyPacket()) await shard.sendGatewayRequest(shard.getIdentifyPacket())
asyncCheck client.handleHeartbeat() asyncCheck shard.handleHeartbeat()
client.heartbeatAcked = true shard.heartbeatAcked = true
of ord(DiscordOpCode.opHeartbeatAck): of ord(DiscordOpCode.opHeartbeatAck):
client.heartbeatAcked = true shard.heartbeatAcked = true
of ord(DiscordOpCode.opDispatch): of ord(DiscordOpCode.opDispatch):
asyncCheck handleDiscordEvent(client, json["d"], json["t"].getStr()) asyncCheck handleDiscordEvent(shard, json["d"], json["t"].getStr())
of ord(DiscordOpCode.opReconnect): of ord(DiscordOpCode.opReconnect):
asyncCheck client.reconnectClient() asyncCheck shard.reconnectShard()
of ord(DiscordOpCode.opInvalidSession): of ord(DiscordOpCode.opInvalidSession):
# If the json field `d` is true then the session may be resumable. # If the json field `d` is true then the session may be resumable.
if json["d"].getBool(): if json["d"].getBool():
let resume = %* { let resume = %* {
"op": ord(opResume), "op": ord(opResume),
"session_id": client.sessionID, "session_id": shard.sessionID,
"seq": client.lastSequence "seq": shard.lastSequence
} }
await client.sendGatewayRequest(resume) await shard.sendGatewayRequest(resume)
else: else:
asyncCheck client.reconnectClient() asyncCheck shard.reconnectShard()
else: else:
discard discard
proc startConnection*(client: DiscordClient) {.async.} = proc newShard(shardID: int, client: DiscordClient): Shard =
return Shard(id: shardID, client: client)
proc startConnection*(client: DiscordClient, shardAmount: int = 1) {.async.} =
## Start a bot connection. ## Start a bot connection.
## ##
## Examples: ## Examples:
@ -170,24 +185,55 @@ proc startConnection*(client: DiscordClient) {.async.} =
let url = urlResult["url"].getStr() let url = urlResult["url"].getStr()
client.endpoint = url client.endpoint = url
client.ws = await newAsyncWebsocketClient(url[6..url.high], Port 443, var shardCount = shardAmount
if (shardCount < urlResult["shards"].getInt()):
shardCount = urlResult["shards"].getInt()
client.shardCount = shardCount
if shardCount > 1:
for index in 0..shardCount - 2:
var shard = newShard(index, client)
client.shards.add(shard)
shard.ws = await newAsyncWebsocketClient(url[6..url.high], Port 443,
path = "/v=6&encoding=json", true)
asyncCheck shard.handleWebsocketPacket()
# Theres a 5 second delay on identify payloads.
await sleepAsync(5500)
var shard = newShard(shardCount - 1, client)
client.shards.add(shard)
shard.ws = await newAsyncWebsocketClient(url[6..url.high], Port 443,
path = "/v=6&encoding=json", true)
asyncCheck shard.handleWebsocketPacket()
# Now just wait. Dont poll while we're reconnecting
while true:
if not shard.reconnecting:
poll()
#[ client.ws = await newAsyncWebsocketClient(url[6..url.high], Port 443,
path = "/v=6&encoding=json", true) path = "/v=6&encoding=json", true)
asyncCheck client.handleWebsocketPacket() asyncCheck client.handleWebsocketPacket()
# Now just wait. Dont poll for new events while we're reconnecting # Now just wait. Dont poll for new events while we're reconnecting
while true: while true:
if not client.reconnecting: if not client.reconnecting:
poll() poll() ]#
else: else:
raise newException(IOError, "Failed to get gateway url, token may of been incorrect!") raise newException(IOError, "Failed to get gateway url, token may of been incorrect!")
proc updateClientPresence*(client: DiscordClient, presence: Presence) {.async.} = proc updateClientPresence*(shard: Shard, presence: Presence) {.async.} =
let jsonPayload = %* { let jsonPayload = %* {
"op": ord(opPresenceUpdate), "op": ord(opPresenceUpdate),
"d": presence.presenceToJson() "d": presence.presenceToJson()
} }
await client.sendGatewayRequest(jsonPayload) await shard.sendGatewayRequest(jsonPayload)
proc newDiscordClient*(tkn: string): DiscordClient = proc newDiscordClient*(tkn: string): DiscordClient =
## Create a DiscordClient using a token. ## Create a DiscordClient using a token.
@ -198,4 +244,4 @@ proc newDiscordClient*(tkn: string): DiscordClient =
var cac: Cache var cac: Cache
new(cac) new(cac)
result = DiscordClient(token: tkn, cache: cac, reconnecting: false) result = DiscordClient(token: tkn, cache: cac)

View File

@ -1,14 +1,21 @@
import websocket, cache, user import websocket, cache, user
type DiscordClient* = ref object type
## Discord Client DiscordClient* = ref object
token*: string ## Discord Client
clientUser*: User token*: string
cache*: Cache clientUser*: User
ws*: AsyncWebSocket cache*: Cache
heartbeatInterval*: int shards*: seq[Shard]
heartbeatAcked*: bool shardCount*: int
lastSequence*: int endpoint*: string
endpoint*: string
reconnecting*: bool Shard* = ref object
sessionID*: string id*: int
client*: DiscordClient
ws*: AsyncWebSocket
heartbeatInterval*: int
heartbeatAcked*: bool
lastSequence*: int
reconnecting*: bool
sessionID*: string

View File

@ -2,13 +2,13 @@ import eventhandler, json, tables, message, emoji, user, member, role
import guild, channel, nimcordutils, httpClient, strformat, cache import guild, channel, nimcordutils, httpClient, strformat, cache
import sequtils, asyncdispatch, clientobjects, discordobject, presence import sequtils, asyncdispatch, clientobjects, discordobject, presence
proc readyEvent(discordClient: DiscordClient, json: JsonNode) = proc readyEvent(shard: Shard, json: JsonNode) =
var readyEvent = ReadyEvent(client: discordClient, readyPayload: json, name: $EventType.evtReady) var readyEvent = ReadyEvent(shard: shard, readyPayload: json, name: $EventType.evtReady)
# Get client user # Get client user
var client = newHttpClient() var client = newHttpClient()
# Add headers # Add headers
client.headers = newHttpHeaders({"Authorization": fmt("Bot {discordClient.token}"), client.headers = newHttpHeaders({"Authorization": fmt("Bot {shard.client.token}"),
"User-Agent": "NimCord (https://github.com/SeanOMik/nimcord, v0.0.0)", "User-Agent": "NimCord (https://github.com/SeanOMik/nimcord, v0.0.0)",
"X-RateLimit-Precision": "millisecond"}) "X-RateLimit-Precision": "millisecond"})
echo "Sending GET request, URL: body: {}" echo "Sending GET request, URL: body: {}"
@ -16,30 +16,30 @@ proc readyEvent(discordClient: DiscordClient, json: JsonNode) =
waitForRateLimits(0, RateLimitBucketType.global) waitForRateLimits(0, RateLimitBucketType.global)
var userJson = handleResponse(client.request(endpoint("/users/@me"), HttpGet, ""), 0, RateLimitBucketType.global) var userJson = handleResponse(client.request(endpoint("/users/@me"), HttpGet, ""), 0, RateLimitBucketType.global)
discordClient.clientUser = newUser(userJson) shard.client.clientUser = newUser(userJson)
discordClient.sessionID = json["session_id"].getStr() shard.sessionID = json["session_id"].getStr()
dispatchEvent(readyEvent) dispatchEvent(readyEvent)
proc channelCreateEvent(discordClient: DiscordClient, json: JsonNode) = proc channelCreateEvent(shard: Shard, json: JsonNode) =
let chnl = newChannel(json) let chnl = newChannel(json)
let channelCreateEvent = ChannelCreateEvent(client: discordClient, channel: chnl, name: $EventType.evtChannelCreate) let channelCreateEvent = ChannelCreateEvent(shard: shard, channel: chnl, name: $EventType.evtChannelCreate)
# Add the channel to its guild's `channels` field # Add the channel to its guild's `channels` field
if (chnl.guildID != 0): if (chnl.guildID != 0):
discordClient.cache.cacheGuildChannel(chnl.guildID, chnl) shard.client.cache.cacheGuildChannel(chnl.guildID, chnl)
discordClient.cache.channels[chnl.id] = chnl shard.client.cache.channels[chnl.id] = chnl
dispatchEvent(channelCreateEvent) dispatchEvent(channelCreateEvent)
proc channelUpdateEvent(discordClient: DiscordClient, json: JsonNode) = proc channelUpdateEvent(shard: Shard, json: JsonNode) =
let chnl = newChannel(json) let chnl = newChannel(json)
let channelUpdateEvent = ChannelUpdateEvent(client: discordClient, channel: chnl, name: $EventType.evtChannelUpdate) let channelUpdateEvent = ChannelUpdateEvent(shard: shard, channel: chnl, name: $EventType.evtChannelUpdate)
discordClient.cache.channels[chnl.id] = chnl shard.client.cache.channels[chnl.id] = chnl
if (chnl.guildID != 0): if (chnl.guildID != 0):
let g = discordClient.cache.getGuild(chnl.guildID) let g = shard.client.cache.getGuild(chnl.guildID)
var index = -1 var index = -1
for i, channel in g.channels: for i, channel in g.channels:
@ -55,81 +55,81 @@ proc channelUpdateEvent(discordClient: DiscordClient, json: JsonNode) =
dispatchEvent(channelUpdateEvent) dispatchEvent(channelUpdateEvent)
proc channelDeleteEvent(discordClient: DiscordClient, json: JsonNode) = proc channelDeleteEvent(shard: Shard, json: JsonNode) =
let chnl = newChannel(json) let chnl = newChannel(json)
let channelDeleteEvent = ChannelDeleteEvent(client: discordClient, channel: chnl, name: $EventType.evtChannelDelete) let channelDeleteEvent = ChannelDeleteEvent(shard: shard, channel: chnl, name: $EventType.evtChannelDelete)
var removedChnl: Channel var removedChnl: Channel
discard discordClient.cache.channels.pop(chnl.id, removedChnl) discard shard.client.cache.channels.pop(chnl.id, removedChnl)
dispatchEvent(channelDeleteEvent) dispatchEvent(channelDeleteEvent)
proc channelPinsUpdate(discordClient: DiscordClient, json: JsonNode) = proc channelPinsUpdate(shard: Shard, json: JsonNode) =
let channelID = getIDFromJson(json["channel_id"].getStr()) let channelID = getIDFromJson(json["channel_id"].getStr())
var channel: Channel var channel: Channel
if (discordClient.cache.channels.hasKey(channelID)): if (shard.client.cache.channels.hasKey(channelID)):
channel = discordClient.cache.channels[channelID] channel = shard.client.cache.channels[channelID]
channel.lastPinTimestamp = json["last_pin_timestamp"].getStr() channel.lastPinTimestamp = json["last_pin_timestamp"].getStr()
let channelPinsUpdateEvent = ChannelPinsUpdateEvent(client: discordClient, channel: channel, name: $EventType.evtChannelPinsUpdate) let channelPinsUpdateEvent = ChannelPinsUpdateEvent(shard: shard, channel: channel, name: $EventType.evtChannelPinsUpdate)
dispatchEvent(channelPinsUpdateEvent) dispatchEvent(channelPinsUpdateEvent)
proc guildCreateEvent(discordClient: DiscordClient, json: JsonNode) = proc guildCreateEvent(shard: Shard, json: JsonNode) =
let g = newGuild(json) let g = newGuild(json)
let guildCreateEvnt = GuildCreateEvent(client: discordClient, guild: g, name: $EventType.evtGuildCreate) let guildCreateEvnt = GuildCreateEvent(shard: shard, guild: g, name: $EventType.evtGuildCreate)
# Add guild and its channels and members in cache. # Add guild and its channels and members in cache.
discordClient.cache.guilds[g.id] = g shard.client.cache.guilds[g.id] = g
for channel in g.channels: for channel in g.channels:
discordClient.cache.channels[channel.id] = channel shard.client.cache.channels[channel.id] = channel
for member in g.members: for member in g.members:
discordClient.cache.members[member.id] = member shard.client.cache.members[member.id] = member
dispatchEvent(guildCreateEvnt) dispatchEvent(guildCreateEvnt)
proc guildUpdateEvent(discordClient: DiscordClient, json: JsonNode) = proc guildUpdateEvent(shard: Shard, json: JsonNode) =
let g = newGuild(json) let g = newGuild(json)
let guildUpdateEvent = GuildUpdateEvent(client: discordClient, guild: g, name: $EventType.evtGuildUpdate) let guildUpdateEvent = GuildUpdateEvent(shard: shard, guild: g, name: $EventType.evtGuildUpdate)
# Update guild in cache. # Update guild in cache.
discordClient.cache.guilds[g.id] = g shard.client.cache.guilds[g.id] = g
dispatchEvent(guildUpdateEvent) dispatchEvent(guildUpdateEvent)
proc guildDeleteEvent(discordClient: DiscordClient, json: JsonNode) = proc guildDeleteEvent(shard: Shard, json: JsonNode) =
let g = newGuild(json) let g = newGuild(json)
let guildDeleteEvent = GuildDeleteEvent(client: discordClient, guild: g, name: $EventType.evtGuildDelete) let guildDeleteEvent = GuildDeleteEvent(shard: shard, guild: g, name: $EventType.evtGuildDelete)
# Remove guild from cache # Remove guild from cache
var removedGuild: Guild var removedGuild: Guild
discard discordClient.cache.guilds.pop(g.id, removedGuild) discard shard.client.cache.guilds.pop(g.id, removedGuild)
dispatchEvent(guildDeleteEvent) dispatchEvent(guildDeleteEvent)
proc guildBanAddEvent(discordClient: DiscordClient, json: JsonNode) = proc guildBanAddEvent(shard: Shard, json: JsonNode) =
let g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) let g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
let user = newUser(json["user"]) let user = newUser(json["user"])
let guildBanAddEvent = GuildBanAddEvent(client: discordClient, guild: g, bannedUser: user, name: $EventType.evtGuildBanAdd) let guildBanAddEvent = GuildBanAddEvent(shard: shard, guild: g, bannedUser: user, name: $EventType.evtGuildBanAdd)
dispatchEvent(guildBanAddEvent) dispatchEvent(guildBanAddEvent)
proc guildBanRemoveEvent(discordClient: DiscordClient, json: JsonNode) = proc guildBanRemoveEvent(shard: Shard, json: JsonNode) =
let g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) let g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
let user = newUser(json["user"]) let user = newUser(json["user"])
let guildBanRemoveEvent = GuildBanRemoveEvent(client: discordClient, guild: g, unbannedUser: user, name: $EventType.evtGuildBanRemove) let guildBanRemoveEvent = GuildBanRemoveEvent(shard: shard, guild: g, unbannedUser: user, name: $EventType.evtGuildBanRemove)
dispatchEvent(guildBanRemoveEvent) dispatchEvent(guildBanRemoveEvent)
proc guildEmojisUpdateEvent(discordClient: DiscordClient, json: JsonNode) = proc guildEmojisUpdateEvent(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
# Empty g.emojis and fill it with the newly updated emojis # Empty g.emojis and fill it with the newly updated emojis
g.emojis = @[] g.emojis = @[]
for emoji in json["emojis"]: for emoji in json["emojis"]:
g.emojis.add(newEmoji(emoji, g.id)) g.emojis.add(newEmoji(emoji, g.id))
let guildEmojisUpdateEvent = GuildEmojisUpdateEvent(client: discordClient, guild: g, emojis: g.emojis, name: $EventType.evtGuildEmojisUpdate) let guildEmojisUpdateEvent = GuildEmojisUpdateEvent(shard: shard, guild: g, emojis: g.emojis, name: $EventType.evtGuildEmojisUpdate)
dispatchEvent(guildEmojisUpdateEvent) dispatchEvent(guildEmojisUpdateEvent)
#[ var updatedEmojis: Table[snowflake, Emoji] = initTable[snowflake, Emoji]() #[ var updatedEmojis: Table[snowflake, Emoji] = initTable[snowflake, Emoji]()
@ -143,28 +143,28 @@ proc guildEmojisUpdateEvent(discordClient: DiscordClient, json: JsonNode) =
#g.emojis.apply #g.emojis.apply
proc guildIntegrationsUpdate(discordClient: DiscordClient, json: JsonNode) = proc guildIntegrationsUpdate(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
let guildIntegrationsUpdateEvent = GuildIntegrationsUpdateEvent(client: discordClient, guild: g, name: $EventType.evtGuildIntegrationsUpdate) let guildIntegrationsUpdateEvent = GuildIntegrationsUpdateEvent(shard: shard, guild: g, name: $EventType.evtGuildIntegrationsUpdate)
dispatchEvent(guildIntegrationsUpdateEvent) dispatchEvent(guildIntegrationsUpdateEvent)
proc guildMemberAdd(discordClient: DiscordClient, json: JsonNode) = proc guildMemberAdd(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
var newMember = newGuildMember(json, g.id) var newMember = newGuildMember(json, g.id)
let guildMemberAddEvent = GuildMemberAddEvent(client: discordClient, guild: g, member: newMember, name: $EventType.evtGuildMemberAdd) let guildMemberAddEvent = GuildMemberAddEvent(shard: shard, guild: g, member: newMember, name: $EventType.evtGuildMemberAdd)
dispatchEvent(guildMemberAddEvent) dispatchEvent(guildMemberAddEvent)
proc guildMemberRemove(discordClient: DiscordClient, json: JsonNode) = proc guildMemberRemove(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
var removedUser = newUser(json["user"]) var removedUser = newUser(json["user"])
let guildMemberRemoveEvent = GuildMemberRemoveEvent(client: discordClient, guild: g, user: removedUser, name: $EventType.evtGuildMemberRemove) let guildMemberRemoveEvent = GuildMemberRemoveEvent(shard: shard, guild: g, user: removedUser, name: $EventType.evtGuildMemberRemove)
dispatchEvent(guildMemberRemoveEvent) dispatchEvent(guildMemberRemoveEvent)
proc guildMemberUpdate(discordClient: DiscordClient, json: JsonNode) = proc guildMemberUpdate(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
var updatedMember = g.getGuildMember(getIDFromJson(json["user"]["id"].getStr())) var updatedMember = g.getGuildMember(getIDFromJson(json["user"]["id"].getStr()))
updatedMember.user = newUser(json["user"]) updatedMember.user = newUser(json["user"])
@ -179,13 +179,13 @@ proc guildMemberUpdate(discordClient: DiscordClient, json: JsonNode) =
if json.contains("premium_since"): if json.contains("premium_since"):
updatedMember.premiumSince = json["premium_since"].getStr() updatedMember.premiumSince = json["premium_since"].getStr()
let guildMemberUpdateEvent = GuildMemberUpdateEvent(client: discordClient, guild: g, member: updatedMember, name: $EventType.evtGuildMemberUpdate) let guildMemberUpdateEvent = GuildMemberUpdateEvent(shard: shard, guild: g, member: updatedMember, name: $EventType.evtGuildMemberUpdate)
dispatchEvent(guildMemberUpdateEvent) dispatchEvent(guildMemberUpdateEvent)
proc guildMembersChunk(discordClient: DiscordClient, json: JsonNode) = proc guildMembersChunk(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
var event = GuildMembersChunkEvent(client: discordClient, guild: g, name: $EventType.evtGuildMembersChunk) var event = GuildMembersChunkEvent(shard: shard, guild: g, name: $EventType.evtGuildMembersChunk)
#var members: seq[GuildMember] #var members: seq[GuildMember]
for member in json["members"]: for member in json["members"]:
@ -207,17 +207,17 @@ proc guildMembersChunk(discordClient: DiscordClient, json: JsonNode) =
dispatchEvent(event) dispatchEvent(event)
proc guildRoleCreate(discordClient: DiscordClient, json: JsonNode) = proc guildRoleCreate(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
let role = newRole(json["role"], g.id) let role = newRole(json["role"], g.id)
g.roles.add(role) g.roles.add(role)
var event = GuildRoleUpdateEvent(client: discordClient, guild: g, role: role, name: $EventType.evtGuildRoleUpdate) var event = GuildRoleUpdateEvent(shard: shard, guild: g, role: role, name: $EventType.evtGuildRoleUpdate)
dispatchEvent(event) dispatchEvent(event)
proc guildRoleUpdate(discordClient: DiscordClient, json: JsonNode) = proc guildRoleUpdate(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
let role = newRole(json["role"], g.id) let role = newRole(json["role"], g.id)
var index = -1 var index = -1
@ -227,11 +227,11 @@ proc guildRoleUpdate(discordClient: DiscordClient, json: JsonNode) =
g.roles[index] = role g.roles[index] = role
var event = GuildRoleUpdateEvent(client: discordClient, guild: g, role: role, name: $EventType.evtGuildRoleUpdate) var event = GuildRoleUpdateEvent(shard: shard, guild: g, role: role, name: $EventType.evtGuildRoleUpdate)
dispatchEvent(event) dispatchEvent(event)
proc guildRoleDelete(discordClient: DiscordClient, json: JsonNode) = proc guildRoleDelete(shard: Shard, json: JsonNode) =
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
let roleID = getIDFromJson(json["role_id"].getStr()) let roleID = getIDFromJson(json["role_id"].getStr())
var role: Role var role: Role
@ -244,53 +244,53 @@ proc guildRoleDelete(discordClient: DiscordClient, json: JsonNode) =
if index != -1: if index != -1:
g.roles.delete(index) g.roles.delete(index)
var event = GuildRoleDeleteEvent(client: discordClient, guild: g, role: role, name: $EventType.evtGuildRoleDelete) var event = GuildRoleDeleteEvent(shard: shard, guild: g, role: role, name: $EventType.evtGuildRoleDelete)
dispatchEvent(event) dispatchEvent(event)
proc inviteCreate(discordClient: DiscordClient, json: JsonNode) = proc inviteCreate(shard: Shard, json: JsonNode) =
var invite = newInvite(json) var invite = newInvite(json)
invite.channel = discordClient.cache.getChannel(getIDFromJson(json["channel_id"].getStr())) invite.channel = shard.client.cache.getChannel(getIDFromJson(json["channel_id"].getStr()))
if (json.contains("guild_id")): if (json.contains("guild_id")):
invite.guildID =getIDFromJson(json["guild_id"].getStr()) invite.guildID =getIDFromJson(json["guild_id"].getStr())
var event = InviteCreateEvent(client: discordClient, invite: invite, name: $EventType.evtInviteCreate) var event = InviteCreateEvent(shard: shard, invite: invite, name: $EventType.evtInviteCreate)
dispatchEvent(event) dispatchEvent(event)
proc inviteDelete(discordClient: DiscordClient, json: JsonNode) = proc inviteDelete(shard: Shard, json: JsonNode) =
var event = InviteDeleteEvent(client: discordClient, name: $EventType.evtInviteDelete) var event = InviteDeleteEvent(shard: shard, name: $EventType.evtInviteDelete)
event.channel = discordClient.cache.getChannel(getIDFromJson(json["channel_id"].getStr())) event.channel = shard.client.cache.getChannel(getIDFromJson(json["channel_id"].getStr()))
event.code = json["code"].getStr() event.code = json["code"].getStr()
if (json.contains("guild_id")): if (json.contains("guild_id")):
event.guild = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) event.guild = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
dispatchEvent(event) dispatchEvent(event)
proc messageCreateEvent(discordClient: DiscordClient, json: JsonNode) = proc messageCreateEvent(shard: Shard, json: JsonNode) =
let msg = newMessage(json) let msg = newMessage(json)
discordClient.cache.messages[msg.id] = msg shard.client.cache.messages[msg.id] = msg
let messageCreateEvnt = MessageCreateEvent(client: discordClient, message: msg, name: $EventType.evtMessageCreate) let messageCreateEvnt = MessageCreateEvent(shard: shard, message: msg, name: $EventType.evtMessageCreate)
dispatchEvent(messageCreateEvnt) dispatchEvent(messageCreateEvnt)
proc messageUpdateEvent(discordClient: DiscordClient, json: JsonNode) = proc messageUpdateEvent(shard: Shard, json: JsonNode) =
let msg = newMessage(json) let msg = newMessage(json)
discordClient.cache.messages[msg.id] = msg shard.client.cache.messages[msg.id] = msg
let event = MessageCreateEvent(client: discordClient, message: msg, name: $EventType.evtMessageUpdate) let event = MessageCreateEvent(shard: shard, message: msg, name: $EventType.evtMessageUpdate)
dispatchEvent(event) dispatchEvent(event)
proc messageDeleteEvent(discordClient: DiscordClient, json: JsonNode) = proc messageDeleteEvent(shard: Shard, json: JsonNode) =
let msgID = getIDFromJson(json["id"].getStr()) let msgID = getIDFromJson(json["id"].getStr())
var msg: Message var msg: Message
if discordClient.cache.messages.hasKey(msgID): if shard.client.cache.messages.hasKey(msgID):
discard discordClient.cache.messages.pop(msgID, msg) discard shard.client.cache.messages.pop(msgID, msg)
else: else:
msg = Message(id: msgID) msg = Message(id: msgID)
@ -298,27 +298,27 @@ proc messageDeleteEvent(discordClient: DiscordClient, json: JsonNode) =
if (json.contains("guild_id")): if (json.contains("guild_id")):
msg.guildID = getIDFromJson(json["guild_id"].getStr()) msg.guildID = getIDFromJson(json["guild_id"].getStr())
let event = MessageDeleteEvent(client: discordClient, message: msg, name: $EventType.evtMessageDelete) let event = MessageDeleteEvent(shard: shard, message: msg, name: $EventType.evtMessageDelete)
dispatchEvent(event) dispatchEvent(event)
proc messageDeleteBulkEvent(discordClient: DiscordClient, json: JsonNode) = proc messageDeleteBulkEvent(shard: Shard, json: JsonNode) =
var event = MessageDeleteBulkEvent(client: discordClient, name: $EventType.evtMessageDeleteBulk) var event = MessageDeleteBulkEvent(shard: shard, name: $EventType.evtMessageDeleteBulk)
event.channel = discordClient.cache.getChannel(getIDFromJson(json["channel_id"].getStr())) event.channel = shard.client.cache.getChannel(getIDFromJson(json["channel_id"].getStr()))
if (json.contains("guild_id")): if (json.contains("guild_id")):
event.guild = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) event.guild = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
for msgIDJson in json["ids"]: for msgIDJson in json["ids"]:
let msgID = getIDFromJson(msgIDJson.getStr()) let msgID = getIDFromJson(msgIDJson.getStr())
var msg: Message var msg: Message
if discordClient.cache.messages.hasKey(msgID): if shard.client.cache.messages.hasKey(msgID):
discard discordClient.cache.messages.pop(msgID, msg) discard shard.client.cache.messages.pop(msgID, msg)
else: else:
let channelID = getIDFromJson(json["channel_id"].getStr()) let channelID = getIDFromJson(json["channel_id"].getStr())
msg = Message(id: msgID, channelID: channelID) msg = Message(id: msgID, channelID: channelID)
event.channel = discordClient.cache.getChannel(msg.channelID) event.channel = shard.client.cache.getChannel(msg.channelID)
if (json.contains("guild_id")): if (json.contains("guild_id")):
msg.guildID = getIDFromJson(json["guild_id"].getStr()) msg.guildID = getIDFromJson(json["guild_id"].getStr())
@ -326,13 +326,13 @@ proc messageDeleteBulkEvent(discordClient: DiscordClient, json: JsonNode) =
dispatchEvent(event) dispatchEvent(event)
proc messageReactionAdd(discordClient: DiscordClient, json: JsonNode) = proc messageReactionAdd(shard: Shard, json: JsonNode) =
var event = MessageReactionAddEvent(client: discordClient, name: $EventType.evtMessageReactionAdd) var event = MessageReactionAddEvent(shard: shard, name: $EventType.evtMessageReactionAdd)
let msgID = getIDFromJson(json["message_id"].getStr()) let msgID = getIDFromJson(json["message_id"].getStr())
var msg: Message var msg: Message
if discordClient.cache.messages.hasKey(msgID): if shard.client.cache.messages.hasKey(msgID):
msg = discordClient.cache.messages[msgID] msg = shard.client.cache.messages[msgID]
else: else:
msg = Message(id: msgID) msg = Message(id: msgID)
@ -340,7 +340,7 @@ proc messageReactionAdd(discordClient: DiscordClient, json: JsonNode) =
if (json.contains("guild_id")): if (json.contains("guild_id")):
msg.guildID = getIDFromJson(json["guild_id"].getStr()) msg.guildID = getIDFromJson(json["guild_id"].getStr())
event.user = discordClient.cache.getUser(getIDFromJson(json["user_id"].getStr())) event.user = shard.client.cache.getUser(getIDFromJson(json["user_id"].getStr()))
if (json.contains("member")): if (json.contains("member")):
event.member = newGuildMember(json["member"], msg.guildID) event.member = newGuildMember(json["member"], msg.guildID)
@ -349,13 +349,13 @@ proc messageReactionAdd(discordClient: DiscordClient, json: JsonNode) =
dispatchEvent(event) dispatchEvent(event)
proc messageReactionRemove(discordClient: DiscordClient, json: JsonNode) = proc messageReactionRemove(shard: Shard, json: JsonNode) =
var event = MessageReactionRemoveEvent(client: discordClient, name: $EventType.evtMessageReactionRemove) var event = MessageReactionRemoveEvent(shard: shard, name: $EventType.evtMessageReactionRemove)
let msgID = getIDFromJson(json["message_id"].getStr()) let msgID = getIDFromJson(json["message_id"].getStr())
var msg: Message var msg: Message
if discordClient.cache.messages.hasKey(msgID): if shard.client.cache.messages.hasKey(msgID):
msg = discordClient.cache.messages[msgID] msg = shard.client.cache.messages[msgID]
else: else:
msg = Message(id: msgID) msg = Message(id: msgID)
@ -363,19 +363,19 @@ proc messageReactionRemove(discordClient: DiscordClient, json: JsonNode) =
if (json.contains("guild_id")): if (json.contains("guild_id")):
msg.guildID = getIDFromJson(json["guild_id"].getStr()) msg.guildID = getIDFromJson(json["guild_id"].getStr())
event.user = discordClient.cache.getUser(getIDFromJson(json["user_id"].getStr())) event.user = shard.client.cache.getUser(getIDFromJson(json["user_id"].getStr()))
event.emoji = newEmoji(json["emoji"], msg.guildID) event.emoji = newEmoji(json["emoji"], msg.guildID)
dispatchEvent(event) dispatchEvent(event)
proc messageReactionRemoveAll(discordClient: DiscordClient, json: JsonNode) = proc messageReactionRemoveAll(shard: Shard, json: JsonNode) =
var event = MessageReactionRemoveAllEvent(client: discordClient, name: $EventType.evtMessageReactionRemoveAll) var event = MessageReactionRemoveAllEvent(shard: shard, name: $EventType.evtMessageReactionRemoveAll)
let msgID = getIDFromJson(json["message_id"].getStr()) let msgID = getIDFromJson(json["message_id"].getStr())
var msg: Message var msg: Message
if discordClient.cache.messages.hasKey(msgID): if shard.client.cache.messages.hasKey(msgID):
msg = discordClient.cache.messages[msgID] msg = shard.client.cache.messages[msgID]
else: else:
msg = Message(id: msgID) msg = Message(id: msgID)
@ -385,13 +385,13 @@ proc messageReactionRemoveAll(discordClient: DiscordClient, json: JsonNode) =
dispatchEvent(event) dispatchEvent(event)
proc messageReactionRemoveEmoji(discordClient: DiscordClient, json: JsonNode) = proc messageReactionRemoveEmoji(shard: Shard, json: JsonNode) =
var event = MessageReactionRemoveEmojiEvent(client: discordClient, name: $EventType.evtMessageReactionRemoveEmoji) var event = MessageReactionRemoveEmojiEvent(shard: shard, name: $EventType.evtMessageReactionRemoveEmoji)
let msgID = getIDFromJson(json["message_id"].getStr()) let msgID = getIDFromJson(json["message_id"].getStr())
var msg: Message var msg: Message
if discordClient.cache.messages.hasKey(msgID): if shard.client.cache.messages.hasKey(msgID):
msg = discordClient.cache.messages[msgID] msg = shard.client.cache.messages[msgID]
else: else:
msg = Message(id: msgID) msg = Message(id: msgID)
@ -403,10 +403,10 @@ proc messageReactionRemoveEmoji(discordClient: DiscordClient, json: JsonNode) =
dispatchEvent(event) dispatchEvent(event)
proc presenceUpdate(discordClient: DiscordClient, json: JsonNode) = proc presenceUpdate(shard: Shard, json: JsonNode) =
# This proc doesn't actually dispatch any events, # This proc doesn't actually dispatch any events,
# it just updates member.presence # it just updates member.presence
var g = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) var g = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
var member = g.getGuildMember(getIDFromJson(json["user"]["id"].getStr())) var member = g.getGuildMember(getIDFromJson(json["user"]["id"].getStr()))
# Make sure some member fields are upto date. # Make sure some member fields are upto date.
@ -421,51 +421,51 @@ proc presenceUpdate(discordClient: DiscordClient, json: JsonNode) =
member.presence = newPresence(json) member.presence = newPresence(json)
proc typingStart(discordClient: DiscordClient, json: JsonNode) = proc typingStart(shard: Shard, json: JsonNode) =
var event = TypingStartEvent(client: discordClient, name: $EventType.evtTypingStart) var event = TypingStartEvent(shard: shard, name: $EventType.evtTypingStart)
event.channel = discordClient.cache.getChannel(getIDFromJson(json["channel_id"].getStr())) event.channel = shard.client.cache.getChannel(getIDFromJson(json["channel_id"].getStr()))
if (json.contains("guild_id")): if (json.contains("guild_id")):
event.channel.guildID = getIDFromJson(json["guild_id"].getStr()) event.channel.guildID = getIDFromJson(json["guild_id"].getStr())
event.user = discordClient.cache.getUser(getIDFromJson(json["user_id"].getStr())) event.user = shard.client.cache.getUser(getIDFromJson(json["user_id"].getStr()))
if (json.contains("member")): if (json.contains("member")):
event.member = newGuildMember(json["member"], event.channel.guildID) event.member = newGuildMember(json["member"], event.channel.guildID)
dispatchEvent(event) dispatchEvent(event)
proc userUpdate(discordClient: DiscordClient, json: JsonNode) = proc userUpdate(shard: Shard, json: JsonNode) =
var event = UserUpdateEvent(client: discordClient, name: $EventType.evtUserUpdate) var event = UserUpdateEvent(shard: shard, name: $EventType.evtUserUpdate)
event.user = newUser(json) event.user = newUser(json)
dispatchEvent(event) dispatchEvent(event)
proc voiceStateUpdate(discordClient: DiscordClient, json: JsonNode) = proc voiceStateUpdate(shard: Shard, json: JsonNode) =
var event = VoiceStateUpdateEvent(client: discordClient, name: $EventType.evtVoiceStateUpdate) var event = VoiceStateUpdateEvent(shard: shard, name: $EventType.evtVoiceStateUpdate)
dispatchEvent(event) dispatchEvent(event)
proc voiceServerUpdate(discordClient: DiscordClient, json: JsonNode) = proc voiceServerUpdate(shard: Shard, json: JsonNode) =
var event = VoiceServerUpdateEvent(client: discordClient, name: $EventType.evtVoiceServerUpdate) var event = VoiceServerUpdateEvent(shard: shard, name: $EventType.evtVoiceServerUpdate)
event.token = json["token"].getStr() event.token = json["token"].getStr()
event.guild = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) event.guild = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
event.endpoint = json["endpoint"].getStr() event.endpoint = json["endpoint"].getStr()
dispatchEvent(event) dispatchEvent(event)
proc webhooksUpdate(discordClient: DiscordClient, json: JsonNode) = proc webhooksUpdate(shard: Shard, json: JsonNode) =
var event = WebhooksUpdateEvent(client: discordClient, name: $EventType.evtWebhooksUpdate) var event = WebhooksUpdateEvent(shard: shard, name: $EventType.evtWebhooksUpdate)
event.guild = discordClient.cache.getGuild(getIDFromJson(json["guild_id"].getStr())) event.guild = shard.client.cache.getGuild(getIDFromJson(json["guild_id"].getStr()))
event.channel = discordClient.cache.getChannel(getIDFromJson(json["channel_id"].getStr())) event.channel = shard.client.cache.getChannel(getIDFromJson(json["channel_id"].getStr()))
dispatchEvent(event) dispatchEvent(event)
let internalEventTable: Table[string, proc(discordClient: DiscordClient, json: JsonNode) {.nimcall.}] = { let internalEventTable: Table[string, proc(shard: Shard, json: JsonNode) {.nimcall.}] = {
"READY": readyEvent, "READY": readyEvent,
"CHANNEL_CREATE": channelCreateEvent, "CHANNEL_CREATE": channelCreateEvent,
"CHANNEL_UPDATE": channelUpdateEvent, "CHANNEL_UPDATE": channelUpdateEvent,
@ -502,11 +502,11 @@ let internalEventTable: Table[string, proc(discordClient: DiscordClient, json: J
"WEBHOOKS_UPDATE": webhooksUpdate "WEBHOOKS_UPDATE": webhooksUpdate
}.toTable }.toTable
proc handleDiscordEvent*(discordClient: DiscordClient, json: JsonNode, eventName: string) {.async.} = proc handleDiscordEvent*(shard: Shard, json: JsonNode, eventName: string) {.async.} =
## Handles, and dispatches, a gateway event. Only used internally. ## Handles, and dispatches, a gateway event. Only used internally.
if (internalEventTable.hasKey(eventName)): if (internalEventTable.hasKey(eventName)):
let eventProc: proc(discordClient: DiscordClient, json: JsonNode) = internalEventTable[eventName] let eventProc: proc(shard: Shard, json: JsonNode) = internalEventTable[eventName]
eventProc(discordClient, json) eventProc(shard, json)
else: else:
echo "Failed to find event: ", eventName echo "Failed to find event: ", eventName

View File

@ -46,7 +46,7 @@ type
BaseEvent* = object of RootObj BaseEvent* = object of RootObj
## Base event that all events inherit from. ## Base event that all events inherit from.
## It stores a reference to the DiscordClient and name of the event. ## It stores a reference to the DiscordClient and name of the event.
client*: DiscordClient shard*: Shard
name*: string name*: string
# Socket Events # Socket Events