-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathTwitchIRC.cpp
121 lines (110 loc) · 3.23 KB
/
TwitchIRC.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
#include "TwitchIRC.h"
#include "MainWindow.h"
#include "Parser.h"
#pragma comment(lib, "libcrypto.lib")
#pragma comment(lib, "libssl.lib")
#pragma comment(lib, "crypt32.lib")
using std::string;
template<class T>
using shared_ptr = std::shared_ptr<T>;
TwitchIRC::TwitchIRC(string server_url, std::shared_ptr<io_service> service) : client(std::move(server_url), false)
{
if (service)
client.io_service = service;
using namespace std::placeholders;
client.on_open = std::bind(&TwitchIRC::OnOpen, this, _1);
client.on_close = std::bind(&TwitchIRC::OnClose, this, _1, _2, _3);
client.on_error = std::bind(&TwitchIRC::OnError, this, _1, _2);
client.on_message = std::bind(&TwitchIRC::OnMessage, this, _1, _2);
}
void TwitchIRC::Connect()
{
client.start();
}
void TwitchIRC::Disconnect()
{
if (client_connection)
client_connection->send_close(1000);
client.stop();
}
void TwitchIRC::Exit()
{
client.io_service->stop();
}
void TwitchIRC::SetUser(string username)
{
this->username = std::move(username);
}
void TwitchIRC::SetPass(string oauth_token)
{
this->oauth_token = std::move(oauth_token);
}
void TwitchIRC::SendMessage(string message)
{
if (client_connection)
client_connection->send(message);
}
bool TwitchIRC::IsConnected() const
{
return client_connection != nullptr;
}
void TwitchIRC::OnOpen(shared_ptr<WssClient::Connection> connection)
{
client_connection = connection;
connection->send("CAP REQ :twitch.tv/tags twitch.tv/commands");
connection->send(string("PASS ") + "oauth:" + oauth_token);
connection->send(string("NICK ") + username);
connection->send(string("USER ") + username + "8 * :" + username);
MainWindow::RPC(&MainWindow::OnChatConnected);
}
void TwitchIRC::OnClose(shared_ptr<WssClient::Connection> /*connection*/, int status, const string & /*reason*/)
{
client_connection.reset();
MainWindow::RPC(&MainWindow::OnChatDisconnected);
}
void TwitchIRC::OnError(shared_ptr<WssClient::Connection> /*connection*/, const SimpleWeb::error_code &ec)
{
client_connection.reset();
MainWindow::RPC(&MainWindow::OnChatDisconnected);
}
std::string GetProperty(const std::vector<TwitchMessage::Property> &properties, const std::string &key)
{
for (const auto &entry : properties)
{
if (entry.first == key)
return entry.second;
}
return std::string();
}
void RemoveBackwards(std::string &str, const std::string &toremove)
{
for (;;)
{
size_t pos = str.find_first_of(toremove);
if (pos + toremove.length() == str.length())
str.erase(pos);
else
break;
}
}
void TwitchIRC::OnMessage(shared_ptr<WssClient::Connection> connection, shared_ptr<WssClient::InMessage> in_message)
{
boost::variant<TwitchMessage, TwitchPing> out;
auto str = in_message->string();
RemoveBackwards(str, "\r\n");
RemoveBackwards(str, "\n");
//OutputDebugString((str + "\n\n").c_str());
bool res = ParseMessage(str, out);
if (res)
{
if (TwitchMessage *msg = boost::get<TwitchMessage>(&out))
{
auto displayname = GetProperty(msg->properties, "display-name");
MainWindow::RPC(&MainWindow::OnChatMessage, displayname, msg->message);
}
else if (TwitchPing *ping = boost::get<TwitchPing>(&out))
{
SendMessage("PONG");
}
}
}