mirror of
https://github.com/matrix-construct/construct
synced 2024-11-15 22:41:12 +01:00
ircd:Ⓜ️ Reorg filter interface and linkage related.
This commit is contained in:
parent
3ec5df018a
commit
1d7fce8368
7 changed files with 279 additions and 210 deletions
|
@ -91,15 +91,8 @@ struct ircd::m::filter
|
||||||
>
|
>
|
||||||
{
|
{
|
||||||
using super_type::tuple;
|
using super_type::tuple;
|
||||||
using super_type::operator=;
|
|
||||||
|
|
||||||
using closure = std::function<void (const json::object &)>;
|
|
||||||
|
|
||||||
static bool get(std::nothrow_t, const user &, const string_view &filter_id, const closure &);
|
|
||||||
static void get(const user &, const string_view &filter_id, const closure &);
|
|
||||||
static string_view set(const mutable_buffer &id, const user &, const json::object &filter);
|
|
||||||
|
|
||||||
filter(const user &, const string_view &filter_id, const mutable_buffer &);
|
filter(const user &, const string_view &filter_id, const mutable_buffer &);
|
||||||
|
using super_type::operator=;
|
||||||
};
|
};
|
||||||
|
|
||||||
#pragma GCC diagnostic pop
|
#pragma GCC diagnostic pop
|
||||||
|
|
|
@ -57,6 +57,13 @@ struct ircd::m::user
|
||||||
json::object account_data(const mutable_buffer &out, const string_view &type) const; //nothrow
|
json::object account_data(const mutable_buffer &out, const string_view &type) const; //nothrow
|
||||||
event::id::buf account_data(const m::user &sender, const string_view &type, const json::object &value);
|
event::id::buf account_data(const m::user &sender, const string_view &type, const json::object &value);
|
||||||
|
|
||||||
|
using filter_closure = std::function<void (const json::object &)>;
|
||||||
|
bool filter(std::nothrow_t, const string_view &filter_id, const filter_closure &) const;
|
||||||
|
void filter(const string_view &filter_id, const filter_closure &) const;
|
||||||
|
std::string filter(std::nothrow_t, const string_view &filter_id) const;
|
||||||
|
std::string filter(const string_view &filter_id) const;
|
||||||
|
event::id::buf filter(const json::object &filter, const mutable_buffer &id);
|
||||||
|
|
||||||
bool is_active() const;
|
bool is_active() const;
|
||||||
event::id::buf deactivate();
|
event::id::buf deactivate();
|
||||||
event::id::buf activate();
|
event::id::buf activate();
|
||||||
|
|
|
@ -108,7 +108,6 @@ libircd_la_SOURCES = \
|
||||||
m/dbs.cc \
|
m/dbs.cc \
|
||||||
m/state.cc \
|
m/state.cc \
|
||||||
m/room.cc \
|
m/room.cc \
|
||||||
m/filter.cc \
|
|
||||||
m/request.cc \
|
m/request.cc \
|
||||||
m/v1.cc \
|
m/v1.cc \
|
||||||
m/m.cc \
|
m/m.cc \
|
||||||
|
|
199
ircd/m/filter.cc
199
ircd/m/filter.cc
|
@ -1,199 +0,0 @@
|
||||||
// Matrix Construct
|
|
||||||
//
|
|
||||||
// Copyright (C) Matrix Construct Developers, Authors & Contributors
|
|
||||||
// Copyright (C) 2016-2018 Jason Volk <jason@zemos.net>
|
|
||||||
//
|
|
||||||
// Permission to use, copy, modify, and/or distribute this software for any
|
|
||||||
// purpose with or without fee is hereby granted, provided that the above
|
|
||||||
// copyright notice and this permission notice is present in all copies. The
|
|
||||||
// full license for this software is available in the LICENSE file.
|
|
||||||
|
|
||||||
//TODO: globular expression
|
|
||||||
bool
|
|
||||||
ircd::m::match(const room_event_filter &filter,
|
|
||||||
const event &event)
|
|
||||||
{
|
|
||||||
for(const auto &room_id : json::get<"not_rooms"_>(filter))
|
|
||||||
if(at<"room_id"_>(event) == unquote(room_id))
|
|
||||||
return false;
|
|
||||||
|
|
||||||
if(empty(json::get<"rooms"_>(filter)))
|
|
||||||
return match(event_filter{filter}, event);
|
|
||||||
|
|
||||||
for(const auto &room_id : json::get<"rooms"_>(filter))
|
|
||||||
if(at<"room_id"_>(event) == unquote(room_id))
|
|
||||||
return match(event_filter{filter}, event);
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
//TODO: globular expression
|
|
||||||
bool
|
|
||||||
ircd::m::match(const event_filter &filter,
|
|
||||||
const event &event)
|
|
||||||
{
|
|
||||||
for(const auto &type : json::get<"not_types"_>(filter))
|
|
||||||
if(at<"type"_>(event) == unquote(type))
|
|
||||||
return false;
|
|
||||||
|
|
||||||
for(const auto &sender : json::get<"not_senders"_>(filter))
|
|
||||||
if(at<"sender"_>(event) == unquote(sender))
|
|
||||||
return false;
|
|
||||||
|
|
||||||
if(empty(json::get<"senders"_>(filter)) && empty(json::get<"types"_>(filter)))
|
|
||||||
return true;
|
|
||||||
|
|
||||||
if(empty(json::get<"senders"_>(filter)))
|
|
||||||
{
|
|
||||||
for(const auto &type : json::get<"types"_>(filter))
|
|
||||||
if(at<"type"_>(event) == unquote(type))
|
|
||||||
return true;
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(empty(json::get<"types"_>(filter)))
|
|
||||||
{
|
|
||||||
for(const auto &sender : json::get<"senders"_>(filter))
|
|
||||||
if(at<"sender"_>(event) == unquote(sender))
|
|
||||||
return true;
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// filter
|
|
||||||
//
|
|
||||||
|
|
||||||
ircd::m::filter::filter(const user &user,
|
|
||||||
const string_view &filter_id,
|
|
||||||
const mutable_buffer &buf)
|
|
||||||
{
|
|
||||||
get(user, filter_id, [this, &buf]
|
|
||||||
(const json::object &filter)
|
|
||||||
{
|
|
||||||
const size_t len
|
|
||||||
{
|
|
||||||
copy(buf, string_view{filter})
|
|
||||||
};
|
|
||||||
|
|
||||||
new (this) m::filter
|
|
||||||
{
|
|
||||||
json::object
|
|
||||||
{
|
|
||||||
data(buf), len
|
|
||||||
}
|
|
||||||
};
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
ircd::string_view
|
|
||||||
ircd::m::filter::set(const mutable_buffer &idbuf,
|
|
||||||
const user &user,
|
|
||||||
const json::object &filter)
|
|
||||||
{
|
|
||||||
const auto user_room_id
|
|
||||||
{
|
|
||||||
user.room_id()
|
|
||||||
};
|
|
||||||
|
|
||||||
const m::room room
|
|
||||||
{
|
|
||||||
user_room_id
|
|
||||||
};
|
|
||||||
|
|
||||||
const sha256::buf hash
|
|
||||||
{
|
|
||||||
sha256{filter}
|
|
||||||
};
|
|
||||||
|
|
||||||
const string_view filter_id
|
|
||||||
{
|
|
||||||
b64encode_unpadded(idbuf, hash)
|
|
||||||
};
|
|
||||||
|
|
||||||
send(room, user.user_id, "ircd.filter", filter_id, filter);
|
|
||||||
return filter_id;
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
ircd::m::filter::get(const user &user,
|
|
||||||
const string_view &filter_id,
|
|
||||||
const closure &closure)
|
|
||||||
{
|
|
||||||
if(!get(std::nothrow, user, filter_id, closure))
|
|
||||||
throw m::NOT_FOUND
|
|
||||||
{
|
|
||||||
"Filter not found"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
bool
|
|
||||||
ircd::m::filter::get(std::nothrow_t,
|
|
||||||
const user &user,
|
|
||||||
const string_view &filter_id,
|
|
||||||
const closure &closure)
|
|
||||||
{
|
|
||||||
const auto user_room_id
|
|
||||||
{
|
|
||||||
user.room_id()
|
|
||||||
};
|
|
||||||
|
|
||||||
const m::room room
|
|
||||||
{
|
|
||||||
user_room_id
|
|
||||||
};
|
|
||||||
|
|
||||||
return room.get(std::nothrow, "ircd.filter", filter_id, [&closure]
|
|
||||||
(const m::event &event)
|
|
||||||
{
|
|
||||||
const json::object &content
|
|
||||||
{
|
|
||||||
at<"content"_>(event)
|
|
||||||
};
|
|
||||||
|
|
||||||
closure(content);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// room_filter
|
|
||||||
//
|
|
||||||
|
|
||||||
ircd::m::room_filter::room_filter(const mutable_buffer &buf,
|
|
||||||
const json::members &members)
|
|
||||||
:super_type::tuple
|
|
||||||
{
|
|
||||||
json::stringify(mutable_buffer{buf}, members)
|
|
||||||
}
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// room_event_filter
|
|
||||||
//
|
|
||||||
|
|
||||||
ircd::m::room_event_filter::room_event_filter(const mutable_buffer &buf,
|
|
||||||
const json::members &members)
|
|
||||||
:super_type::tuple
|
|
||||||
{
|
|
||||||
json::stringify(mutable_buffer{buf}, members)
|
|
||||||
}
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// event_filter
|
|
||||||
//
|
|
||||||
|
|
||||||
ircd::m::event_filter::event_filter(const mutable_buffer &buf,
|
|
||||||
const json::members &members)
|
|
||||||
:super_type::tuple
|
|
||||||
{
|
|
||||||
json::stringify(mutable_buffer{buf}, members)
|
|
||||||
}
|
|
||||||
{
|
|
||||||
}
|
|
197
ircd/m/m.cc
197
ircd/m/m.cc
|
@ -1430,6 +1430,132 @@ ircd::m::events::for_each(const uint64_t &start,
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// m/filter.h
|
||||||
|
//
|
||||||
|
|
||||||
|
//TODO: globular expression
|
||||||
|
bool
|
||||||
|
ircd::m::match(const room_event_filter &filter,
|
||||||
|
const event &event)
|
||||||
|
{
|
||||||
|
for(const auto &room_id : json::get<"not_rooms"_>(filter))
|
||||||
|
if(at<"room_id"_>(event) == unquote(room_id))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if(empty(json::get<"rooms"_>(filter)))
|
||||||
|
return match(event_filter{filter}, event);
|
||||||
|
|
||||||
|
for(const auto &room_id : json::get<"rooms"_>(filter))
|
||||||
|
if(at<"room_id"_>(event) == unquote(room_id))
|
||||||
|
return match(event_filter{filter}, event);
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
//TODO: globular expression
|
||||||
|
bool
|
||||||
|
ircd::m::match(const event_filter &filter,
|
||||||
|
const event &event)
|
||||||
|
{
|
||||||
|
for(const auto &type : json::get<"not_types"_>(filter))
|
||||||
|
if(at<"type"_>(event) == unquote(type))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
for(const auto &sender : json::get<"not_senders"_>(filter))
|
||||||
|
if(at<"sender"_>(event) == unquote(sender))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if(empty(json::get<"senders"_>(filter)) && empty(json::get<"types"_>(filter)))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if(empty(json::get<"senders"_>(filter)))
|
||||||
|
{
|
||||||
|
for(const auto &type : json::get<"types"_>(filter))
|
||||||
|
if(at<"type"_>(event) == unquote(type))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(empty(json::get<"types"_>(filter)))
|
||||||
|
{
|
||||||
|
for(const auto &sender : json::get<"senders"_>(filter))
|
||||||
|
if(at<"sender"_>(event) == unquote(sender))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// filter
|
||||||
|
//
|
||||||
|
|
||||||
|
ircd::m::filter::filter(const user &user,
|
||||||
|
const string_view &filter_id,
|
||||||
|
const mutable_buffer &buf)
|
||||||
|
{
|
||||||
|
get(user, filter_id, [this, &buf]
|
||||||
|
(const json::object &filter)
|
||||||
|
{
|
||||||
|
const size_t len
|
||||||
|
{
|
||||||
|
copy(buf, string_view{filter})
|
||||||
|
};
|
||||||
|
|
||||||
|
new (this) m::filter
|
||||||
|
{
|
||||||
|
json::object
|
||||||
|
{
|
||||||
|
data(buf), len
|
||||||
|
}
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// room_filter
|
||||||
|
//
|
||||||
|
|
||||||
|
ircd::m::room_filter::room_filter(const mutable_buffer &buf,
|
||||||
|
const json::members &members)
|
||||||
|
:super_type::tuple
|
||||||
|
{
|
||||||
|
json::stringify(mutable_buffer{buf}, members)
|
||||||
|
}
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// room_event_filter
|
||||||
|
//
|
||||||
|
|
||||||
|
ircd::m::room_event_filter::room_event_filter(const mutable_buffer &buf,
|
||||||
|
const json::members &members)
|
||||||
|
:super_type::tuple
|
||||||
|
{
|
||||||
|
json::stringify(mutable_buffer{buf}, members)
|
||||||
|
}
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// event_filter
|
||||||
|
//
|
||||||
|
|
||||||
|
ircd::m::event_filter::event_filter(const mutable_buffer &buf,
|
||||||
|
const json::members &members)
|
||||||
|
:super_type::tuple
|
||||||
|
{
|
||||||
|
json::stringify(mutable_buffer{buf}, members)
|
||||||
|
}
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// m/rooms.h
|
// m/rooms.h
|
||||||
|
@ -1679,6 +1805,77 @@ const
|
||||||
return function(*this);
|
return function(*this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ircd::m::event::id::buf
|
||||||
|
ircd::m::user::filter(const json::object &filter,
|
||||||
|
const mutable_buffer &idbuf)
|
||||||
|
{
|
||||||
|
using prototype = event::id::buf (const m::user &, const json::object &, const mutable_buffer &);
|
||||||
|
|
||||||
|
static import<prototype> function
|
||||||
|
{
|
||||||
|
"client_user", "filter_set"
|
||||||
|
};
|
||||||
|
|
||||||
|
return function(*this, filter, idbuf);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string
|
||||||
|
ircd::m::user::filter(const string_view &filter_id)
|
||||||
|
const
|
||||||
|
{
|
||||||
|
std::string ret;
|
||||||
|
filter(filter_id, [&ret]
|
||||||
|
(const json::object &filter)
|
||||||
|
{
|
||||||
|
ret.assign(data(filter), size(filter));
|
||||||
|
});
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string
|
||||||
|
ircd::m::user::filter(std::nothrow_t,
|
||||||
|
const string_view &filter_id)
|
||||||
|
const
|
||||||
|
{
|
||||||
|
std::string ret;
|
||||||
|
filter(std::nothrow, filter_id, [&ret]
|
||||||
|
(const json::object &filter)
|
||||||
|
{
|
||||||
|
ret.assign(data(filter), size(filter));
|
||||||
|
});
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
ircd::m::user::filter(const string_view &filter_id,
|
||||||
|
const filter_closure &closure)
|
||||||
|
const
|
||||||
|
{
|
||||||
|
if(!filter(std::nothrow, filter_id, closure))
|
||||||
|
throw m::NOT_FOUND
|
||||||
|
{
|
||||||
|
"Filter '%s' not found", filter_id
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
ircd::m::user::filter(std::nothrow_t,
|
||||||
|
const string_view &filter_id,
|
||||||
|
const filter_closure &closure)
|
||||||
|
const
|
||||||
|
{
|
||||||
|
using prototype = bool (std::nothrow_t, const m::user &, const string_view &, const filter_closure &);
|
||||||
|
|
||||||
|
static import<prototype> function
|
||||||
|
{
|
||||||
|
"client_user", "filter_get"
|
||||||
|
};
|
||||||
|
|
||||||
|
return function(std::nothrow, *this, filter_id, closure);
|
||||||
|
}
|
||||||
|
|
||||||
ircd::m::event::id::buf
|
ircd::m::event::id::buf
|
||||||
ircd::m::user::account_data(const m::user &sender,
|
ircd::m::user::account_data(const m::user &sender,
|
||||||
const string_view &type,
|
const string_view &type,
|
||||||
|
|
|
@ -23,7 +23,12 @@ get__filter(client &client,
|
||||||
url::decode(request.parv[2], filter_id_buf)
|
url::decode(request.parv[2], filter_id_buf)
|
||||||
};
|
};
|
||||||
|
|
||||||
m::filter::get(user_id, filter_id, [&client]
|
const m::user user
|
||||||
|
{
|
||||||
|
user_id
|
||||||
|
};
|
||||||
|
|
||||||
|
user.filter(filter_id, [&client]
|
||||||
(const json::object &filter)
|
(const json::object &filter)
|
||||||
{
|
{
|
||||||
resource::response
|
resource::response
|
||||||
|
@ -94,10 +99,15 @@ post__filter(client &client,
|
||||||
json::get<"presence"_>(request)
|
json::get<"presence"_>(request)
|
||||||
};
|
};
|
||||||
|
|
||||||
|
m::user user
|
||||||
|
{
|
||||||
|
user_id
|
||||||
|
};
|
||||||
|
|
||||||
char filter_id_buf[64];
|
char filter_id_buf[64];
|
||||||
const auto filter_id
|
const auto filter_id
|
||||||
{
|
{
|
||||||
m::filter::set(filter_id_buf, user_id, request.body)
|
user.filter(request.body, filter_id_buf)
|
||||||
};
|
};
|
||||||
|
|
||||||
return resource::response
|
return resource::response
|
||||||
|
@ -108,3 +118,54 @@ post__filter(client &client,
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
m::event::id::buf
|
||||||
|
filter_set(const m::user &user,
|
||||||
|
const json::object &filter,
|
||||||
|
const mutable_buffer &idbuf)
|
||||||
|
{
|
||||||
|
const m::user::room user_room
|
||||||
|
{
|
||||||
|
user
|
||||||
|
};
|
||||||
|
|
||||||
|
const sha256::buf hash
|
||||||
|
{
|
||||||
|
sha256{filter}
|
||||||
|
};
|
||||||
|
|
||||||
|
const string_view filter_id
|
||||||
|
{
|
||||||
|
b64encode_unpadded(idbuf, hash)
|
||||||
|
};
|
||||||
|
|
||||||
|
//TODO: ABA
|
||||||
|
if(user_room.has("ircd.filter", filter_id))
|
||||||
|
return {};
|
||||||
|
|
||||||
|
//TODO: ABA
|
||||||
|
return send(user_room, user.user_id, "ircd.filter", filter_id, filter);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
filter_get(std::nothrow_t,
|
||||||
|
const m::user &user,
|
||||||
|
const string_view &filter_id,
|
||||||
|
const m::user::filter_closure &closure)
|
||||||
|
{
|
||||||
|
const m::user::room user_room
|
||||||
|
{
|
||||||
|
user
|
||||||
|
};
|
||||||
|
|
||||||
|
return user_room.get(std::nothrow, "ircd.filter", filter_id, [&closure]
|
||||||
|
(const m::event &event)
|
||||||
|
{
|
||||||
|
const json::object &content
|
||||||
|
{
|
||||||
|
at<"content"_>(event)
|
||||||
|
};
|
||||||
|
|
||||||
|
closure(content);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
|
@ -15,6 +15,17 @@ extern ircd::resource user_resource;
|
||||||
// filter.cc
|
// filter.cc
|
||||||
//
|
//
|
||||||
|
|
||||||
|
extern "C" bool
|
||||||
|
filter_get(std::nothrow_t,
|
||||||
|
const ircd::m::user &,
|
||||||
|
const ircd::string_view &filter_id,
|
||||||
|
const ircd::m::user::filter_closure &);
|
||||||
|
|
||||||
|
extern "C" ircd::m::event::id::buf
|
||||||
|
filter_set(const ircd::m::user &,
|
||||||
|
const ircd::json::object &filter,
|
||||||
|
const ircd::mutable_buffer &idbuf);
|
||||||
|
|
||||||
ircd::resource::response
|
ircd::resource::response
|
||||||
get__filter(ircd::client &,
|
get__filter(ircd::client &,
|
||||||
const ircd::resource::request &,
|
const ircd::resource::request &,
|
||||||
|
|
Loading…
Reference in a new issue