diff options
| author | Adam <Adam@anope.org> | 2016-10-15 16:25:57 -0400 |
|---|---|---|
| committer | Adam <Adam@anope.org> | 2016-10-15 16:25:57 -0400 |
| commit | 1ba242179fee46583098f48421af39ce9a8985a1 (patch) | |
| tree | a276cd7bd53e7270c86ab3744bd6a568a016501b | |
| parent | 696239e93391f3dfd6459857fb02a6006048093a (diff) | |
Various improvements/bugfixes to extdb stuff
| -rw-r--r-- | include/config.h | 8 | ||||
| -rw-r--r-- | include/modules/sql.h | 4 | ||||
| -rw-r--r-- | include/serialize.h | 76 | ||||
| -rw-r--r-- | include/users.h | 1 | ||||
| -rw-r--r-- | include/xline.h | 2 | ||||
| -rw-r--r-- | modules/botserv/assign.cpp | 4 | ||||
| -rw-r--r-- | modules/botserv/bot.cpp | 26 | ||||
| -rw-r--r-- | modules/botserv/info.cpp | 7 | ||||
| -rw-r--r-- | modules/botserv/set.cpp | 2 | ||||
| -rw-r--r-- | modules/chanserv/main/channeltype.cpp | 8 | ||||
| -rw-r--r-- | modules/chanserv/main/channeltype.h | 2 | ||||
| -rw-r--r-- | modules/chanserv/main/chanserv.cpp | 16 | ||||
| -rw-r--r-- | modules/database/old.cpp | 4 | ||||
| -rw-r--r-- | modules/database/sql.cpp | 184 | ||||
| -rw-r--r-- | modules/extra/mysql.cpp | 82 | ||||
| -rw-r--r-- | modules/extra/sqlite.cpp | 124 | ||||
| -rw-r--r-- | modules/nickserv/cert.cpp | 19 | ||||
| -rw-r--r-- | modules/nickserv/main/accounttype.cpp | 13 | ||||
| -rw-r--r-- | modules/nickserv/main/accounttype.h | 2 | ||||
| -rw-r--r-- | modules/nickserv/main/nickserv.cpp | 9 | ||||
| -rw-r--r-- | modules/nickserv/main/nicktype.cpp | 9 | ||||
| -rw-r--r-- | modules/nickserv/main/nicktype.h | 2 | ||||
| -rw-r--r-- | src/bots.cpp | 21 | ||||
| -rw-r--r-- | src/config.cpp | 169 | ||||
| -rw-r--r-- | src/init.cpp | 3 | ||||
| -rw-r--r-- | src/service_manager.cpp | 8 | ||||
| -rw-r--r-- | src/xline.cpp | 3 |
27 files changed, 426 insertions, 382 deletions
diff --git a/include/config.h b/include/config.h index dccadbe79..b6b36b726 100644 --- a/include/config.h +++ b/include/config.h @@ -102,8 +102,9 @@ namespace Configuration struct Usermode; struct Channelmode; - struct CoreExport Conf : Block + class CoreExport Conf : public Block { + public: /* options:readtimeout */ time_t ReadTimeout; /* options:useprivmsg */ @@ -162,6 +163,11 @@ namespace Configuration ServiceBot *GetClient(const Anope::string &name); Block *GetCommand(CommandSource &); + + void LoadBots(); + void ApplyBots(); + + void LoadOpers(); }; struct Uplink diff --git a/include/modules/sql.h b/include/modules/sql.h index 2e84db152..6770f407e 100644 --- a/include/modules/sql.h +++ b/include/modules/sql.h @@ -202,8 +202,8 @@ namespace SQL virtual std::vector<Query> InitSchema(const Anope::string &prefix) anope_abstract; virtual std::vector<Query> Replace(const Anope::string &table, const Query &, const std::set<Anope::string> &) anope_abstract; - virtual std::vector<Query> CreateTable(const Anope::string &prefix, const Anope::string &table) anope_abstract; - virtual std::vector<Query> AlterTable(const Anope::string &, const Anope::string &table, const Anope::string &field, bool object) anope_abstract; + virtual std::vector<Query> CreateTable(const Anope::string &prefix, Serialize::TypeBase *) anope_abstract; + virtual std::vector<Query> AlterTable(const Anope::string &, Serialize::TypeBase *, Serialize::FieldBase *) anope_abstract; virtual std::vector<Query> CreateIndex(const Anope::string &table, const Anope::string &field) anope_abstract; virtual Query BeginTransaction() anope_abstract; diff --git a/include/serialize.h b/include/serialize.h index 1d0fb9400..8f35e61c6 100644 --- a/include/serialize.h +++ b/include/serialize.h @@ -49,6 +49,9 @@ namespace Serialize inline T GetObject(); template<typename T> + inline std::vector<T> GetObjects_(TypeBase *); + + template<typename T> inline std::vector<T> GetObjects(const Anope::string &name); template<typename T> @@ -235,29 +238,6 @@ class CoreExport Serialize::TypeBase : public Service */ const Anope::string &GetName() { return this->name; } - /** - * Get all objects of the given type - */ - template<typename T> - std::vector<T> List() - { - std::vector<ID> ids; - EventReturn result = EventManager::Get()->Dispatch(&Event::SerializeEvents::OnSerializeList, this, ids); - if (result == EVENT_ALLOW) - { - std::vector<T> o; - for (ID id : ids) - { - Object *s = Require(id); - if (s) - o.push_back(anope_dynamic_static_cast<T>(s)); - } - return o; - } - - return GetObjects<T>(); - } - /** Create a new object of this type. */ virtual Object *Create() anope_abstract; @@ -306,7 +286,10 @@ class Serialize::Type : public Base return new T(this, id); if (s->GetSerializableType() != this) + { + Log(LOG_DEBUG) << "Mismatch for required id " << id << ", is of type " << s->GetSerializableType()->GetName() << " but wants " << this->GetName(); return nullptr; + } return static_cast<T *>(s); } @@ -387,6 +370,8 @@ class Serialize::FieldBase : public Service */ bool depends; + bool object = false; + FieldBase(Module *, const Anope::string &, const Anope::string &, bool); virtual ~FieldBase(); void Unregister(); @@ -592,7 +577,10 @@ class Serialize::Field : public CommonFieldBase<TypeImpl, T> // module returned us data, so we unserialize it T t2 = this->Unserialize(value); + // should cache the default value somehow, but can't differentiate not cached from cached and default + // Cache + OnSet(s, t2); this->Set_(s, t2); return t2; @@ -609,11 +597,18 @@ class Serialize::Field : public CommonFieldBase<TypeImpl, T> SetField(this->Upcast(s), value); } - virtual void SetField(TypeImpl *s, const T &value) + /** + * Override to hook to changes in the internally + * cached value + */ + virtual void OnSet(TypeImpl *s, const T &value) { } + + void SetField(TypeImpl *s, const T &value) { Anope::string strvalue = this->Serialize(value); EventManager::Get()->Dispatch(&Event::SerializeEvents::OnSerializeSet, s, this, strvalue); + OnSet(s, value); this->Set_(s, value); } @@ -697,10 +692,12 @@ class Serialize::ObjectField : public CommonFieldBase<TypeImpl, T> public: ObjectField(TypeBase *t, const Anope::string &n, bool d = false) : CommonFieldBase<TypeImpl, T>(t, n, d) { + this->object = true; } ObjectField(TypeBase *t, const Anope::string &n, T TypeImpl::*field, bool d = false) : CommonFieldBase<TypeImpl, T>(t, n, field, d) { + this->object = true; } T GetField(TypeImpl *s) @@ -723,6 +720,7 @@ class Serialize::ObjectField : public CommonFieldBase<TypeImpl, T> T t2 = result == EVENT_ALLOW ? static_cast<T>(base->Require(sid)) : nullptr; + OnSet(s, t2); this->Set_(s, t2); return t2; @@ -739,7 +737,9 @@ class Serialize::ObjectField : public CommonFieldBase<TypeImpl, T> SetField(this->Upcast(s), value); } - virtual void SetField(TypeImpl *s, T value) + virtual void OnSet(TypeImpl *s, T value) { } + + void SetField(TypeImpl *s, T value) { EventManager::Get()->Dispatch(&Event::SerializeEvents::OnSerializeSetSerializable, s, this, value); @@ -747,6 +747,7 @@ class Serialize::ObjectField : public CommonFieldBase<TypeImpl, T> if (old != nullptr && *old != nullptr) s->RemoveEdge(*old, this); + OnSet(s, value); this->Set_(s, value); if (value != nullptr) @@ -812,13 +813,34 @@ T Serialize::GetObject() } template<typename T> +std::vector<T> Serialize::GetObjects_(TypeBase *type) +{ + std::vector<T> o; + std::vector<ID> ids; + EventReturn result = EventManager::Get()->Dispatch(&Event::SerializeEvents::OnSerializeList, type, ids); + if (result == EVENT_ALLOW) + { + for (ID id : ids) + { + Object *s = type->Require(id); + if (s) + o.push_back(anope_dynamic_static_cast<T>(s)); + } + return o; + } + + std::transform(type->objects.begin(), type->objects.end(), std::back_inserter(o), [](Object *e) { return anope_dynamic_static_cast<T>(e); }); + return o; +} + +template<typename T> std::vector<T> Serialize::GetObjects(const Anope::string &name) { std::vector<T> objs; for (TypeBase *t : GetTypes(name)) - for (Object *s : t->objects) - objs.push_back(anope_dynamic_static_cast<T>(s)); + for (T obj : GetObjects_<T>(t)) + objs.push_back(obj); return objs; } diff --git a/include/users.h b/include/users.h index dacb7045e..be4ee2a39 100644 --- a/include/users.h +++ b/include/users.h @@ -38,7 +38,6 @@ extern CoreExport int OperCount; enum class UserType { USER, - //LOCAL_USER, BOT }; diff --git a/include/xline.h b/include/xline.h index 87b64d1da..05ddbe2d3 100644 --- a/include/xline.h +++ b/include/xline.h @@ -87,7 +87,7 @@ class XLineType : public Serialize::Type<XLine> { using Serialize::Field<XLine, Anope::string>::Field; - void SetField(XLine *s, const Anope::string &value) override; + void OnSet(XLine *s, const Anope::string &value) override; } mask; Serialize::Field<XLine, Anope::string> by, reason, id; Serialize::Field<XLine, time_t> created, expires; diff --git a/modules/botserv/assign.cpp b/modules/botserv/assign.cpp index eb6b8da10..a26b869fe 100644 --- a/modules/botserv/assign.cpp +++ b/modules/botserv/assign.cpp @@ -67,7 +67,7 @@ class CommandBSAssign : public Command return; } - if (bi->bi->GetOperOnly() && !source.HasPriv("botserv/administration")) + if (bi->bi && bi->bi->GetOperOnly() && !source.HasPriv("botserv/administration")) { source.Reply(_("Access denied. Bot \002{0}\002 is for operators only."), bi->nick); return; @@ -265,7 +265,7 @@ class BSAssign : public Module return; } - if (bi->bi->GetOperOnly() && !source->HasPriv("botserv/administration")) + if (bi->bi && bi->bi->GetOperOnly() && !source->HasPriv("botserv/administration")) { targ->SendMessage(bi, _("Access denied. Bot \002{0}\002 is for operators only."), bi->nick); return; diff --git a/modules/botserv/bot.cpp b/modules/botserv/bot.cpp index c93c4cf50..2e33b7ccb 100644 --- a/modules/botserv/bot.cpp +++ b/modules/botserv/bot.cpp @@ -93,6 +93,16 @@ class CommandBSBot : public Command ServiceBot *bi = new ServiceBot(nick, user, host, real); + BotInfo *botinfo = Serialize::New<BotInfo *>(); + botinfo->SetNick(nick); + botinfo->SetUser(user); + botinfo->SetHost(host); + botinfo->SetRealName(real); + botinfo->SetCreated(Anope::CurTime); + + bi->bi = botinfo; + botinfo->bot = bi; + Log(LOG_ADMIN, source, this) << "ADD " << bi->GetMask() << " " << bi->realname; source.Reply(_("\002{0}!{1}@{2}\002 (\002{3}\002) added to the bot list."), bi->nick, bi->GetIdent(), bi->host, bi->realname); @@ -121,7 +131,7 @@ class CommandBSBot : public Command return; } - if (bi->bi->conf) + if (bi->bi && bi->bi->conf) { source.Reply(_("Bot \002{0}\002 is not changeable because it is configured in services configuration."), bi->nick.c_str()); return; @@ -226,23 +236,27 @@ class CommandBSBot : public Command if (!nick.equals_cs(bi->nick)) { bi->SetNewNick(nick); - bi->bi->SetNick(nick); + if (bi->bi != nullptr) + bi->bi->SetNick(nick); } if (!user.equals_cs(bi->GetIdent())) { bi->SetIdent(user); - bi->bi->SetUser(user); + if (bi->bi != nullptr) + bi->bi->SetUser(user); } if (!host.equals_cs(bi->host)) { bi->host = host; - bi->bi->SetHost(host); + if (bi->bi != nullptr) + bi->bi->SetHost(host); } if (real.equals_cs(bi->realname)) { bi->realname = real; - bi->bi->SetRealName(real); + if (bi->bi != nullptr) + bi->bi->SetRealName(real); } if (!user.empty()) @@ -271,7 +285,7 @@ class CommandBSBot : public Command return; } - if (bi->bi->conf) + if (bi->bi && bi->bi->conf) { source.Reply(_("Bot \002{0}\002 is can not be deleted because it is configured in services configuration."), bi->nick); return; diff --git a/modules/botserv/info.cpp b/modules/botserv/info.cpp index 94b1bbbd7..4de86643f 100644 --- a/modules/botserv/info.cpp +++ b/modules/botserv/info.cpp @@ -41,8 +41,11 @@ class CommandBSInfo : public Command source.Reply(_("Information for bot \002%s\002:"), bi->nick.c_str()); info[_("Mask")] = bi->GetIdent() + "@" + bi->host; info[_("Real name")] = bi->realname; - info[_("Created")] = Anope::strftime(bi->bi->GetCreated(), source.GetAccount()); - info[_("Options")] = bi->bi->GetOperOnly() ? _("Private") : _("None"); + if (bi->bi) + { + info[_("Created")] = Anope::strftime(bi->bi->GetCreated(), source.GetAccount()); + info[_("Options")] = bi->bi->GetOperOnly() ? _("Private") : _("None"); + } info[_("Used on")] = stringify(bi->GetChannelCount()) + " channel(s)"; EventManager::Get()->Dispatch(&Event::ServiceBotEvent::OnServiceBot, source, bi, ci, info); diff --git a/modules/botserv/set.cpp b/modules/botserv/set.cpp index 47c5337d2..bb432e3f0 100644 --- a/modules/botserv/set.cpp +++ b/modules/botserv/set.cpp @@ -174,7 +174,7 @@ class CommandBSSetPrivate : public Command source.Reply(_("Services are in read-only mode. Any changes made may not persist.")); ServiceBot *bi = ServiceBot::Find(nick, true); - if (bi == NULL) + if (bi == NULL || !bi->bi) { source.Reply(_("Bot \002{0}\002 does not exist."), nick); return; diff --git a/modules/chanserv/main/channeltype.cpp b/modules/chanserv/main/channeltype.cpp index fa5e03e4c..37c290ef1 100644 --- a/modules/chanserv/main/channeltype.cpp +++ b/modules/chanserv/main/channeltype.cpp @@ -37,12 +37,12 @@ ChannelType::ChannelType(Module *me) : Serialize::Type<ChannelImpl>(me) } -void ChannelType::Name::SetField(ChannelImpl *c, const Anope::string &value) +void ChannelType::Name::OnSet(ChannelImpl *c, const Anope::string &value) { ChanServ::registered_channel_map& map = ChanServ::service->GetChannels(); - map.erase(GetField(c)); - - Serialize::Field<ChannelImpl, Anope::string>::SetField(c, value); + Anope::string *old = this->Get_(c); + if (old != nullptr) + map.erase(*old); map[value] = c; } diff --git a/modules/chanserv/main/channeltype.h b/modules/chanserv/main/channeltype.h index 95158427a..1f1c92201 100644 --- a/modules/chanserv/main/channeltype.h +++ b/modules/chanserv/main/channeltype.h @@ -27,7 +27,7 @@ class ChannelType : public Serialize::Type<ChannelImpl> { using Serialize::Field<ChannelImpl, Anope::string>::Field; - void SetField(ChannelImpl *c, const Anope::string &value) override; + void OnSet(ChannelImpl *c, const Anope::string &value) override; } name; Serialize::Field<ChannelImpl, Anope::string> desc; Serialize::Field<ChannelImpl, time_t> time_registered; diff --git a/modules/chanserv/main/chanserv.cpp b/modules/chanserv/main/chanserv.cpp index ec2e8a623..dc44173a0 100644 --- a/modules/chanserv/main/chanserv.cpp +++ b/modules/chanserv/main/chanserv.cpp @@ -322,7 +322,7 @@ class ChanServCore : public Module { ::Log(LOG_NORMAL, "chanserv/drop", ChanServ) << "Deleting channel " << ci->GetName() << " owned by deleted nick " << nc->GetDisplay(); - delete ci; + ci->Delete(); continue; } } @@ -330,6 +330,7 @@ class ChanServCore : public Module if (ci->GetSuccessor() == nc) ci->SetSuccessor(NULL); +#warning "these arent necessary?" /* are these necessary? */ for (unsigned j = 0; j < ci->GetAccessCount(); ++j) { @@ -338,7 +339,7 @@ class ChanServCore : public Module if (anc && anc == nc) { - delete ca; + ca->Delete(); break; } } @@ -348,7 +349,7 @@ class ChanServCore : public Module AutoKick *ak = ci->GetAkick(j); if (ak->GetAccount() == nc) { - delete ak; + ak->Delete(); break; } } @@ -359,6 +360,7 @@ class ChanServCore : public Module { /* remove access entries that are this channel */ +#warning "also not necessary?" for (ChanServ::Channel *c : ci->GetRefs<ChanServ::Channel *>()) { for (unsigned j = 0; j < c->GetAccessCount(); ++j) @@ -367,7 +369,7 @@ class ChanServCore : public Module if (a->Mask().equals_ci(ci->GetName())) { - delete a; + a->Delete(); break; } } @@ -465,7 +467,7 @@ class ChanServCore : public Module if (!chanserv_expire || Anope::NoExpire || Anope::ReadOnly) return; - for (ChanServ::Channel *ci : channel_type.List<ChanServ::Channel *>()) + for (ChanServ::Channel *ci : Serialize::GetObjects<ChanServ::Channel *>()) { bool expire = false; @@ -488,7 +490,7 @@ class ChanServCore : public Module { ::Log(LOG_NORMAL, "chanserv/expire", ChanServ) << "Expiring channel " << ci->GetName() << " (founder: " << (ci->GetFounder() ? ci->GetFounder()->GetDisplay() : "(none)") << ")"; EventManager::Get()->Dispatch(&ChanServ::Event::ChanExpire::OnChanExpire, ci); - delete ci; + ci->Delete(); } } } @@ -505,7 +507,7 @@ class ChanServCore : public Module void OnPreUplinkSync(Server *serv) override { /* Find all persistent channels and create them, as we are about to finish burst to our uplink */ - for (ChanServ::Channel *ci : channel_type.List<ChanServ::Channel *>()) + for (ChanServ::Channel *ci : Serialize::GetObjects<ChanServ::Channel *>()) { if (ci->HasFieldS("PERSIST")) { diff --git a/modules/database/old.cpp b/modules/database/old.cpp index d63b2c4d8..61be22e9d 100644 --- a/modules/database/old.cpp +++ b/modules/database/old.cpp @@ -777,6 +777,10 @@ static void LoadBots() ServiceBot *bi = ServiceBot::Find(nick, true); if (!bi) bi = new ServiceBot(nick, user, host, real); + + if (bi->bi == nullptr) + bi->bi = Serialize::New<BotInfo *>(); + bi->bi->SetCreated(created); if (flags & OLD_BI_PRIVATE) diff --git a/modules/database/sql.cpp b/modules/database/sql.cpp index d7ed1963a..aa1c94bc0 100644 --- a/modules/database/sql.cpp +++ b/modules/database/sql.cpp @@ -22,7 +22,7 @@ using namespace SQL; -class DBMySQL : public Module, public Pipe +class DBSQL : public Module, public Pipe , public EventHook<Event::SerializeEvents> { private: @@ -58,8 +58,6 @@ class DBMySQL : public Module, public Pipe SQL->RunQuery(q); } - Log(LOG_DEBUG_2) << query.Unsafe(); - return SQL->RunQuery(query); } @@ -85,7 +83,7 @@ class DBMySQL : public Module, public Pipe } public: - DBMySQL(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE | VENDOR) + DBSQL(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE | VENDOR) , EventHook<Event::SerializeEvents>(this) { } @@ -129,10 +127,10 @@ class DBMySQL : public Module, public Pipe StartTransaction(); - for (Query &q : SQL->CreateTable(prefix, type->GetName())) + for (Query &q : SQL->CreateTable(prefix, type)) Run(q); - for (Query &q : SQL->AlterTable(prefix, type->GetName(), field->serialize_name, false)) + for (Query &q : SQL->AlterTable(prefix, type, field)) Run(q); for (const Query &q : SQL->CreateIndex(prefix + type->GetName(), field->serialize_name)) @@ -150,6 +148,7 @@ class DBMySQL : public Module, public Pipe catch (const ConvertException &) { } + return EVENT_CONTINUE; } @@ -159,7 +158,7 @@ class DBMySQL : public Module, public Pipe StartTransaction(); Query query = "SELECT `" + field->serialize_name + "` FROM `" + prefix + object->GetSerializableType()->GetName() + "` WHERE `id` = @id@"; - query.SetValue("id", object->id); + query.SetValue("id", object->id, false); Result res = Run(query); if (res.Rows() == 0) @@ -169,6 +168,40 @@ class DBMySQL : public Module, public Pipe return true; } + void GetRefs(Serialize::Object *object, Serialize::TypeBase *type, std::vector<Serialize::Edge> &edges) + { + for (Serialize::FieldBase *field : type->GetFields()) + { + if (field->object) + { + Anope::string table = prefix + type->GetName(); + + Query query = "SELECT " + table + ".id FROM " + table + + " INNER JOIN " + prefix + "objects AS o ON " + + table + "." + field->serialize_name + " = o.id " + "WHERE o.id = @id@"; + + query.SetValue("id", object->id, false); + + Result res = Run(query); + for (int i = 0; i < res.Rows(); ++i) + { + Serialize::ID id = convertTo<Serialize::ID>(res.Get(i, "id")); + + Serialize::Object *other = type->Require(id); + if (other == nullptr) + { + Log(LOG_DEBUG) << "Unable to require id " << id << " type " << type->GetName(); + continue; + } + + // other type, other field, direction + edges.emplace_back(other, field, false); + } + } + } + } + public: EventReturn OnSerializeGet(Serialize::Object *object, Serialize::FieldBase *field, Anope::string &value) override { @@ -193,93 +226,16 @@ class DBMySQL : public Module, public Pipe edges.clear(); - Query query; - if (type) - query = "SELECT field," + prefix + "edges.id,other_id,j1.type,j2.type AS other_type FROM `" + prefix + "edges` " - "JOIN `" + prefix + "objects` AS j1 ON " + prefix + "edges.id = j1.id " - "JOIN `" + prefix + "objects` AS j2 ON " + prefix + "edges.other_id = j2.id " - "WHERE " - " (" + prefix + "edges.id = @id@ AND j2.type = @other_type@) " - "OR" - " (other_id = @id@ AND j1.type = @other_type@)"; + if (type == nullptr) + { + for (Serialize::TypeBase *type : Serialize::TypeBase::GetTypes()) + GetRefs(object, type, edges); + } else - query = "SELECT field," + prefix + "edges.id,other_id,j1.type,j2.type AS other_type FROM `" + prefix + "edges` " - "JOIN `" + prefix + "objects` AS j1 ON " + prefix + "edges.id = j1.id " - "JOIN `" + prefix + "objects` AS j2 ON " + prefix + "edges.other_id = j2.id " - "WHERE " + prefix + "edges.id = @id@ OR other_id = @id@"; - - query.SetValue("type", object->GetSerializableType()->GetName()); - query.SetValue("id", object->id); - if (type) - query.SetValue("other_type", type->GetName()); - - Result res = Run(query); - for (int i = 0; i < res.Rows(); ++i) { - Serialize::ID id = convertTo<Serialize::ID>(res.Get(i, "id")); // object edge is on - - if (id == object->id) - { - // we want other type, this is my edge - Anope::string t = res.Get(i, "other_type"); - Anope::string f = res.Get(i, "field"); - id = convertTo<Serialize::ID>(res.Get(i, "other_id")); - - Serialize::FieldBase *obj_field = object->GetSerializableType()->GetField(f); - if (obj_field == nullptr) - { - Log(LOG_DEBUG) << "Unable to find field " << f << " on " << object->GetSerializableType()->GetName(); - continue; - } - - Serialize::TypeBase *obj_type = Serialize::TypeBase::Find(t); - if (obj_type == nullptr) - { - Log(LOG_DEBUG) << "Unable to find type " << t; - continue; - } - - Serialize::Object *other = obj_type->Require(id); - if (other == nullptr) - { - Log(LOG_DEBUG) << "Unable to require id " << id << " type " << obj_type->GetName(); - continue; - } - - edges.emplace_back(other, obj_field, true); - } - else - { - // edge to me - Anope::string t = res.Get(i, "type"); - Anope::string f = res.Get(i, "field"); - - Serialize::TypeBase *obj_type = Serialize::TypeBase::Find(t); - if (obj_type == nullptr) - { - Log(LOG_DEBUG) << "Unable to find type " << t; - continue; - } - - Serialize::FieldBase *obj_field = obj_type->GetField(f); - if (obj_field == nullptr) - { - Log(LOG_DEBUG) << "Unable to find field " << f << " on " << obj_type->GetName(); - continue; - } - - Serialize::Object *other = obj_type->Require(id); - if (other == nullptr) - { - Log(LOG_DEBUG) << "Unable to require id " << id << " type " << obj_type->GetName(); - continue; - } - - // other type, other field, - edges.emplace_back(other, obj_field, false); - } + GetRefs(object, type, edges); } - + return EVENT_ALLOW; } @@ -288,7 +244,7 @@ class DBMySQL : public Module, public Pipe StartTransaction(); Query query = "SELECT `id` FROM `" + prefix + type->GetName() + "` WHERE `id` = @id@"; - query.SetValue("id", id); + query.SetValue("id", id, false); Result res = Run(query); if (res.Rows() == 0) return EVENT_CONTINUE; @@ -302,7 +258,7 @@ class DBMySQL : public Module, public Pipe Query query = "SELECT `" + field->serialize_name + "`,j1.type AS " + field->serialize_name + "_type FROM `" + prefix + object->GetSerializableType()->GetName() + "` " "JOIN `" + prefix + "objects` AS j1 ON " + prefix + object->GetSerializableType()->GetName() + "." + field->serialize_name + " = j1.id " "WHERE " + prefix + object->GetSerializableType()->GetName() + ".id = @id@"; - query.SetValue("id", object->id); + query.SetValue("id", object->id, false); Result res = Run(query); if (res.Rows() == 0) @@ -329,16 +285,16 @@ class DBMySQL : public Module, public Pipe StartTransaction(); - for (Query &q : SQL->CreateTable(prefix, object->GetSerializableType()->GetName())) + for (Query &q : SQL->CreateTable(prefix, object->GetSerializableType())) Run(q); - for (Query &q : SQL->AlterTable(prefix, object->GetSerializableType()->GetName(), field->serialize_name, is_object)) + for (Query &q : SQL->AlterTable(prefix, object->GetSerializableType(), field)) Run(q); Query q; - q.SetValue("id", object->id); + q.SetValue("id", object->id, false); if (value) - q.SetValue(field->serialize_name, *value); + q.SetValue(field->serialize_name, *value, !is_object); else q.SetNull(field->serialize_name); @@ -364,23 +320,10 @@ class DBMySQL : public Module, public Pipe { Anope::string v = stringify(value->id); DoSet(object, field, true, &v); - - Query query; - query.SetValue("field", field->serialize_name); - query.SetValue("id", object->id); - query.SetValue("other_id", value->id); - - for (Query &q : SQL->Replace(prefix + "edges", query, { "id", "field" })) - Run(q); } else { DoSet(object, field, true, nullptr); - - Query query("DELETE FROM `" + prefix + "edges` WHERE `id` = @id@ AND `field` = @field@"); - query.SetValue("id", object->id); - query.SetValue("field", field->serialize_name); - Run(query); } return EVENT_STOP; @@ -395,12 +338,6 @@ class DBMySQL : public Module, public Pipe EventReturn OnSerializeUnsetSerializable(Serialize::Object *object, Serialize::FieldBase *field) override { DoSet(object, field, true, nullptr); - - Query query("DELETE FROM `" + prefix + "edges` WHERE `id` = @id@ AND `field` = @field@"); - query.SetValue("id", object->id); - query.SetValue("field", field->serialize_name); - Run(query); - return EVENT_STOP; } @@ -408,7 +345,14 @@ class DBMySQL : public Module, public Pipe { SQL::Result::Value v; - return GetValue(object, field, v) && !v.null ? EVENT_STOP : EVENT_CONTINUE; + if (!GetValue(object, field, v)) + return EVENT_CONTINUE; + + if (v.null) + return EVENT_CONTINUE; + + field->UnserializeFromString(object, v.value); + return EVENT_STOP; } EventReturn OnSerializableGetId(Serialize::ID &id) override @@ -427,7 +371,7 @@ class DBMySQL : public Module, public Pipe StartTransaction(); Query q = Query("INSERT INTO `" + prefix + "objects` (`id`,`type`) VALUES (@id@, @type@)"); - q.SetValue("id", object->id); + q.SetValue("id", object->id, false); q.SetValue("type", object->GetSerializableType()->GetName()); Run(q); } @@ -436,10 +380,10 @@ class DBMySQL : public Module, public Pipe { StartTransaction(); - Query query("DELETE FROM `" + prefix + object->GetSerializableType()->GetName() + "` WHERE `id` = " + stringify(object->id)); + Query query("DELETE FROM `" + prefix + "objects` WHERE `id` = " + stringify(object->id)); Run(query); } }; -MODULE_INIT(DBMySQL) +MODULE_INIT(DBSQL) diff --git a/modules/extra/mysql.cpp b/modules/extra/mysql.cpp index b0aec1f6d..b5ff0c3d9 100644 --- a/modules/extra/mysql.cpp +++ b/modules/extra/mysql.cpp @@ -156,8 +156,8 @@ class MySQLService : public Provider std::vector<Query> InitSchema(const Anope::string &prefix) override; std::vector<Query> Replace(const Anope::string &table, const Query &, const std::set<Anope::string> &) override; - std::ve |
