Skip to content

Commit

Permalink
XEP-0425: Updates based on list feedback
Browse files Browse the repository at this point in the history
- Remove the dependency on XEP-0422 Message Fastening
- Rename to 'Moderated Message Retraction' and focus only on the retraction use-case
- Clarify the purpose of the `reason` element
- Specify that clients must check that the correct stanza ID was used (based on the `by` attribute)
- Relax the requirement that a `by` attribute be added to the `<moderated>` element to SHOULD.

Mailing list thread is here:
https://mail.jabber.org/pipermail/standards/2021-December/038660.html
  • Loading branch information
jcbrand committed Mar 12, 2024
1 parent 2ec7b59 commit ef79d2c
Showing 1 changed file with 60 additions and 42 deletions.
102 changes: 60 additions & 42 deletions xep-0425.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,11 @@
<?xml-stylesheet type='text/xsl' href='xep.xsl'?>
<xep>
<header>
<title>Message Moderation</title>
<abstract>This specification defines a method for groupchat moderators to moderate messages.</abstract>
<title>Moderated Message Retraction</title>
<abstract>This specification defines a method for groupchat moderators to retract messages of other users.</abstract>
&LEGALNOTICE;
<number>0425</number>
<status>Proposed</status>
<status>Experimental</status>
<lastcall>2022-01-04</lastcall>
<type>Standards Track</type>
<sig>Standards</sig>
Expand All @@ -19,12 +19,24 @@
<spec>XMPP Core</spec>
<spec>XMPP IM</spec>
<spec>XEP-0313</spec>
<spec>XEP-0422</spec>
</dependencies>
<supersedes/>
<supersededby/>
<shortname>message-moderation</shortname>
&jcbrand;
<revision>
<version>0.3.0</version>
<date>2023-03-02</date>
<initials>jcb</initials>
<remark>
<ul>
<li>Remove the dependency on XEP-0422 Message Fastening</li>
<li>Rename to 'Moderated Message Retraction' and focus only on the retraction use-case</li>
<li>Ensure compatibility with clients that only implement XEP-0424</li>
<li>Clarify the purpose of the &lt;reason/&gt; element</li>
</ul>
</remark>
</revision>
<revision>
<version>0.2.1</version>
<date>2020-01-28</date>
Expand All @@ -51,74 +63,75 @@
</revision>
</header>
<section1 topic='Introduction' anchor='intro'>
<p>Occasionally, a &xep0045; moderator might wish to moderate certain groupchat messages by, for example, retracting them from the groupchat history as part of an effort to address and remedy issues such as message spam, indecent language for the venue or exposing private third-party personal information. Alternatively, a moderator might want to correct a message on another user's behalf, or flag a message as inappropriate without requiring that it be retracted.</p>
<p>Occasionally, a &xep0045; moderator might wish to moderate certain groupchat messages by, for example, retracting them from the groupchat history as part of an effort to address and remedy issues such as message spam, indecent language for the venue or exposing private third-party personal information.</p>
<p>This XEP is designed in such a way to also allow other potential moderator actions, such as message editing, but these actions fall out of the scope of this XEP and we will only be considering message retractions.</p>
<p>Due to the federated nature of XMPP and as with any content moderation tool, the moderation request can <strong>only be considered as a hint</strong> and clients which don't support message moderation are not obligated to enforce any such request.</p>
</section1>
<section1 topic='Discovering support' anchor='disco'>
<p>If a client or service implements message moderation, it MUST specify the 'urn:xmpp:message-moderate:0' feature in its service discovery information features as specified in &xep0030; and the Entity Capabilities profile specified in &xep0115;.</p>
<example caption='Client requests information from a groupchat service'><![CDATA[
<p>If a groupchat supports moderated message retraction, it MUST specify the 'urn:xmpp:message-moderate:1' feature in its service discovery information features as specified in &xep0030; and the Entity Capabilities profile specified in &xep0115;.</p>
<example caption='Client requests information from a Multi-User Chat (MUC)'><![CDATA[
<iq type='get'
from='romeo@montague.example/orchard'
to='room@muc.example.com'
id='info1'>
<query xmlns='http://jabber.org/protocol/disco#info'/>
</iq>]]></example>
<example caption='The groupchat service advertises support for moderation'><![CDATA[
<example caption='The MUC advertises support for moderation'><![CDATA[
<iq type='result'
to='romeo@montague.example/home'
from='room@muc.example.com'
id='info1'>
<query xmlns='http://jabber.org/protocol/disco#info'>
...
<feature var='urn:xmpp:message-moderate:0'/>
<feature var='urn:xmpp:message-moderate:1'/>
...
</query>
</iq>]]></example>
</section1>
<section1 topic='Use Case' anchor='usecase'>
<p>Consider a situation where a user sends a message that may be deemed inappropriate by a groupchat moderator. The groupchat service will append a &xep0359; stanza ID to the message before relaying it to all participants.</p>
<example caption="The user's client sends a message and the groupchat service adds a stanza id."><![CDATA[
<p>Consider a situation where a user sends a message that may be deemed inappropriate by a groupchat moderator. The MUC will append a &xep0359; stanza ID to the message before relaying it to all participants.</p>
<example caption="The user's client sends a message and the MUC adds a stanza id."><![CDATA[
<message type="groupchat" from="room@muc.example.com/oldhag" to='room@muc.example.com/macbeth' id='inappropriate-1'>
<body>DM me for free magic potions!</body>
<stanza-id xmlns='urn:xmpp:sid:0' id='stanza-id-1' by='room@muc.example.com'/>
</message>]]></example>

<p>The moderator sees the message and indicates to their client that the message should be retracted. The client then sends an IQ stanza to the MUC service, requesting that the message be retracted.</p>
<p>An optional &lt;reason/&gt; element may be included inside the &lt;moderate/&gt; element, to provide a human-readable explanation why the message was retracted.</p>

<example caption="The moderator's client sends an IQ stanza to the MUC service"><![CDATA[
<iq type='set' to='room@muc.example.com' id='retract-request-1'>
<apply-to id="stanza-id-1" xmlns="urn:xmpp:fasten:0">
<moderate xmlns='urn:xmpp:message-moderate:0'>
<retract xmlns='urn:xmpp:message-retract:0'/>
<reason>This message contains inappropriate content for this forum</reason>
</moderate>
</apply-to>
<moderate id="stanza-id-1" xmlns='urn:xmpp:message-moderate:1'>
<retract xmlns='urn:xmpp:message-retract:1'/>
<reason>This message contains inappropriate content for this forum</reason>
</moderate>
</iq>]]></example>

<section2 topic='Success case' anchor='usecase-success'>

<p>If the moderator is allowed to moderate the message, the groupchat service will send a message stanza to all participants (including the moderator), indicating that the message has been retracted and by whom.</p>
<p>This message will use &xep0422; to indicate that it applies to the moderated message, by referring to its XEP-0359 Stanza ID.</p>
<p>If the moderator is allowed to moderate the message, the MUC will send a message stanza to all participants (including the moderator), indicating that the message has been retracted and by whom.</p>
<p>This message will use &xep0424; to indicate that it is a retraction, and will refer to the retracted message by its XEP-0359 Stanza ID. Care must be taken to use the stanza ID that was added by the MUC, i.e. which has a "by" attribute set to the MUC JID, and not some other stanza ID. The client MUST check that the correct stanza ID was used and ignore the stanza if not.</p>
<p>Inside the &lt;retract/&gt; element is a &lt;moderated/&gt; element indicating that the retraction was a moderator action, as well as an optional reason.</p>

<example caption='The groupchat service sends a moderation message to all participants'><![CDATA[
<example caption='The MUC sends a moderation message to all participants'><![CDATA[
<message type="groupchat" id='retraction-id-1' from='room@muc.example.com' to="room@muc.example.com/macbeth">
<apply-to id="stanza-id-1" xmlns="urn:xmpp:fasten:0">
<moderated by='room@muc.example.com/macbeth' xmlns='urn:xmpp:message-moderate:0'>
<retract xmlns='urn:xmpp:message-retract:0' />
<reason>This message contains inappropriate content for this forum</reason>
<retract id="stanza-id-1" xmlns='urn:xmpp:message-retract:1'>
<moderated by='room@muc.example.com/macbeth' xmlns='urn:xmpp:message-moderate:1'>
<occupant-id xmlns="urn:xmpp:occupant-id:0" id="dd72603deec90a38ba552f7c68cbcc61bca202cd" />
</moderated>
</apply-to>
<reason>This message contains inappropriate content for this forum</reason>
</retract>
</message>]]></example>

<p>The groupchat service also responds with an IQ "result" stanza.</p>
<p>The MUC also responds with an IQ "result" stanza.</p>

<example caption='The groupchat service responds to the IQ stanza'><![CDATA[
<example caption='The MUC responds to the IQ stanza'><![CDATA[
<iq type='result' to='juliet@montague.example/home' id='retract-request-1'></iq>]]></example>
</section2>

<section2 topic='Error case' anchor='usecase-error'>
<p>In case the message could for some reason not be retracted, the grouchat service responds with an IQ stanza of type error.</p>
<example caption='The groupchat service responds with an error stanza'><![CDATA[
<p>In case the message could for some reason not be retracted, the MUC responds with an IQ stanza of type error.</p>
<example caption='The MUC responds with an error stanza'><![CDATA[
<iq type='error' to='room@muc.example.com/macbeth' id='retract-request-1'>
<error type='modify'>
<forbidden xmlns='urn:ietf:params:xml:ns:xmpp-stanzas'/>
Expand All @@ -132,8 +145,10 @@

<section1 topic='Tombstones' anchor='tombstones'>
<p>A &xep0313; service MAY replace the contents of a message, that was retracted due to moderation, with a 'tombstone' similar to the one described in &xep0424;.</p>
<p>The archiving service replaces the message contents (i.e. the &lt;body/&gt; and any related elements which might leak information about the original message) with a &lt;moderated/&gt; element which in turn contains a &lt;retracted/&gt; element. The &lt;moderated/&gt; element MUST have a 'by' attribute specifying the JID of the moderating entity.</p>
<p>If the message was sent in a semi-anonymous MUC, the occupant id from &xep0421; SHOULD be included for the moderator and the message author in the &lt;moderated/&gt; and &lt;retracted/&gt; elements respectively. </p>
<p>The archiving service replaces the message contents (i.e. the &lt;body/&gt; and any related elements which might leak information about the original message) with a &lt;retracted/&gt; element which in turn contains a &lt;moderated/&gt; element.</p>
<p>Note the past tense in the element names, e.g. "retracted" instead of just "retract", to indicate that the retraction has already been executed and that this is therefore a tombstone and not an action that should be applied.</p>
<p>The &lt;moderated/&gt; element SHOULD have a 'by' attribute specifying the JID of the moderating entity. There might however be cases where it's preferable to not specify which JID was responsible for the moderation, for example when the moderation happens in an automated manner.</p>
<p>If the message was sent in a semi-anonymous MUC, the occupant id from &xep0421; SHOULD be included for the moderator in the &lt;moderated/&gt; element and for the original (retracted) message author in the &lt;message/&gt; element.</p>

<example caption='Retracted groupchat message tombstone in a MAM result'><![CDATA[
<message id='aeb213' to='room@muc.example.com/macbeth'>
Expand All @@ -142,11 +157,12 @@
<delay xmlns='urn:xmpp:delay' stamp='2019-09-20T23:18:41Z'/>
<message type="groupchat" from="room@muc.example.com/oldhag" to="room@muc.example.com/macbeth" id="message-id-1">
<occupant-id xmlns="urn:xmpp:occupant-id:0" id="ef73b09de9c90a38ba552f7c68cbeef1dca24429" />
<moderated by="witch@shakespeare.example">
<occupant-id xmlns="urn:xmpp:occupant-id:0" id="dd72603deec90a38ba552f7c68cbcc61bca202cd" />
<retracted stamp='2019-09-20T23:19:12Z' xmlns='urn:xmpp:message-retract:0'/>
<retracted stamp='2019-09-20T23:19:12Z' xmlns='urn:xmpp:message-retract:0'>
<moderated by="witch@shakespeare.example" xmlns="urn:xmpp:message-moderate:1">
<occupant-id xmlns="urn:xmpp:occupant-id:0" id="dd72603deec90a38ba552f7c68cbcc61bca202cd" />
</moderated>
<reason>This message contains inappropriate content for this forum</reason>
</moderated>
</retracted>
</message>
</forwarded>
</result>
Expand All @@ -156,7 +172,7 @@
<section1 topic='Business Rules' anchor='rules'>
<p>A moderator MUST NOT send a moderation request for a message with non-messaging payloads. For example, a moderator MUST NOT moderate a roster item exchange request or a file transfer part.</p>
<p>In MUCs, only moderation messages (not tombstones, but messages containing the &lt;moderate/&gt; element) received from the MUC service itself are legitimate, all other such messages MUST be discarded.</p>
<p>If message moderation includes a retraction request, the MUC or other service that supports message retraction SHOULD prevent further distribution of the retracted message by the service and the archiving service MAY replace the retracted message with a tombstone as detailed in &xep0424;.</p>
<p>The MUC or other service that supports message retraction SHOULD prevent further distribution of a moderated retracted message and the archiving service MAY replace the retracted message with a tombstone.</p>
</section1>
<section1 topic='Security Considerations' anchor='security'>
<p>There can never be a guarantee that a moderated message will appear as such in all clients. Clients should therefore, when possible, inform users that no such guarantee exists.</p>
Expand All @@ -167,9 +183,9 @@
</section1>
<section1 topic='XMPP Registrar Considerations' anchor='registrar'>
<section2 topic='Protocol Namespaces' anchor='ns'>
<p>The &REGISTRAR; includes 'urn:xmpp:message-moderate:0' in its registry of protocol namespaces (see &NAMESPACES;).</p>
<p>The &REGISTRAR; includes 'urn:xmpp:message-moderate:1' in its registry of protocol namespaces (see &NAMESPACES;).</p>
<ul>
<li>urn:xmpp:message-moderate:0</li>
<li>urn:xmpp:message-moderate:1</li>
</ul>
</section2>
<section2 topic='Protocol Versioning' anchor='registrar-versioning'>
Expand All @@ -182,17 +198,19 @@
<xs:schema
xmlns:xs='http://www.w3.org/2001/XMLSchema'
targetNamespace='urn:xmpp:message-moderate:0'
xmlns='urn:xmpp:message-moderate:0'
targetNamespace='urn:xmpp:message-moderate:1'
xmlns='urn:xmpp:message-moderate:1'
elementFormDefault='qualified'>
<xs:element name='moderate'></xs:element>
<xs:element name='moderate'>
<xs:attribute name='id' type='xs:string' use='required'/>
</xs:element>
<xs:element name='moderated'>
<xs:complexType>
<xs:simpleContent>
<xs:extension base='xs:string'>
<xs:attribute name='by' type='xs:string' use='required'/>
<xs:attribute name='by' type='xs:string'/>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
Expand Down

0 comments on commit ef79d2c

Please sign in to comment.