This mode is disabled by default. When specified, this restricts
authoratative ident responses to be the authuser account name.
This is a cut-down version of,
https://github.com/quassel/quassel/pull/164 which was originally
authored by @esainane. @AlD requested that the database schema
change be removed, but the request fell dormant and was eventually
closed. This version removes the schema change as requested,
always using the user's core username as the ident when enabled.
Co-authored-by: Sai Nane <esainane+github@gmail.com>
Co-authored-by: Michael Marley <michael@michaelmarley.com>
15 files changed:
cliParser->addOption("change-userpass", 0, "Starts an interactive session to change the password of the user identified by <username>", "username");
cliParser->addSwitch("oidentd", 0, "Enable oidentd integration");
cliParser->addOption("oidentd-conffile", 0, "Set path to oidentd configuration file", "file");
cliParser->addOption("change-userpass", 0, "Starts an interactive session to change the password of the user identified by <username>", "username");
cliParser->addSwitch("oidentd", 0, "Enable oidentd integration");
cliParser->addOption("oidentd-conffile", 0, "Set path to oidentd configuration file", "file");
+ cliParser->addSwitch("oidentd-strict", 0, "Use users' quasselcore username as ident reply. Ignores each user's configured ident setting. Only meaningful with --oidentd.");
#ifdef HAVE_SSL
cliParser->addSwitch("require-ssl", 0, "Require SSL for remote (non-loopback) client connections");
cliParser->addOption("ssl-cert", 0, "Specify the path to the SSL Certificate", "path", "configdir/quasselCert.pem");
#ifdef HAVE_SSL
cliParser->addSwitch("require-ssl", 0, "Require SSL for remote (non-loopback) client connections");
cliParser->addOption("ssl-cert", 0, "Specify the path to the SSL Certificate", "path", "configdir/quasselCert.pem");
--- /dev/null
+SELECT username
+FROM quasseluser
+WHERE userid = :userid
--- /dev/null
+SELECT username
+FROM quasseluser
+WHERE userid = :userid
if (!startListening()) exit(1); // TODO make this less brutal
if (Quassel::isOptionSet("oidentd"))
if (!startListening()) exit(1); // TODO make this less brutal
if (Quassel::isOptionSet("oidentd"))
- _oidentdConfigGenerator = new OidentdConfigGenerator(this);
+ _oidentdConfigGenerator = new OidentdConfigGenerator(Quassel::isOptionSet("oidentd-strict"), this);
return instance()->_storage->setBufferLastSeenMsg(user, bufferId, msgId);
}
return instance()->_storage->setBufferLastSeenMsg(user, bufferId, msgId);
}
+ //! Get the auth username associated with a userId
+ /** \param user The user to retrieve the username for
+ * \return The username for the user
+ */
+ static inline const QString getAuthusername(UserId user) {
+ return instance()->_storage->getAuthusername(user);
+ }
+
//! Get a Hash of all last seen message ids
/** This Method is called when the Quassel Core is started to restore the lastSeenMsgIds
//! Get a Hash of all last seen message ids
/** This Method is called when the Quassel Core is started to restore the lastSeenMsgIds
createIdentity(coreIdentity);
}
createIdentity(coreIdentity);
}
+const QString CoreSession::strictSysident() {
+ const QString authusername = Core::getAuthusername(_user);
+ return authusername;
+}
void CoreSession::createIdentity(const CoreIdentity &identity)
{
void CoreSession::createIdentity(const CoreIdentity &identity)
{
inline UserId user() const { return _user; }
CoreNetwork *network(NetworkId) const;
CoreIdentity *identity(IdentityId) const;
inline UserId user() const { return _user; }
CoreNetwork *network(NetworkId) const;
CoreIdentity *identity(IdentityId) const;
+ const QString strictSysident();
inline CoreNetworkConfig *networkConfig() const { return _networkConfig; }
NetworkConnection *networkConnection(NetworkId) const;
inline CoreNetworkConfig *networkConfig() const { return _networkConfig; }
NetworkConnection *networkConnection(NetworkId) const;
***************************************************************************/
#include "oidentdconfiggenerator.h"
***************************************************************************/
#include "oidentdconfiggenerator.h"
+#include "corenetwork.h"
-OidentdConfigGenerator::OidentdConfigGenerator(QObject *parent) :
+#include <QString>
+
+OidentdConfigGenerator::OidentdConfigGenerator(bool strict, QObject *parent) :
+ _initialized(false),
+ _strict(strict)
{
if (!_initialized)
init();
{
if (!_initialized)
init();
+const QString OidentdConfigGenerator::sysidentForIdentity(const CoreIdentity *identity) {
+ if (!_strict) {
+ return identity->ident();
+ }
+ const CoreNetwork *network = qobject_cast<CoreNetwork *>(sender());
+ return network->coreSession()->strictSysident();
+}
bool OidentdConfigGenerator::addSocket(const CoreIdentity *identity, const QHostAddress &localAddress, quint16 localPort, const QHostAddress &peerAddress, quint16 peerPort)
{
Q_UNUSED(localAddress) Q_UNUSED(peerAddress) Q_UNUSED(peerPort)
bool OidentdConfigGenerator::addSocket(const CoreIdentity *identity, const QHostAddress &localAddress, quint16 localPort, const QHostAddress &peerAddress, quint16 peerPort)
{
Q_UNUSED(localAddress) Q_UNUSED(peerAddress) Q_UNUSED(peerPort)
- QString ident = identity->ident();
+ const QString ident = sysidentForIdentity(identity);
_quasselConfig.append(_quasselStanzaTemplate.arg(localPort).arg(ident).arg(_configTag).toLatin1());
_quasselConfig.append(_quasselStanzaTemplate.arg(localPort).arg(ident).arg(_configTag).toLatin1());
#define OIDENTDCONFIGGENERATOR_H
#include <QObject>
#define OIDENTDCONFIGGENERATOR_H
#include <QObject>
#include <QDir>
#include <QFile>
#include <QDateTime>
#include <QDir>
#include <QFile>
#include <QDateTime>
- explicit OidentdConfigGenerator(QObject *parent = 0);
+ /**
+ * @param strict If false, any identity a user chooses is reported to servers as authoritative.
+ * If true, the user's quassel username is always reported.
+ */
+ explicit OidentdConfigGenerator(bool strict = false, QObject *parent = 0);
~OidentdConfigGenerator();
public slots:
~OidentdConfigGenerator();
public slots:
bool removeSocket(const CoreIdentity *identity, const QHostAddress &localAddress, quint16 localPort, const QHostAddress &peerAddress, quint16 peerPort);
private:
bool removeSocket(const CoreIdentity *identity, const QHostAddress &localAddress, quint16 localPort, const QHostAddress &peerAddress, quint16 peerPort);
private:
+ const QString sysidentForIdentity(const CoreIdentity *identity);
bool init();
bool writeConfig();
bool parseConfig(bool readQuasselStanzas = false);
bool lineByUs(const QByteArray &line);
bool _initialized;
bool init();
bool writeConfig();
bool parseConfig(bool readQuasselStanzas = false);
bool lineByUs(const QByteArray &line);
bool _initialized;
QDateTime _lastSync;
QFile *_configFile;
QByteArray _parsedConfig;
QDateTime _lastSync;
QFile *_configFile;
QByteArray _parsedConfig;
+const QString PostgreSqlStorage::getAuthusername(UserId user) {
+ QString authusername;
+ QSqlQuery query(logDb());
+ query.prepare(queryString("select_authusername"));
+ query.bindValue(":userid", user.toInt());
+ safeExec(query);
+ watchQuery(query);
+
+ if (query.first()) {
+ authusername = query.value(0).toString();
+ }
+ return authusername;
+}
// void PostgreSqlStorage::safeExec(QSqlQuery &query) {
// qDebug() << "PostgreSqlStorage::safeExec";
// void PostgreSqlStorage::safeExec(QSqlQuery &query) {
// qDebug() << "PostgreSqlStorage::safeExec";
QList<Message> requestMsgs(UserId user, BufferId bufferId, MsgId first = -1, MsgId last = -1, int limit = -1) override;
QList<Message> requestAllMsgs(UserId user, MsgId first = -1, MsgId last = -1, int limit = -1) override;
QList<Message> requestMsgs(UserId user, BufferId bufferId, MsgId first = -1, MsgId last = -1, int limit = -1) override;
QList<Message> requestAllMsgs(UserId user, MsgId first = -1, MsgId last = -1, int limit = -1) override;
+ /* Sysident handling */
+ virtual const QString getAuthusername(UserId user);
+
protected:
bool initDbSession(QSqlDatabase &db) override;
void setConnectionProperties(const QVariantMap &properties) override;
protected:
bool initDbSession(QSqlDatabase &db) override;
void setConnectionProperties(const QVariantMap &properties) override;
<file>./SQL/PostgreSQL/migrate_write_usersetting.sql</file>
<file>./SQL/PostgreSQL/select_authenticator.sql</file>
<file>./SQL/PostgreSQL/select_authuser.sql</file>
<file>./SQL/PostgreSQL/migrate_write_usersetting.sql</file>
<file>./SQL/PostgreSQL/select_authenticator.sql</file>
<file>./SQL/PostgreSQL/select_authuser.sql</file>
+ <file>./SQL/PostgreSQL/select_authusername.sql</file>
<file>./SQL/PostgreSQL/select_bufferByName.sql</file>
<file>./SQL/PostgreSQL/select_bufferExists.sql</file>
<file>./SQL/PostgreSQL/select_buffer_bufferactivities.sql</file>
<file>./SQL/PostgreSQL/select_bufferByName.sql</file>
<file>./SQL/PostgreSQL/select_bufferExists.sql</file>
<file>./SQL/PostgreSQL/select_buffer_bufferactivities.sql</file>
<file>./SQL/SQLite/migrate_read_usersetting.sql</file>
<file>./SQL/SQLite/select_authenticator.sql</file>
<file>./SQL/SQLite/select_authuser.sql</file>
<file>./SQL/SQLite/migrate_read_usersetting.sql</file>
<file>./SQL/SQLite/select_authenticator.sql</file>
<file>./SQL/SQLite/select_authuser.sql</file>
+ <file>./SQL/SQLite/select_authusername.sql</file>
<file>./SQL/SQLite/select_bufferByName.sql</file>
<file>./SQL/SQLite/select_bufferExists.sql</file>
<file>./SQL/SQLite/select_buffer_bufferactivities.sql</file>
<file>./SQL/SQLite/select_bufferByName.sql</file>
<file>./SQL/SQLite/select_bufferExists.sql</file>
<file>./SQL/SQLite/select_buffer_bufferactivities.sql</file>
+const QString SqliteStorage::getAuthusername(UserId user) {
+ QString authusername;
+ QSqlQuery query(logDb());
+ query.prepare(queryString("select_authusername"));
+ query.bindValue(":userid", user.toInt());
+
+ lockForRead();
+ safeExec(query);
+ watchQuery(query);
+ unlock();
+
+ if (query.first()) {
+ authusername = query.value(0).toString();
+ }
+
+ return authusername;
+}
QString SqliteStorage::backlogFile()
{
QString SqliteStorage::backlogFile()
{
QList<Message> requestMsgs(UserId user, BufferId bufferId, MsgId first = -1, MsgId last = -1, int limit = -1) override;
QList<Message> requestAllMsgs(UserId user, MsgId first = -1, MsgId last = -1, int limit = -1) override;
QList<Message> requestMsgs(UserId user, BufferId bufferId, MsgId first = -1, MsgId last = -1, int limit = -1) override;
QList<Message> requestAllMsgs(UserId user, MsgId first = -1, MsgId last = -1, int limit = -1) override;
+ /* Sysident handling */
+ virtual const QString getAuthusername(UserId user);
+
protected:
void setConnectionProperties(const QVariantMap & /* properties */) override {}
QString driverName() override { return "QSQLITE"; }
protected:
void setConnectionProperties(const QVariantMap & /* properties */) override {}
QString driverName() override { return "QSQLITE"; }
*/
virtual QList<Message> requestAllMsgs(UserId user, MsgId first = -1, MsgId last = -1, int limit = -1) = 0;
*/
virtual QList<Message> requestAllMsgs(UserId user, MsgId first = -1, MsgId last = -1, int limit = -1) = 0;
+ //! Get the auth username associated with a userId
+ /** \param user The user to retrieve the username for
+ * \return The username for the user
+ */
+ virtual const QString getAuthusername(UserId user) = 0;
+
signals:
//! Sent when a new BufferInfo is created, or an existing one changed somehow.
void bufferInfoUpdated(UserId user, const BufferInfo &);
signals:
//! Sent when a new BufferInfo is created, or an existing one changed somehow.
void bufferInfoUpdated(UserId user, const BufferInfo &);