inspircd / inspircd-contrib

Third-party InspIRCd module repository.
https://www.inspircd.org
66 stars 72 forks source link

Module request: /nick that preserves prefix #258

Open Kagee opened 3 years ago

Kagee commented 3 years ago

I asked this on #inspircd and it was suggested that i post a request here:

We limit users to a specific nick prefix (Foo-Nick) by using the sqlauth module and then by disabling the /NICK command so users can't change nicks (and thus prefix) after join. Is it possible to write a module that would allow nick change via /NICK if the nick retains the same prefix, either wrapping or overriding the /NICK command.

SadieCat commented 3 years ago

How are you requiring the prefix? with <sqlauth:allowpattern>?

Kagee commented 3 years ago

Sorry for the late reply, no, we do not use allowpattern. <sqlauth dbid="userdb" query="SELECT nickmask FROM users WHERE '$nick' LIKE nickmask ESCAPE '\\' AND password='$sha256pass' LIMIT 1">

Where the table is as follows

CREATE TABLE users (id integer PRIMARY KEY, nickmask varchar(60), password varchar(256), last_updated datetime DEFAULT CURRENT_TIMESTAMP);
INSERT INTO "users" VALUES(1,'SomeTeam-_%','<some hash>','2017-10-30 10:17:46');

Thus users that has a nick prefix of "SomeTeam-" can login with the password for that prefix.

We are currently on Inspircd 2, but moving to 3 these days.

Kagee commented 2 years ago

I wrote this as a solution to my own problem, i would love any feedback on my module- or C++-skills 😄

/*
 * InspIRCd -- Internet Relay Chat Daemon
 *
 *   Copyright (C) 2021 Anders Einar Hilden <hildenae@gmail.com>
 *
 * This file is part of InspIRCd.  InspIRCd is free software: you can
 * redistribute it and/or modify it under the terms of the GNU General Public
 * License as published by the Free Software Foundation, version 2.
 *
 * This program is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
 * FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
 * details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

/// $ModAuthor: Anders Einar Hilden
/// $ModAuthorMail: hildenae@gmail.com
/// $ModConfig: <nicklockprefix separator="-">
/// $ModDepends: core 3
/// $ModDesc: Block nick changes that would change a users nick prefix.
//      Prefix is defined as everything before the first separator.

#include "inspircd.h"

class ModuleNickLockPrefix : public Module {
  std::string separator;

public:
  ModResult OnUserPreNick(LocalUser *user,
                          const std::string &newnick) CXX11_OVERRIDE {

    if ((IS_LOCAL(user)) && (user->nick != user->uuid)) {
      std::size_t sepold = user->nick.find(separator);
      std::size_t sepnew = newnick.find(separator);
      std::string prefix = user->nick.substr(0, sepold + 1);

      // changing nick to Prefix- or shorter
      if (newnick.length() <= sepold + 1 ||
          // changing to another prefix
          newnick.compare(0, sepnew, user->nick, 0, sepold) != 0) {

        ServerInstance->Logs->Log(
            MODNAME, LOG_DEFAULT,
            InspIRCd::Format("User %s was prevented from changing nick to %s",
                             user->nick.c_str(), newnick.c_str()));

        user->WriteNotice(InspIRCd::Format(
            "*** You are not allowed to change your nick to %s, your new nick "
            "must start with %s",
            newnick.c_str(), prefix.c_str()));
        return MOD_RES_DENY;
      }
    }
    return MOD_RES_PASSTHRU;
  }

  void ReadConfig(ConfigStatus &) CXX11_OVERRIDE {
    ConfigTag *tag = ServerInstance->Config->ConfValue("nicklockprefix");
    separator = tag->getString("separator", "-");
  }

  Version GetVersion() CXX11_OVERRIDE {
    return Version("Block nick changes that would change a users nick prefix");
  }
};

MODULE_INIT(ModuleNickLockPrefix)