FEP Convergence (400e, 7888, 171b/Conversation Containers, 76ea)
-
Conversation containers does send a 'Remove' if something is removed from a collection. But we typically don't waste resources on spammers, so we don't necessarily send a 'Remove' if we decided not to add it in the first place (perhaps due to comment controls, permissions, or blocks). You can send these as Remove activities if you want, but please don't force me to do so.
If you've fetched a conversation collection, it would be most common to do so in order to cache the conversation locally. In this case storing under local entities is going to be much more efficient if parents are stored before their children, so the InReplyTo can be pointed to an existing stored entity. If you do it backward, it's kind of awkward.
That said, our implementation of Collection objects has a flag to reverse the returned item order. So as long as the order is defined and isn't going to change, I don't actually care what it is; beyond the storage efficiency mentioned above. We need to sort it how we want after fetch anyway, because that's just basic input sanitisation.
It would seem most natural to me to send the collection in "thread" order - start from the root and recursively traverse every branch/leaf encountered. I'll mention this for consideration -- but again I really don't care. -
jenniferplusplus@hachyderm.ioreplied to jenniferplusplus@hachyderm.io on last edited by
@julian @silverpill @evan @trwnh @erincandescent @mikedev
As a side note, it's beyond frustrating that the original goal of this topic was to accomplish reply-limiting controls. But, a year and a half later, we're still bike shedding data types and haven't even gotten to the point of talking about an actual behavioral protocol for proposing, accepting, rejecting, and verifying the addition of an object to a relevant collection. -
No, that's for
target
property. Here's an example ofAdd.target
from Streams:"target": { "id": "https://streams.lndo.site/conversation/ed4775f8-18ee-46a5-821e-b2ed2dc546e8", "type": "Collection", "attributedTo": "https://streams.lndo.site/channel/red" },
In my code I have a handler for
Add
activity, which then sends activity to one of the other handlers:- Add{target: featured}
- Add{target: subscribers}
- Add{target: context}Currently I use heuristics to determine which one to use. But with
Add.target.type == <meaningful type name>
the code would be simpler and less fragile.Do you have something like that in NodeBB? I wonder how others solve this "routing" problem
-
julian@community.nodebb.orgreplied to jenniferplusplus@hachyderm.io on last edited by
@jenniferplusplus@hachyderm.io said in FEP Convergence (400e, 7888, 171b/Conversation Containers, 76ea):
As a side note, it's beyond frustrating that the original goal of this topic was to accomplish reply-limiting controls.
I understand your frustrations, and for what it's worth, I feel like we need to get the more basic expectations out of the way first, that is: how do we meaningfully assign context to a set of individual posts, besides the already available but fragile
inReplyTo
traversal?At the same time, I do think that all four FEPs mentioned utilise the same mechanism for establishing basic reply-limiting... that there is a context owner that ultimately decides whether a reply is added to the collection or not.
-
julian@community.nodebb.orgreplied to silverpill@mitra.social on last edited by
@silverpill@mitra.social said in FEP Convergence (400e, 7888, 171b/Conversation Containers, 76ea):
Do you have something like that in NodeBB? I wonder how others solve this "routing" problem
We do the same. We don't actually handle
Add
s right now, but ourUpdate
handler has aswitch..case
based ontype
.Adding a separate type would be easier, yes. Otherwise you're looking at additional logic to tease apart different variants that share the same base object type. For example, the logic for
Update(Note)
has further logic paths depending on whether the note is publicly addressed or not.So then yes, a
Add{target: Collectionish}
might be vague, but that's only the case if other implementations use the same. -
@julian This pattern can also be used in Accept and Undo activities:
{ "type": "Undo", "id": "https://social.example/activities/undo/1" "object": { "type": "Like", # or "Follow" "id": "https://social.example/activities/like/1" } }
-
@mikedev @julian you shouldn't have to send a Remove if you never Added it.
i also agree that the order should generally be forward-chrono because fetching the context in a linked data browser should render the context in the same way that the HTML view would render it by default. i don't know anyone who reads threads backwards.
in any case i recently submitted https://w3id.org/fep/1985 for explicitly declaring an `orderType` for OrderedCollection
-
trwnh@mastodon.socialreplied to trwnh@mastodon.social on last edited by
@mikedev @julian i am also thinking about extended OrderedCollection to specifically represent *sorted* sets and not just *ordered* sets. that fep would define `sortedBy` pointing to a vocab term, as well as `sortType` being either `Ascending` or `Descending`. the only thing that gives me pause is that people can lie about the value of their object's sorting property, for example setting an as:published in the distant past to be pinned to the beginning of the SortedCollection.
-
@julian i replied from socialhub but it seems to not have made it across yet... again :x https://socialhub.activitypub.rocks/t/fep-convergence-400e-7888-171b-conversation-containers-76ea/4669/12
-
julian:
They establish a conversational context for a given object
from my understanding, only 7888 and 171b do this. 76ea instead tries to establish a central view of a reply tree, which is not the same as a conversation. there are several cases where replies and context diverge:
- replying to something in a different conversation (for example, when conversations get forked or posts get moved to a new conversation)
- participating in a conversation without replying
- replying without participating in a conversation
also, there is the consideration that
julian:context
is used for grouping, even if it's not resolvable. so it gracefully falls back to basic grouping behavior in the simplest case.thr:thread
doesn't do this.They federate out an
Add
on collection addition. (76ea also sendsRemove
)you can send a Remove in all three FEPs, it might just not be called out explicitly. the use of Add/Remove is a courtesy to anyone else following along, so they don't have to fetch the collection manually every single time. (although fetching the collection every single time is inefficient, it is the only way to have a guaranteed consistent state, so there are reasons why you may want to browse the collection "at the authoritative origin", so to speak.)
julian:171b specifies a new object type
Context
i am not strictly opposed to this, but neither do i support it. it might end up being useful to define a type that means "this specifically represents a collection whose items share the same
context
property" (as i thinkContext
is trying to do), but this should not be required.similarly, we could define a type that means "this specifically represents a collection whose items all have
content
" (we could call itConversation
orCollectionOfPosts
orCollectionOfContentfulObjects
or whatever) but this is similarly something that shouldn't be required.the reason that i think such types shouldn't be required is that not only are they not necessary for the basic mechanisms to work, they also might be misleading or incorrect, because ultimately the contents of any collection are solely decided by whoever owns the collection. i could declare that a collection is a
julian:Context
and then immediately after this i go and Add a bunch of objects that don't have thatcontext
, or anycontext
at all for that matter. this is something that is going to be very relevant in the interim where NodeBB and similar implementations continue to have behavior for traversing reply trees and attaching posts to topics that aren't explicitly declared ascontext
. (not that i think this behavior is necessarily always correct, either -- it's just something that could be done, and is probably useful to do, insofar as other implementations continue to remain unaware ofcontext
and its grouping properties. you could just as equally convert posts withinReplyTo
but nocontext
into NodeBB Chat Messages instead of NodeBB Topic Posts... but this is an implementation decision.)Collection items:
- 7888 sends objects in chronological order
- 171b sends activities in chronological order
- 76ea sends objects in reverse chronological order
7888 is agnostic as to what the exact contents are, aside from them ideally all sharing the same
context
-- you could have a 7888 collection contain any type in any order. however, with that said: i favor post objects (anything that hascontent
) in forward chronological order, because this is what is most useful to the casual browser. i don't know of any forum software that chooses to present threads in reverse order with the newest posts at the top. they usually do this for topics, but not for posts.also: these are "defaults", and ultimately we should probably move toward explicitly signaling how collections might be ordered or sorted, as well as providing a mechanism for requesting non-default presentations like "show me this thread in reverse chronological order" (
?reversed=true
or?sort=newest
or whatever) or "show me posts starting at index 69 and containing 7 items" (?startIndex=69&window=7
). to that end, i recently submitted https://w3id.org/fep/1985 for declaring anOrderedCollection
to have an explicitorderType
ofForwardChronological
orReverseChronological
. i also have a pre-draft of a FEP dealing with collections that are not just ordered sets, but specifically sorted sets. this would defineSortedCollection
as an extension ofOrderedCollection
, as well as defining asortedBy
property pointing to a vocab term, plus asortType
of eitherAscending
orDescending
. there's https://socialhub.activitypub.rocks/t/pre-fep-evolving-orderedcollection-to-be-more-useful/4608 as the thread exploring this.regarding the signaling of any given collection or actor following a specific protocol, i think we should define that explicit protocol before defining types. my old draft of FEP-9988 for "Federated Forums" was put on hold for exactly this reason -- there are simply too many protocol considerations that need to happen first. https://socialhub.activitypub.rocks/t/desired-ux-for-forums-and-accompanying-user-stories/4181 or https://community.nodebb.org/post/99491 exists as a thread to collect user stories for forum UX that should directly inform the development of such a protocol.
-
julian@community.nodebb.orgreplied to trwnh@mastodon.social on last edited by
@trwnh@mastodon.social @mikedev@fediversity.site I think end of the day it's an implementation detail that is of minimal significance. When I fetch the collection pages I don't trust the order anyway, I reorder them all by date once I have them all anyways.
@silverpill@mitra.social said that reverse chrono for activities is preferable, and that makes sense if you want to sync up. Just retrieve activities until you reach one you've seen and you're caught up.
-
julian@community.nodebb.orgreplied to trwnh@socialhub.activitypub.rocks on last edited by
@trwnh@socialhub.activitypub.rocks said in FEP Convergence (400e, 7888, 171b/Conversation Containers, 76ea):
i don't know of any forum software that chooses to present threads in reverse order with the newest posts at the top.
I'll bite. NodeBB lets you choose how to sort the posts. Chrono, reverse, or by vote count. Q&A forums might elect to use the latter two. But that's neither here nor there, it's a frontend UX thing and shouldn't really have any bearing on an AP S2S implementation detail.
-
@julian @mikedev @silverpill i generally agree that seeing newest activities is usually preferable , but you could just as easily traverse as:last/as:prev* and stop when you reach something you've already seen, instead of traversing as:first/as:next* and likewise stopping when you reach something you've already seen. it's never made sense to me to mandate reversed order when it should just be the "recommended default". i think the real issue is that OrderedCollection doesn't imply any real order
-
trwnh@socialhub.activitypub.rocksreplied to julian@community.nodebb.org on last edited byjulian:
that's neither here nor there, it's a frontend UX thing and shouldn't really have any bearing on an AP S2S implementation detail
It has bearing on anyone browsing the linked data, as brought up immediately after:
trwnh:also: these are “defaults”, and ultimately we should probably move toward explicitly signaling how collections might be ordered or sorted, as well as providing a mechanism for requesting non-default presentations like “show me this thread in reverse chronological order” (
?reversed=true
or?sort=newest
or whatever) or “show me posts starting at index 69 and containing 7 items” (?startIndex=69&window=7
). to that end, i recently submitted fep/fep/1985/fep-1985.md at main - fediverse/fep - Codeberg.org for declaring anOrderedCollection
to have an explicitorderType
ofForwardChronological
orReverseChronological
. i also have a pre-draft of a FEP dealing with collections that are not just ordered sets, but specifically sorted sets. this would defineSortedCollection
as an extension ofOrderedCollection
, as well as defining asortedBy
property pointing to a vocab term, plus asortType
of eitherAscending
orDescending
. there’s Pre-FEP: Evolving OrderedCollection to be more useful as the thread exploring this.Basically, imagine using https://browser.pub (or any other Web browser, really). The representation you serve in response to any GET request should be usable without requiring additional processing. You should be able to follow links normally like any other browser. This is the foundation of linked data.
-
@julian @silverpill @trwnh @erincandescent @mikedev @jenniferplusplus@hachyderm.io obviously `context` isn't good enough to identify the thread relationship. Trying to hijack it is contrary to the AS2 spec and common interoperability. One proposal tries to specify it by duck-typing every object; the other by defining a new Collection type. The clearest way to define the relationship is with a property, `thread`, which is specific, clear, and requires no other changes.
-
evan@cosocial.careplied to evan@cosocial.ca on last edited by
@julian @silverpill @trwnh @erincandescent @mikedev I think most developers understand that the reply tree and the conversation are identical. The use cases a describes -- forking, etc. -- can be implemented with `Announce`, perhaps with `content` in the `Announce` activity. I'll add these next week and push a new draft.
-
erincandescent@akko.erincandescent.netreplied to evan@cosocial.ca on last edited by@evan @julian @silverpill @trwnh @mikedev "context" isn't good enough to identify any relationship; this is the fundamental problem. It is a property that should never have existed. Today it identifies one relationship: the (loosely defined) thread. I would argue that this is in fact "common interoperability". I would also argue that this fully meets the incredibly vague letter of the ActivityStreams specification.
I have yet to see an alternative use of context that would not be better served by inventing a more specific term. Yes, this applies to use of context for thread too, but we have 7 years of its user to identify the thread as a defacto standard. -
trwnh@mastodon.socialreplied to erincandescent@akko.erincandescent.net on last edited by
@erincandescent @julian @evan @mikedev @silverpill i don’t think “conversational thread” is a special semantic relationship, and i certainly don’t think it is equal or equivalent to a reply tree! the basis of 7888 is that context should be used for purposeful logical grouping, as it was intended and as it ended up being used in pleroma for years. an unresolvable opaque uri is 7888-compliant. so is a collection with an owner. so is anything else. but IF it is a collection,
-
trwnh@mastodon.socialreplied to trwnh@mastodon.social on last edited by
@erincandescent @julian @evan @mikedev @silverpill …then it makes sense that the collection ought to contain items sharing the same contextual grouping. it’s similar to how hashtags are content-addressed grouping, but less purposeful, and no one owns them. the key is that even if you can’t resolve anything out of whatever is in context, you can still use it for grouping by opaque string matching. so there’s clearly defined graceful fallback.
-
evan@cosocial.careplied to evan@cosocial.ca on last edited by
@julian @silverpill @trwnh @erincandescent @mikedev I think `context` can be used as a fallback, which provides continuity for most of the legacy implementations.