From e66063e6304538d34c40460ca0aa2be5ddb6bdec Mon Sep 17 00:00:00 2001 From: Adam Date: Fri, 5 Aug 2011 05:35:31 -0400 Subject: Rewrote the example configurations and split them up into seperate files for each pseudo client. Also reorganized how the modules are stored, and made most of the old "extra" modules "core" --- modules/commands/cs_entrymsg.cpp | 224 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 224 insertions(+) create mode 100644 modules/commands/cs_entrymsg.cpp (limited to 'modules/commands/cs_entrymsg.cpp') diff --git a/modules/commands/cs_entrymsg.cpp b/modules/commands/cs_entrymsg.cpp new file mode 100644 index 000000000..3aa8ed862 --- /dev/null +++ b/modules/commands/cs_entrymsg.cpp @@ -0,0 +1,224 @@ +/* ChanServ core functions + * + * (C) 2003-2011 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +/*************************************************************************/ + +#include "module.h" + +struct EntryMsg +{ + static unsigned MaxEntries; + + EntryMsg(const Anope::string &cname, const Anope::string &cmessage, time_t ct = Anope::CurTime) + { + this->creator = cname; + this->message = cmessage; + this->when = ct; + } + + Anope::string creator; + Anope::string message; + time_t when; +}; +unsigned EntryMsg::MaxEntries = 0; + +class CommandEntryMessage : public Command +{ + private: + void DoList(CommandSource &source, ChannelInfo *ci) + { + std::vector messages; + if (ci->GetExtRegular("cs_entrymsg", messages)) + { + source.Reply(_("Entry message list for \2%s\2:"), ci->name.c_str()); + for (unsigned i = 0; i < messages.size(); ++i) + source.Reply(CHAN_LIST_ENTRY, i + 1, messages[i].message.c_str(), messages[i].creator.c_str(), do_strftime(messages[i].when).c_str()); + source.Reply(_("End of entry message list.")); + } + else + source.Reply(_("Entry message list for \2%s\2 is empty."), ci->name.c_str()); + } + + void DoAdd(CommandSource &source, ChannelInfo *ci, const Anope::string &message) + { + std::vector messages; + ci->GetExtRegular("cs_entrymsg", messages); + + if (EntryMsg::MaxEntries && messages.size() >= EntryMsg::MaxEntries) + source.Reply(_("The entry message list for \2%s\2 is full."), ci->name.c_str()); + else + { + messages.push_back(EntryMsg(source.u->nick, message)); + ci->Extend("cs_entrymsg", new ExtensibleItemRegular >(messages)); + source.Reply(_("Entry message added to \2%s\2"), ci->name.c_str()); + } + } + + void DoDel(CommandSource &source, ChannelInfo *ci, const Anope::string &message) + { + std::vector messages; + if (!message.is_pos_number_only()) + source.Reply(("Entry message \002%s\002 not found on channel \002%s\002."), message.c_str(), ci->name.c_str()); + else if (ci->GetExtRegular("cs_entrymsg", messages)) + { + try + { + unsigned i = convertTo(message); + if (i > 0 && i <= messages.size()) + { + messages.erase(messages.begin() + i - 1); + if (!messages.empty()) + ci->Extend("cs_entrymsg", new ExtensibleItemRegular >(messages)); + else + ci->Shrink("cs_entrymsg"); + source.Reply(_("Entry message \2%i\2 for \2%s\2 deleted."), i, ci->name.c_str()); + } + else + throw ConvertException(); + } + catch (const ConvertException &) + { + source.Reply(_("Entry message \2%s\2 not found on channel \2%s\2."), message.c_str(), ci->name.c_str()); + } + } + else + source.Reply(_("Entry message list for \2%s\2 is empty."), ci->name.c_str()); + } + + void DoClear(CommandSource &source, ChannelInfo *ci) + { + ci->Shrink("cs_entrymsg"); + source.Reply(_("Entry messages for \2%s\2 have been cleared."), ci->name.c_str()); + } + + public: + CommandEntryMessage(Module *creator) : Command(creator, "chanserv/entrymsg", 2, 3) + { + this->SetDesc(_("Manage the channel's entry messages")); + this->SetSyntax(_("\037channel\037 {ADD|DEL|LIST|CLEAR} [\037message\037|\037num\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) + { + User *u = source.u; + + ChannelInfo *ci = cs_findchan(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (IsFounder(u, ci) || u->HasCommand("chanserv/entrymsg")) + { + bool success = true; + if (params[1].equals_ci("LIST")) + this->DoList(source, ci); + else if (params[1].equals_ci("CLEAR")) + this->DoClear(source, ci); + else if (params.size() < 3) + { + success = false; + this->OnSyntaxError(source, ""); + } + else if (params[1].equals_ci("ADD")) + this->DoAdd(source, ci, params[2]); + else if (params[1].equals_ci("DEL")) + this->DoDel(source, ci, params[2]); + else + { + success = false; + this->OnSyntaxError(source, ""); + } + if (success) + Log(IsFounder(u, ci) ? LOG_COMMAND : LOG_OVERRIDE, u, this, ci) << params[1]; + } + else + source.Reply(ACCESS_DENIED); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Controls what messages will be sent to users when they join the channel.")); + return true; + } +}; + +class CSEntryMessage : public Module +{ + CommandEntryMessage commandentrymsg; + + public: + CSEntryMessage(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, SUPPORTED), commandentrymsg(this) + { + this->SetAuthor("Anope"); + + Implementation i[] = { I_OnJoinChannel, I_OnReload, I_OnDatabaseReadMetadata, I_OnDatabaseWriteMetadata }; + ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); + + ModuleManager::RegisterService(&commandentrymsg); + + this->OnReload(); + } + + void OnJoinChannel(User *u, Channel *c) + { + if (u && c && c->ci && u->server->IsSynced()) + { + std::vector messages; + + if (c->ci->GetExtRegular("cs_entrymsg", messages)) + for (unsigned i = 0; i < messages.size(); ++i) + u->SendMessage(c->ci->WhoSends(), "[%s] %s", c->ci->name.c_str(), messages[i].message.c_str()); + } + } + + void OnReload() + { + ConfigReader config; + EntryMsg::MaxEntries = config.ReadInteger("cs_entrymsg", "maxentries", "5", 0, true); + } + + EventReturn OnDatabaseReadMetadata(ChannelInfo *ci, const Anope::string &key, const std::vector ¶ms) + { + if (key.find("CS_ENTRYMSG_") == 0 && params.size() > 2) + { + Anope::string creator = params[0]; + time_t t = params[1].is_pos_number_only() ? convertTo(params[1]) : Anope::CurTime; + Anope::string message = params[2]; + for (unsigned j = 3; j < params.size(); ++j) + message += " " + params[j]; + + std::vector messages; + ci->GetExtRegular("cs_entrymsg", messages); + messages.push_back(EntryMsg(creator, message, t)); + ci->Extend("cs_entrymsg", new ExtensibleItemRegular >(messages)); + + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } + + void OnDatabaseWriteMetadata(void (*WriteMetadata)(const Anope::string &, const Anope::string &), ChannelInfo *ci) + { + std::vector messages; + if (ci->GetExtRegular("cs_entrymsg", messages)) + for (unsigned i = 0; i < messages.size(); ++i) + WriteMetadata("CS_ENTRYMSG_" + stringify(i), messages[i].creator + " " + stringify(messages[i].when) + " " + messages[i].message); + } +}; + +MODULE_INIT(CSEntryMessage) -- cgit