[asterisk-dev] ARI events order

Matthew Jordan mjordan at digium.com
Thu Sep 6 09:18:04 CDT 2018


On Wed, Sep 5, 2018 at 5:23 PM Seán C. McCord <ulexus at gmail.com> wrote:

> As to the events should have a deterministic order or not, I cannot speak,
> but this is definitely normal behaviour.
>
>
> On Wed, Sep 5, 2018 at 12:22 PM Jean Aunis <jean.aunis at prescom.fr> wrote:
>
>> Hello,
>>
>> It looks like the ARI events ordering during channel destruction is not
>> deterministic. I noticed this for ChannelLeftBridge and ChannelDestroyed
>> events : given a channel is in a bridge and is hanged up, sometimes
>> ChannelLeftBridge is raised before ChannelDestroyed, sometimes it's the
>> contrary. Test conditions are exactly the same in both cases.
>>
>> Is this non-deterministic behaviour normal, or should it be considered as
>> a bug ?
>>
>> To my mind, ChannelDestroyed should always be the very last event raised
>> for a given channel. From a developper point of view, it would give a clear
>> indication that the resources associated to the channel can be freed.
>>
>> Regards
>>
> The events regarding a Channel entering and leaving a Bridge are
deterministic with respect to the Bridge's lifetime, but are not
deterministic with respect to the Channel's lifetime. While it's a bit
different, this is discussed somewhat on the AMI specification page:

https://wiki.asterisk.org/wiki/display/AST/AMI+v2+Specification#AMIv2Specification-Bridging

While AMI and ARI are two different APIs, both are built on top of a shared
internal abstraction layer inside Asterisk that determines that event
ordering. In the case of channels, channel event ordering is guaranteed
when those events are published to what is known as the 'channel' topic for
that channel. The act of entering / leaving a bridge is published to the
bridge's topic, which is technically independent of the channel's topic. As
such, the ordering of those events as they are presented to the AMI / ARI
topics is not guaranteed.

An example can be seen in publishing the bridge leave message:

void ast_bridge_publish_leave(struct ast_bridge *bridge, struct ast_channel
*chan)
{
    struct stasis_message *msg;

    if (ast_test_flag(&bridge->feature_flags, AST_BRIDGE_FLAG_INVISIBLE)) {
        return;
    }
    msg = ast_bridge_blob_create(ast_channel_left_bridge_type(), bridge,
chan, NULL);
    if (!msg) {
        return;
    }

    /* state first, then leave blob (opposite of enter, preserves nesting
of events) */
    bridge_publish_state_from_blob(bridge, stasis_message_data(msg));
    stasis_publish(ast_bridge_topic(bridge), msg);
    ao2_ref(msg, -1);
}

Note that we're publishing that message to the bridge topic -
ast_bridge_topic(bridge) - as opposed to the channel topic (which would be
ast_channel_topic(chan)). (To be pedantic, if you really wanted to preserve
event ordering for both the bridge and the channel's respective lifetimes,
you'd have to make a new aggregation topic for each channel / bridge and
publish their messages to those aggregation topics, but that's a lot of
overhead.)

You could argue that it *should* be ordered with respect to both the
channel and bridge's lifetime, but generally enforcing that ordering
imposes a penalty on the system, as it requires more synchronization. If
someone went down that path, it'd require some careful testing to ensure it
doesn't bog things down in some massive way.

-- 
Matthew Jordan
Digium, Inc. | CTO
445 Jan Davis Drive NW - Huntsville, AL 35806 - USA
Check us out at: http://digium.com & http://asterisk.org
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.digium.com/pipermail/asterisk-dev/attachments/20180906/6cd81d59/attachment.html>


More information about the asterisk-dev mailing list