0
0
Fork 0
mirror of https://github.com/matrix-construct/construct synced 2024-06-25 21:38:18 +02:00

ircd:Ⓜ️:event::auth: Add auth chain traversal.

This commit is contained in:
Jason Volk 2019-02-08 07:54:03 -08:00
parent 2b82dfec76
commit 80a25cf352
4 changed files with 97 additions and 6 deletions

View file

@ -18,6 +18,7 @@ namespace ircd::m
struct ircd::m::event::auth
{
struct chain;
event::idx idx;
@ -40,10 +41,17 @@ struct ircd::m::event::auth
}
};
inline
ircd::m::event::auth::auth(const event::idx &idx)
noexcept
:idx{idx}
struct ircd::m::event::auth::chain
{
assert(idx);
}
event::auth auth;
public:
using closure = std::function<event::idx (const event::idx &)>;
bool for_each(const string_view &type, const closure &) const;
bool for_each(const closure &) const;
chain(const event::idx &idx)
:auth{idx}
{}
};

View file

@ -1125,6 +1125,32 @@ ircd::m::is_power_event(const m::event &event)
return false;
}
//
// event::auth::chain
//
bool
ircd::m::event::auth::chain::for_each(const closure &closure)
const
{
return for_each(string_view{}, closure);
}
bool
ircd::m::event::auth::chain::for_each(const string_view &type,
const closure &c)
const
{
using prototype = bool (event::auth, const string_view &, const closure &);
static mods::import<prototype> auth_chain_for_each
{
"m_event", "auth_chain_for_each"
};
return auth_chain_for_each(auth, type, c);
}
//
// event::auth
//

View file

@ -5917,6 +5917,31 @@ console_cmd__event__auth(opt &out, const string_view &line)
return true;
}
bool
console_cmd__event__auth__chain(opt &out, const string_view &line)
{
const params param{line, " ",
{
"event_id", "type"
}};
const m::event::id &event_id
{
param.at("event_id")
};
const string_view type
{
param.at("type", ""_sv)
};
const m::event::auth::chain auth
{
index(event_id)
};
auth.for_each(type, [&out]
(const m::event::idx &idx)
{
const m::event::fetch event
{

View file

@ -682,3 +682,35 @@ event_auth__rebuild()
txn();
}
extern "C" bool
auth_chain_for_each(event::auth auth,
const string_view &type,
const event::auth::chain::closure &closure)
{
event::idx next(0);
uint64_t depth[2] {uint64_t(-1), 0}; do
{
auth.for_each(type, [&depth, &next]
(const event::idx &event_idx)
{
if(!m::get(event_idx, "depth", depth[1]))
return true;
if(depth[1] >= depth[0])
return true;
depth[0] = depth[1];
next = event_idx;
return true;
});
if(!closure(next))
return false;
auth.idx = next;
next = 0;
}
while(auth.idx);
return true;
}