Protocol compliance

We are currently challenging our implementation of ActivityPub in Mobilizon, starting with event creation.

There are messages of type Announce and Create, each one signed with an Actor’s private key.

As of now, when a Person publishes a message within a Group on an instance, Mobilizon publishes the following messages to the recipient’s inboxes:

  1. an ‘Announce’ of the event object, signed by the relay actor
  2. a ‘Create’ of the event object, signed by the Person actor
  3. an ‘Announce of the event object’ signed by the Group actor

Note: the order is likely this one even if messages may be sent by different threads.

We are wondering if Mobilizon is respecting the ActivityPub specifications.
What is the right way to announce a new event ? We are also looking for a good resource explaining it.

This seems to be compatible with ActivityPub. However, a more interesting question is how well it works with other Fediverse software.

I think (3) could be replaced with Announce(Create(Event)), which is used by federated forums: https://codeberg.org/fediverse/fep/src/branch/main/fep/1b12/fep-1b12.md

how well it works with other Fediverse software

great question.

It kinda works with Mastodon except that it is showing each content twice.

On the contrary, when getting Event contents from Gancio, Mobilizon is not displaying them because it is waiting for an announce.

That’s why I’m looking documentation on how to implement the protocol properly.

I don’t know much about event federation, but on the surface, the proposed solutions look reasonable:

  • Do not send Announce if you already send Create - that seems redundant.
  • Do not require Announce (in theory, the application should also be able to fetch Event by its id if a user wants to look it up).

cc @andre

I’m going to highjack this a bit to get a question answered. It’s somewhat related.

@setop If I understand you correctly, sending the activity:

{
  "@context": [
    "https://www.w3.org/ns/activitystreams"
  ],
  "actor": "http://host.test/some/actor",
  "cc": [],
  "id": "http://host.test/activities/Czql1UuLLI2uHtqO",
  "object": {
    "@context": [
      "https://www.w3.org/ns/activitystreams"
    ],
    "attributedTo": "http://host.test/some/actor",
    "cc": [],
    "content": "event content",
    "endTime": "2026-04-18T10:48:43.257016+00:00Z",
    "id": "http://host.test/objects/9vWnkV49TTwQWuNx",
    "location": {
      "type": "VirtualLocation",
      "url": "http://localhost"
    },
    "name": "my event",
    "published": "2026-04-14T07:48:43Z",
    "startTime": "2026-04-18T07:48:43.256966+00:00Z",
    "to": [
      "https://www.w3.org/ns/activitystreams#Public",
      "http://other.test/some/actor"
    ],
    "type": "Event"
  },
  "published": "2026-04-14T07:48:43Z",
  "to": [
    "https://www.w3.org/ns/activitystreams#Public",
    "http://other.test/some/actor"
  ],
  "type": "Create"
}

to a mobilizon actor will not work, i.e. it is not displayed in Mobilizon. If instead, I use "type": "Announce", it will be displayed?

For context, the example is from Some events - Funfedi Connect and this is currently only tested with gancio,