diff --git a/include/ircd/m/event/append.h b/include/ircd/m/event/append.h index d3519207b..474017d57 100644 --- a/include/ircd/m/event/append.h +++ b/include/ircd/m/event/append.h @@ -41,6 +41,8 @@ struct ircd::m::event::append bool is_invisible(const event &, const opts &) const; bool is_excluded(const event &, const opts &) const; + bool bundle_replace(json::stack::object &, const event &, const opts &); + void _relations(json::stack::object &, const event &, const opts &); void _age(json::stack::object &, const event &, const opts &); void _txnid(json::stack::object &, const event &, const opts &); void _prev_state(json::stack::object &, const event &, const opts &); @@ -72,6 +74,8 @@ struct ircd::m::event::append::opts bool query_prev_state {true}; bool query_redacted {true}; bool query_visible {false}; + bool bundle_all {false}; + bool bundle_replace {false}; }; inline diff --git a/matrix/event_append.cc b/matrix/event_append.cc index 4157e1b90..d4ec165f6 100644 --- a/matrix/event_append.cc +++ b/matrix/event_append.cc @@ -187,7 +187,7 @@ ircd::m::event::append::_unsigned(json::stack::object &out, _age(object, event, opts); _txnid(object, event, opts); - + _relations(object, event, opts); if(defined(json::get<"state_key"_>(event))) _prev_state(object, event, opts); } @@ -197,7 +197,7 @@ ircd::m::event::append::_prev_state(json::stack::object &out, const event &event, const opts &opts) { - assert(defined(json::get<"state_key"_>(event))) + assert(defined(json::get<"state_key"_>(event))); const bool query_prev_state { @@ -339,6 +339,68 @@ ircd::m::event::append::_age(json::stack::object &out, }; } +void +ircd::m::event::append::_relations(json::stack::object &out, + const event &event, + const opts &opts) +{ + assert(out.s); + json::stack::checkpoint cp + { + *out.s, false + }; + + json::stack::object object + { + out, "m.relations" + }; + + bool commit + { + cp.committing() + }; + + if(opts.bundle_all || opts.bundle_replace) + commit |= bundle_replace(object, event, opts); + + cp.committing(commit); +} + +bool +ircd::m::event::append::bundle_replace(json::stack::object &out, + const event &event, + const opts &opts) +{ + const m::replaced replaced + { + opts.event_idx, m::replaced::latest + }; + + const event::idx &replace_idx + { + replaced + }; + + if(likely(!replace_idx)) + return false; + + const m::event::fetch replace + { + std::nothrow, replace_idx + }; + + if(unlikely(!replace.valid)) + return false; + + json::stack::object object + { + out, "m.replace" + }; + + object.append(replace); + return true; +} + bool ircd::m::event::append::is_excluded(const event &event, const opts &opts)