#include "network.h"
CtcpHandler::CtcpHandler(NetworkConnection *parent)
- : BasicHandler(parent) {
-
- QString MQUOTE = QString('\020');
- ctcpMDequoteHash[MQUOTE + '0'] = QString('\000');
- ctcpMDequoteHash[MQUOTE + 'n'] = QString('\n');
- ctcpMDequoteHash[MQUOTE + 'r'] = QString('\r');
+ : BasicHandler(parent),
+ XDELIM("\001")
+{
+
+ QByteArray MQUOTE = QByteArray("\020");
+ ctcpMDequoteHash[MQUOTE + '0'] = QByteArray("\000");
+ ctcpMDequoteHash[MQUOTE + 'n'] = QByteArray("\n");
+ ctcpMDequoteHash[MQUOTE + 'r'] = QByteArray("\r");
ctcpMDequoteHash[MQUOTE + MQUOTE] = MQUOTE;
- XDELIM = QString('\001');
- QString XQUOTE = QString('\134');
+ QByteArray XQUOTE = QByteArray("\134");
ctcpXDelimDequoteHash[XQUOTE + XQUOTE] = XQUOTE;
- ctcpXDelimDequoteHash[XQUOTE + QString('a')] = XDELIM;
+ ctcpXDelimDequoteHash[XQUOTE + QByteArray("a")] = XDELIM;
}
-QString CtcpHandler::dequote(QString message) {
- QString dequotedMessage;
- QString messagepart;
- QHash<QString, QString>::iterator ctcpquote;
+QByteArray CtcpHandler::dequote(const QByteArray &message) {
+ QByteArray dequotedMessage;
+ QByteArray messagepart;
+ QHash<QByteArray, QByteArray>::iterator ctcpquote;
// copy dequote Message
for(int i = 0; i < message.size(); i++) {
- messagepart = message[i];
+ messagepart = message.mid(i,1);
if(i+1 < message.size()) {
for(ctcpquote = ctcpMDequoteHash.begin(); ctcpquote != ctcpMDequoteHash.end(); ++ctcpquote) {
if(message.mid(i,2) == ctcpquote.key()) {
}
-QString CtcpHandler::XdelimDequote(QString message) {
- QString dequotedMessage;
- QString messagepart;
- QHash<QString, QString>::iterator xdelimquote;
+QByteArray CtcpHandler::xdelimDequote(const QByteArray &message) {
+ QByteArray dequotedMessage;
+ QByteArray messagepart;
+ QHash<QByteArray, QByteArray>::iterator xdelimquote;
for(int i = 0; i < message.size(); i++) {
- messagepart = message[i];
+ messagepart = message.mid(i,1);
if(i+1 < message.size()) {
for(xdelimquote = ctcpXDelimDequoteHash.begin(); xdelimquote != ctcpXDelimDequoteHash.end(); ++xdelimquote) {
if(message.mid(i,2) == xdelimquote.key()) {
return dequotedMessage;
}
-void CtcpHandler::parse(Message::Type messageType, QString prefix, QString target, QString message) {
- QString ctcp;
+void CtcpHandler::parse(Message::Type messageType, const QString &prefix, const QString &target, const QByteArray &message) {
+ QByteArray ctcp;
//lowlevel message dequote
- QString dequotedMessage = dequote(message);
+ QByteArray dequotedMessage = dequote(message);
- CtcpType ctcptype = (messageType == Message::Notice)
+ CtcpType ctcptype = messageType == Message::Notice
? CtcpReply
: CtcpQuery;
+
+ quint8 flags = (messageType == Message::Notice && !network()->isChannelName(target))
+ ? Message::Redirected
+ : Message::None;
- BufferInfo::Type bufferType = typeByTarget(target);
-
// extract tagged / extended data
- while(dequotedMessage.contains(XDELIM)) {
- if(dequotedMessage.indexOf(XDELIM) > 0)
- emit displayMsg(messageType, bufferType, target, dequotedMessage.section(XDELIM,0,0), prefix);
- // messages << dequotedMessage.section(XDELIM,0,0), prefix);
- ctcp = XdelimDequote(dequotedMessage.section(XDELIM,1,1));
- dequotedMessage = dequotedMessage.section(XDELIM,2,2);
+ int xdelimPos = -1;
+ int xdelimEndPos = -1;
+ int spacePos = -1;
+ while((xdelimPos = dequotedMessage.indexOf(XDELIM)) != -1) {
+ if(xdelimPos > 0)
+ displayMsg(messageType, target, userDecode(target, dequotedMessage.left(xdelimPos)), prefix, flags);
+
+ xdelimEndPos = dequotedMessage.indexOf(XDELIM, xdelimPos + 1);
+
+ ctcp = xdelimDequote(dequotedMessage.mid(xdelimPos + 1, xdelimEndPos - xdelimPos - 1));
+ dequotedMessage = dequotedMessage.mid(xdelimEndPos + 1);
//dispatch the ctcp command
- QString ctcpcmd = ctcp.section(' ', 0, 0);
- QString ctcpparam = ctcp.section(' ', 1);
+ spacePos = ctcp.indexOf(' ');
+ QString ctcpcmd = userDecode(target, ctcp.left(spacePos));
+ QString ctcpparam = userDecode(target, ctcp.mid(spacePos + 1));
handle(ctcpcmd, Q_ARG(CtcpType, ctcptype), Q_ARG(QString, prefix), Q_ARG(QString, target), Q_ARG(QString, ctcpparam));
}
if(!dequotedMessage.isEmpty())
- emit displayMsg(messageType, bufferType, target, dequotedMessage, prefix);
-
+ displayMsg(messageType, target, userDecode(target, dequotedMessage), prefix, flags);
}
-QString CtcpHandler::pack(QString ctcpTag, QString message) {
+QByteArray CtcpHandler::pack(const QByteArray &ctcpTag, const QByteArray &message) {
return XDELIM + ctcpTag + ' ' + message + XDELIM;
}
// TODO handle encodings correctly!
-void CtcpHandler::query(QString bufname, QString ctcpTag, QString message) {
- QStringList params;
- params << bufname << pack(ctcpTag, message);
- emit putCmd("PRIVMSG", serverEncode(params));
+void CtcpHandler::query(const QString &bufname, const QString &ctcpTag, const QString &message) {
+ QList<QByteArray> params;
+ params << serverEncode(bufname) << pack(serverEncode(ctcpTag), userEncode(bufname, message));
+ emit putCmd("PRIVMSG", params);
}
-void CtcpHandler::reply(QString bufname, QString ctcpTag, QString message) {
- QStringList params;
- params << bufname << pack(ctcpTag, message);
- emit putCmd("NOTICE", serverEncode(params));
+void CtcpHandler::reply(const QString &bufname, const QString &ctcpTag, const QString &message) {
+ QList<QByteArray> params;
+ params << serverEncode(bufname) << pack(serverEncode(ctcpTag), userEncode(bufname, message));
+ emit putCmd("NOTICE", params);
}
//******************************/
// CTCP HANDLER
//******************************/
-void CtcpHandler::handleAction(CtcpType ctcptype, QString prefix, QString target, QString param) {
+void CtcpHandler::handleAction(CtcpType ctcptype, const QString &prefix, const QString &target, const QString ¶m) {
Q_UNUSED(ctcptype)
emit displayMsg(Message::Action, typeByTarget(target), target, param, prefix);
}
-void CtcpHandler::handlePing(CtcpType ctcptype, QString prefix, QString target, QString param) {
+void CtcpHandler::handlePing(CtcpType ctcptype, const QString &prefix, const QString &target, const QString ¶m) {
Q_UNUSED(target)
if(ctcptype == CtcpQuery) {
reply(nickFromMask(prefix), "PING", param);
}
}
-void CtcpHandler::handleVersion(CtcpType ctcptype, QString prefix, QString target, QString param) {
+void CtcpHandler::handleVersion(CtcpType ctcptype, const QString &prefix, const QString &target, const QString ¶m) {
Q_UNUSED(target)
if(ctcptype == CtcpQuery) {
// FIXME use real Info about quassel :)
}
}
-void CtcpHandler::defaultHandler(QString cmd, CtcpType ctcptype, QString prefix, QString target, QString param) {
+void CtcpHandler::defaultHandler(const QString &cmd, CtcpType ctcptype, const QString &prefix, const QString &target, const QString ¶m) {
Q_UNUSED(ctcptype);
Q_UNUSED(target);
Q_UNUSED(param);
enum CtcpType {CtcpQuery, CtcpReply};
- void parse(Message::Type, QString prefix, QString target, QString message);
+ void parse(Message::Type, const QString &prefix, const QString &target, const QByteArray &message);
- QString dequote(QString);
- QString XdelimDequote(QString);
+ QByteArray dequote(const QByteArray &);
+ QByteArray xdelimDequote(const QByteArray &);
- QString pack(QString ctcpTag, QString message);
- void query(QString bufname, QString ctcpTag, QString message);
- void reply(QString bufname, QString ctcpTag, QString message);
+ QByteArray pack(const QByteArray &ctcpTag, const QByteArray &message);
+ void query(const QString &bufname, const QString &ctcpTag, const QString &message);
+ void reply(const QString &bufname, const QString &ctcpTag, const QString &message);
public slots:
- void handleAction(CtcpType, QString prefix, QString target, QString param);
- void handlePing(CtcpType, QString prefix, QString target, QString param);
- void handleVersion(CtcpType, QString prefix, QString target, QString param);
+ void handleAction(CtcpType, const QString &prefix, const QString &target, const QString ¶m);
+ void handlePing(CtcpType, const QString &prefix, const QString &target, const QString ¶m);
+ void handleVersion(CtcpType, const QString &prefix, const QString &target, const QString ¶m);
- void defaultHandler(QString cmd, CtcpType ctcptype, QString prefix, QString target, QString param);
+ void defaultHandler(const QString &cmd, CtcpType ctcptype, const QString &prefix, const QString &target, const QString ¶m);
private:
- QString XDELIM;
- QHash<QString, QString> ctcpMDequoteHash;
- QHash<QString, QString> ctcpXDelimDequoteHash;
-
-
+ QByteArray XDELIM;
+ QHash<QByteArray, QByteArray> ctcpMDequoteHash;
+ QHash<QByteArray, QByteArray> ctcpXDelimDequoteHash;
};
#include <QDebug>
-IrcServerHandler::IrcServerHandler(NetworkConnection *parent) : BasicHandler(parent) {
- _whois = false;
+IrcServerHandler::IrcServerHandler(NetworkConnection *parent)
+ : BasicHandler(parent),
+ _whois(false)
+{
}
IrcServerHandler::~IrcServerHandler() {
emit displayMsg(Message::Error, BufferInfo::StatusBuffer, "", params.join(" "), prefix);
break;
// Server error messages, display them in red. First param will be appended.
- case 401:
- {
- // FIXME needs proper redirection
+ case 401: {
QString target = params.takeFirst();
- BufferInfo::Type bufferType = network()->isChannelName(target)
- ? BufferInfo::ChannelBuffer
- : BufferInfo::QueryBuffer;
- emit displayMsg(Message::Error, BufferInfo::StatusBuffer, "", params.join(" ") + " " + target, prefix);
- emit displayMsg(Message::Error, bufferType, target, params.join(" ") + " " + target, prefix);
- break;
+ displayMsg(Message::Error, target, params.join(" ") + " " + target, prefix, Message::Redirected);
+ break;
}
- case 402: case 403: case 404: case 406: case 408: case 415: case 421: case 442:
- { QString channelName = params.takeFirst();
+ case 402: case 403: case 404: case 406: case 408: case 415: case 421: case 442: {
+ QString channelName = params.takeFirst();
emit displayMsg(Message::Error, BufferInfo::StatusBuffer, "", params.join(" ") + " " + channelName, prefix);
break;
}
return;
}
+ QString target = serverDecode(params[0]);
+
+
// check if it's only a Server Message or if it's a regular Notice
if(network()->currentServer().isEmpty() || network()->currentServer() == prefix) {
emit displayMsg(Message::Server, BufferInfo::StatusBuffer, "", serverDecode(params[1]), prefix);
return;
}
- QString target = serverDecode(params[0]);
+
// kick notices to the server buffer if they are directly addressed to us
if(network()->isMyNick(target))
? nickFromMask(prefix)
: prefix;
- networkConnection()->ctcpHandler()->parse(Message::Notice, sender, target, userDecode(sender, params[1]));
+ networkConnection()->ctcpHandler()->parse(Message::Notice, sender, target, params[1]);
}
void IrcServerHandler::handlePart(const QString &prefix, const QList<QByteArray> ¶ms) {
// it's possible to pack multiple privmsgs into one param using ctcp
// - > we let the ctcpHandler do the work
- networkConnection()->ctcpHandler()->parse(Message::Plain, prefix, target, userDecode(ircuser->nick(), msg));
+ networkConnection()->ctcpHandler()->parse(Message::Plain, prefix, target, msg);
}
void IrcServerHandler::handleQuit(const QString &prefix, const QList<QByteArray> ¶ms) {