have are in a new namespace Global. This is bound to change to Quassel:: or sumthing.
Oh yeah, and if you find out why QPainter complains, feel free to tell me or fix it.
Everything seems to work, but we still get spurious debug output.
connect(&socket, SIGNAL(disconnected()), this, SLOT(coreDisconnected()));
connect(&socket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(serverError(QAbstractSocket::SocketError)));
- connect(Global::instance(), SIGNAL(dataPutLocally(UserId, QString)), this, SLOT(updateCoreData(UserId, QString)));
- connect(clientProxy, SIGNAL(csUpdateGlobalData(QString, QVariant)), this, SLOT(updateLocalData(QString, QVariant)));
connect(this, SIGNAL(sendSessionData(const QString &, const QVariant &)), clientProxy, SLOT(gsSessionDataChanged(const QString &, const QVariant &)));
connect(clientProxy, SIGNAL(csSessionDataChanged(const QString &, const QVariant &)), this, SLOT(recvSessionData(const QString &, const QVariant &)));
// TODO connect to remote cores
}
- VarMap data = state["CoreData"].toMap();
- foreach(QString key, data.keys()) {
- Global::updateData(key, data[key]);
- }
- //if(!Global::data("CoreReady").toBool()) {
- // qFatal("Something is wrong, getting invalid data from core!");
- //}
-
VarMap sessionState = state["SessionState"].toMap();
VarMap sessData = sessionState["SessionData"].toMap();
foreach(QString key, sessData.keys()) {
}
}
-void Client::updateCoreData(UserId, QString key) {
- if(clientMode == LocalCore) return;
- QVariant data = Global::data(key);
- recvProxySignal(GS_UPDATE_GLOBAL_DATA, key, data, QVariant());
-}
-
-void Client::updateLocalData(QString key, QVariant data) {
- Global::updateData(key, data);
-}
-
void Client::recvSessionData(const QString &key, const QVariant &data) {
sessionData[key] = data;
emit sessionDataChanged(key, data);
void disconnectFromCore();
private slots:
- void updateCoreData(UserId, QString);
- void updateLocalData(QString, QVariant);
void recvSessionData(const QString &key, const QVariant &data);
void recvProxySignal(ClientSignal sig, QVariant arg1, QVariant arg2, QVariant arg3);
case CS_SERVER_STATE: emit csServerState(arg1.toString(), arg2.toMap()); break;
case CS_SERVER_CONNECTED: emit csServerConnected(arg1.toString()); break;
case CS_SERVER_DISCONNECTED: emit csServerDisconnected(arg1.toString()); break;
- case CS_UPDATE_GLOBAL_DATA: emit csUpdateGlobalData(arg1.toString(), arg2); break;
- //case CS_GLOBAL_DATA_CHANGED: emit csGlobalDataChanged(arg1.toString()); break;
case CS_SESSION_DATA_CHANGED: emit csSessionDataChanged(arg1.toString(), arg2); break;
case CS_DISPLAY_MSG: emit csDisplayMsg(arg1.value<Message>()); break;
case CS_DISPLAY_STATUS_MSG: emit csDisplayStatusMsg(arg1.toString(), arg2.toString()); break;
void csServerDisconnected(QString);
void csDisplayMsg(Message);
void csDisplayStatusMsg(QString, QString);
- void csUpdateGlobalData(QString key, QVariant data);
- void csGlobalDataChanged(QString key);
void csSessionDataChanged(const QString &key, const QVariant &data);
void csModeSet(QString, QString, QString);
void csTopicSet(QString, QString, QString);
SET(common_SRCS global.cpp logger.cpp message.cpp settings.cpp util.cpp ircuser.cpp)
-SET(common_HDRS message.h util.h)
-SET(common_MOCS global.h logger.h ircuser.h quasselui.h settings.h)
+SET(common_HDRS global.h message.h util.h)
+SET(common_MOCS logger.h ircuser.h quasselui.h settings.h)
QT4_WRAP_CPP(_MOC ${common_MOCS})
ADD_LIBRARY(common ${common_SRCS} ${_MOC})
extern void messageHandler(QtMsgType type, const char *msg);
-Global *Global::instanceptr = 0;
-
-Global * Global::instance() {
- if(instanceptr) return instanceptr;
- return instanceptr = new Global();
-}
-
-void Global::destroy() {
- delete instanceptr;
- instanceptr = 0;
-}
-
-Global::Global() {
- qInstallMsgHandler(messageHandler);
- qRegisterMetaType<Message>("Message");
- qRegisterMetaTypeStreamOperators<Message>("Message");
- qRegisterMetaType<BufferId>("BufferId");
- qRegisterMetaTypeStreamOperators<BufferId>("BufferId");
-
- guiUser = 0;
-}
-
-Global::~Global() {
-
-
-}
-
-void Global::setGuiUser(UserId uid) {
- guiUser = uid;
-}
-
-QVariant Global::data(QString key, QVariant defval) {
- return data(guiUser, key, defval);
-}
-
-QVariant Global::data(UserId uid, QString key, QVariant defval) {
- QVariant d;
- mutex.lock();
- if(instance()->datastore[uid].contains(key)) d = instance()->datastore[uid][key];
- else d = defval;
- mutex.unlock();
- //qDebug() << "getData("<<key<<"): " << d;
- return d;
-}
-
-QStringList Global::keys() {
- return keys(guiUser);
-}
-
-QStringList Global::keys(UserId uid) {
- QStringList k;
- mutex.lock();
- k = instance()->datastore[uid].keys();
- mutex.unlock();
- return k;
-}
-
-void Global::putData(QString key, QVariant d) {
- putData(guiUser, key, d);
-}
-
-void Global::putData(UserId uid, QString key, QVariant d) {
- mutex.lock();
- instance()->datastore[uid][key] = d;
- mutex.unlock();
- emit instance()->dataPutLocally(uid, key);
-}
-
-void Global::updateData(QString key, QVariant d) {
- updateData(guiUser, key, d);
-}
-
-void Global::updateData(UserId uid, QString key, QVariant d) {
- mutex.lock();
- instance()->datastore[uid][key] = d;
- mutex.unlock();
- emit instance()->dataUpdatedRemotely(uid, key);
-}
-
/* not done yet */
/*
void Global::initIconMap() {
// return 0;
//}
-QMutex Global::mutex;
Global::RunMode Global::runMode;
-UserId Global::guiUser;
QString Global::quasselDir;
#define DEFAULT_PORT 4242
-class Global;
-
#include <QHash>
#include <QMutex>
#include <QString>
typedef uint UserId;
typedef uint MsgId;
-/**
- * This class is mostly a globally synchronized data store, meant for storing systemwide settings such
- * as identities or network lists. This class is a singleton, but not static as we'd like to use signals and
- * slots with it.
- * The global object is used in both Core and GUI clients. Storing and retrieving data is thread-safe.
- * \note While updated data is propagated to all the remote parts of Quassel quite quickly, the synchronization
- * protocol is in no way designed to guarantee strict consistency at all times. In other words, it may
- * well happen that different instances of global data differ from one another for a little while until
- * all update messages have been processed. You should never rely on all global data stores being consistent.
-*/
-class Global : public QObject {
- Q_OBJECT
-
- public:
- //static Logger *getLogger();
- //static void setLogger(Logger *);
-
-// static QIcon *getIcon(QString symbol);
-
- static Global *instance();
- static void destroy();
- static void setGuiUser(UserId);
-
- static QVariant data(QString key, QVariant defaultValue = QVariant());
- static QVariant data(UserId, QString key, QVariant defaultValue = QVariant());
- static QStringList keys();
- static QStringList keys(UserId);
-
- static void putData(QString key, QVariant data); ///< Store data changed locally, will be propagated to all other clients and the core
- static void putData(UserId, QString key, QVariant data);
-
- static void updateData(QString key, QVariant data); ///< Update stored data if requested by the core or other clients
- static void updateData(UserId, QString key, QVariant data);
-
- signals:
- void dataPutLocally(UserId, QString key);
- void dataUpdatedRemotely(UserId, QString key); // sent by remote update only!
-
- public:
- enum RunMode { Monolithic, ClientOnly, CoreOnly };
- static RunMode runMode;
- static QString quasselDir;
-
- private:
- Global();
- ~Global();
- static Global *instanceptr;
-
- static UserId guiUser;
- //static void initIconMap();
-
- //static Logger *logger;
-
-// static QString iconPath;
- //QHash<QString, QString> iconMap;
- static QMutex mutex;
- QHash<UserId, QHash<QString, QVariant> > datastore;
-};
+namespace Global {
+ enum RunMode { Monolithic, ClientOnly, CoreOnly };
+ extern RunMode runMode;
+ extern QString quasselDir;
+}
struct Exception {
Exception(QString msg = "Unknown Exception") : _msg(msg) {};
#ifndef _PROXY_COMMON_H_
#define _PROXY_COMMON_H_
-enum ClientSignal { GS_CLIENT_INIT, GS_USER_INPUT, GS_REQUEST_CONNECT, GS_UPDATE_GLOBAL_DATA, GS_IMPORT_BACKLOG,
+enum ClientSignal { GS_CLIENT_INIT, GS_USER_INPUT, GS_REQUEST_CONNECT, GS_IMPORT_BACKLOG,
GS_REQUEST_BACKLOG, GS_REQUEST_NETWORK_STATES, GS_SESSION_DATA_CHANGED
};
enum CoreSignal { CS_CORE_STATE, CS_SERVER_CONNECTED, CS_SERVER_DISCONNECTED, CS_SERVER_STATE,
- CS_DISPLAY_MSG, CS_DISPLAY_STATUS_MSG, CS_UPDATE_GLOBAL_DATA, CS_SESSION_DATA_CHANGED,
+ CS_DISPLAY_MSG, CS_DISPLAY_STATUS_MSG, CS_SESSION_DATA_CHANGED,
CS_MODE_SET, CS_TOPIC_SET, CS_SET_NICKS, CS_NICK_ADDED, CS_NICK_REMOVED, CS_NICK_RENAMED, CS_NICK_UPDATED,
CS_OWN_NICK_SET, CS_QUERY_REQUESTED, CS_BACKLOG_DATA, CS_UPDATE_BUFFERID
}
//SqliteStorage::init();
storage = new SqliteStorage();
- connect(Global::instance(), SIGNAL(dataPutLocally(UserId, QString)), this, SLOT(updateGlobalData(UserId, QString)));
connect(&server, SIGNAL(newConnection()), this, SLOT(incomingConnection()));
//startListening(); // FIXME
guiUser = 0;
createSession(guiUser);
} else guiUser = 0;
*/
- // Read global settings from config file
- QSettings s;
- s.beginGroup("Global");
- foreach(QString unum, s.childGroups()) {
- UserId uid = unum.toUInt();
- s.beginGroup(unum);
- foreach(QString key, s.childKeys()) {
- Global::updateData(uid, key, s.value(key));
- }
- s.endGroup();
- }
- s.endGroup();
}
Core::~Core() {
while(readDataFromDevice(socket, bsize, item)) {
if(validClients.contains(socket)) {
QList<QVariant> sigdata = item.toList();
- if((ClientSignal)sigdata[0].toInt() == GS_UPDATE_GLOBAL_DATA) {
- processClientUpdate(socket, sigdata[1].toString(), sigdata[2]);
- } else {
- sessions[validClients[socket]]->processSignal((ClientSignal)sigdata[0].toInt(), sigdata[1], sigdata[2], sigdata[3]);
- }
+ sessions[validClients[socket]]->processSignal((ClientSignal)sigdata[0].toInt(), sigdata[1], sigdata[2], sigdata[3]);
} else {
// we need to auth the client
try {
UserId uid = instance()->storage->validateUser(user, passwd);
QVariant reply = instance()->initSession(uid);
instance()->guiUser = uid;
- Global::setGuiUser(uid);
qDebug() << "Local client connected.";
return reply;
}
void Core::disconnectLocalClient() {
qDebug() << "Local client disconnected.";
instance()->guiUser = 0;
- Global::setGuiUser(0);
}
void Core::processClientInit(QTcpSocket *socket, const QVariant &v) {
//validClients[socket] = uid;
}
VarMap reply;
- VarMap coreData;
- QStringList dataKeys = Global::keys(uid);
- foreach(QString key, dataKeys) {
- coreData[key] = Global::data(uid, key);
- }
- reply["CoreData"] = coreData;
reply["SessionState"] = sess->sessionState();
return reply;
}
-void Core::processClientUpdate(QTcpSocket *socket, QString key, const QVariant &data) {
- UserId uid = validClients[socket];
- Global::updateData(uid, key, data);
- QList<QVariant> sigdata;
- sigdata.append(CS_UPDATE_GLOBAL_DATA); sigdata.append(key); sigdata.append(data); sigdata.append(QVariant());
- foreach(QTcpSocket *s, validClients.keys()) {
- if(validClients[s] == uid && s != socket) writeDataToDevice(s, QVariant(sigdata));
- }
-}
-
-void Core::updateGlobalData(UserId uid, QString key) {
- QVariant data = Global::data(uid, key);
- QList<QVariant> sigdata;
- sigdata.append(CS_UPDATE_GLOBAL_DATA); sigdata.append(key); sigdata.append(data); sigdata.append(QVariant());
- foreach(QTcpSocket *socket, validClients.keys()) {
- if(validClients[socket] == uid) writeDataToDevice(socket, QVariant(sigdata));
- }
-}
-
void Core::recvProxySignal(CoreSignal sig, QVariant arg1, QVariant arg2, QVariant arg3) {
CoreSession *sess = qobject_cast<CoreSession*>(sender());
Q_ASSERT(sess);
void incomingConnection();
void clientHasData();
void clientDisconnected();
- void updateGlobalData(UserId, QString);
private:
Core();
*/
QVariant initSession(UserId userId);
void processClientInit(QTcpSocket *socket, const QVariant &v);
- void processClientUpdate(QTcpSocket *socket, QString key, const QVariant &data);
UserId guiUser;
QHash<UserId, CoreSession *> sessions;
void CoreProxy::recv(ClientSignal sig, QVariant arg1, QVariant arg2, QVariant arg3) {
//qDebug() << "[CORE] Received signal" << sig << ":" << arg1<<arg2<<arg3;
switch(sig) {
- case GS_UPDATE_GLOBAL_DATA: emit gsPutGlobalData(arg1.toString(), arg2); break;
case GS_SESSION_DATA_CHANGED: emit gsSessionDataChanged(arg1.toString(), arg2); break;
case GS_USER_INPUT: emit gsUserInput(arg1.value<BufferId>(), arg2.toString()); break;
case GS_REQUEST_CONNECT: emit gsRequestConnect(arg1.toStringList()); break;
CoreProxy();
public slots:
- inline void csUpdateGlobalData(QString key, QVariant data) { send(CS_UPDATE_GLOBAL_DATA, key, data); }
inline void csSessionDataChanged(const QString &key, const QVariant &data) { send(CS_SESSION_DATA_CHANGED, key, data); }
inline void csServerConnected(QString net) { send(CS_SERVER_CONNECTED, net); }
inline void csServerDisconnected(QString net) { send(CS_SERVER_DISCONNECTED, net); }
inline void csGeneric(CoreSignal sig, QVariant v1 = QVariant(), QVariant v2 = QVariant(), QVariant v3 = QVariant()) { send(sig, v1, v2, v3); }
signals:
- void gsPutGlobalData(QString, QVariant);
void gsSessionDataChanged(const QString &, const QVariant &);
void gsUserInput(BufferId, QString);
void gsRequestConnect(QStringList networks);
connect(this, SIGNAL(backlogData(BufferId, QList<QVariant>, bool)), coreProxy, SLOT(csBacklogData(BufferId, QList<QVariant>, bool)));
connect(this, SIGNAL(bufferIdUpdated(BufferId)), coreProxy, SLOT(csUpdateBufferId(BufferId)));
connect(storage, SIGNAL(bufferIdUpdated(BufferId)), coreProxy, SLOT(csUpdateBufferId(BufferId)));
- connect(Global::instance(), SIGNAL(dataUpdatedRemotely(UserId, QString)), this, SLOT(globalDataUpdated(UserId, QString)));
- connect(Global::instance(), SIGNAL(dataPutLocally(UserId, QString)), this, SLOT(globalDataUpdated(UserId, QString)));
connect(this, SIGNAL(sessionDataChanged(const QString &, const QVariant &)), coreProxy, SLOT(csSessionDataChanged(const QString &, const QVariant &)));
connect(coreProxy, SIGNAL(gsSessionDataChanged(const QString &, const QVariant &)), this, SLOT(storeSessionData(const QString &, const QVariant &)));
}
coreProxy->recv(sig, arg1, arg2, arg3);
}
-void CoreSession::globalDataUpdated(UserId uid, QString key) {
- Q_ASSERT(uid == userId());
- QVariant data = Global::data(userId(), key);
- QSettings s;
- s.setValue(QString("Global/%1/").arg(userId())+key, data);
-}
-
void CoreSession::storeSessionData(const QString &key, const QVariant &data) {
QSettings s;
s.beginGroup(QString("SessionData/%1").arg(user));
void sessionDataChanged(const QString &key, const QVariant &data);
private slots:
- //void recvProxySignal(CoreSignal, QVariant arg1 = QVariant(), QVariant arg2 = QVariant(), QVariant arg3 = QVariant());
- void globalDataUpdated(UserId, QString);
void recvStatusMsgFromServer(QString msg);
void recvMessageFromServer(Message::Type, QString target, QString text, QString sender = "", quint8 flags = Message::None);
void serverConnected(QString net);
IdentitiesDlg::IdentitiesDlg(QWidget *parent, QString selected) : QDialog(parent) {
ui.setupUi(this);
- connect(Global::instance(), SIGNAL(dataUpdatedRemotely(UserId, QString)), this, SLOT(globalDataUpdated(UserId, QString)));
+ connect(Client::instance(), SIGNAL(sessionDataChanged(const QString &)), this, SLOT(globalDataUpdated(QString)));
connect(ui.enableAutoAway, SIGNAL(stateChanged(int)), this, SLOT(autoAwayChecked()));
}
/* this needs more work! mapping? */
-void IdentitiesDlg::globalDataUpdated(UserId, QString key) {
+void IdentitiesDlg::globalDataUpdated(QString key) {
if(key == "Identities") {
if(QMessageBox::warning(this, tr("Data changed remotely!"), tr("<b>Some other GUI client changed the identities data!</b><br>"
"Apply updated settings, losing all changes done locally?"),
void editIdentities();
- void globalDataUpdated(UserId, QString);
+ void globalDataUpdated(QString);
private:
Ui::IdentitiesDlg ui;
ui.actionNetworkList->setEnabled(false);
ui.bufferWidget->hide();
ui.actionConnectCore->setEnabled(false); // FIXME
- qDebug() << "mainwin disconnected";
+ //qDebug() << "mainwin disconnected";
}
AbstractUiMsg *MainWin::layoutMsg(const Message &msg) {