public synchronized CompletableFuture<?> propagate( @Nonnull Packet stanza, @Nonnull MUCOccupant sender )
    {
        if ( !(room.isFmucEnabled() && FMUC_ENABLED.getValue()) ) {
            Log.debug( "(room: '{}'): FMUC disabled, skipping FMUC propagation.", room.getJID() );
            return CompletableFuture.completedFuture(null);
        }

        Log.debug( "(room: '{}'): A stanza (type: {}, from: {}) is to be propagated in the FMUC node set.", room.getJID(), stanza.getClass().getSimpleName(), stanza.getFrom() );

        /* TODO this implementation currently is blocking, and synchronous: inbound propagation only occurs after outbound
                propagation has been started. Is this needed? What should happen if outbound propagation fails? When the
                mode used is master/slave, then it is reasonable to assume that a failed outbound propagation makes the
                message propagation fail completely (and thus should not be propagated to the inbound nodes or locally?
        */
        // propagate to joined FMUC node (conditionally blocks, depending on FMUC mode that's in effect).
        final CompletableFuture<?> propagateToOutbound = propagateOutbound( stanza, sender );

        // propagate to all joining FMUC nodes (need never block).
        final CompletableFuture<?> propagateToInbound = propagateInbound( stanza, sender );

        // Return a Future that completes when all of the Futures constructed above complete.
        return CompletableFuture.allOf( propagateToOutbound, propagateToInbound );
    }
Propagates a stanza to the FMUC set, if FMUC is active for this room.

Note that when a master-slave mode is active, we need to wait for an echo back, before the message can be
broadcasted locally. This method will return a CompletableFuture object that is completed as soon as processing
can continue. This doesn't necessarily mean that processing/propagating has been completed (eg: when the FMUC
is configured to use master-master mode, a completed Future instance will be returned.

When FMUC is not active, this method will return a completed Future instance.

@param stanza the stanza to be propagated through FMUC.
@param sender the occupant data of the sender that is the original author of the stanza.
@return A future object that completes when the stanza can be propagated locally.
xmppserver/src/main/java/org/jivesoftware/openfire/muc/spi/FMUCHandler.java