diff options
author | Kinsey Moore <kmoore@digium.com> | 2013-05-10 13:13:06 +0000 |
---|---|---|
committer | Kinsey Moore <kmoore@digium.com> | 2013-05-10 13:13:06 +0000 |
commit | 7ce05bfb9b5f06c18451e37bb5b91cd543d6ba84 (patch) | |
tree | b4e833909ec2ba776d39848ecf8d28f74b341424 /main/manager_channels.c | |
parent | 2cfedc12adf64cc24e855bd9ea30df3aa1b759ce (diff) |
Add channel events for res_stasis apps
This change adds a framework in res_stasis for handling events from
channel topics. JSON event generation and validation code is created
from event documentation in rest-api/api-docs/events.json to assist in
JSON event generation, ensure consistency, and ensure that accurate
documentation is available for ALL events that are received by
res_stasis applications.
The userevent application has been refactored along with the code that
handles userevent channel blob events to pass the headers as key/value
pairs in the JSON blob. As a side-effect, app_userevent now handles
duplicate keys by overwriting the previous value.
Review: https://reviewboard.asterisk.org/r/2428/
(closes issue ASTERISK-21180)
Patch-By: Kinsey Moore <kmoore@digium.com>
git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@388275 65c4cc65-6c06-0410-ace0-fbb531ad65f3
Diffstat (limited to 'main/manager_channels.c')
-rw-r--r-- | main/manager_channels.c | 100 |
1 files changed, 49 insertions, 51 deletions
diff --git a/main/manager_channels.c b/main/manager_channels.c index 804bca663..63380a762 100644 --- a/main/manager_channels.c +++ b/main/manager_channels.c @@ -402,34 +402,6 @@ static struct snapshot_manager_event *channel_state_change( return NULL; } -/*! - * \brief Compares the context, exten and priority of two snapshots. - * \param old_snapshot Old snapshot - * \param new_snapshot New snapshot - * \return True (non-zero) if context, exten or priority are identical. - * \return False (zero) if context, exten and priority changed. - */ -static inline int cep_equal( - const struct ast_channel_snapshot *old_snapshot, - const struct ast_channel_snapshot *new_snapshot) -{ - ast_assert(old_snapshot != NULL); - ast_assert(new_snapshot != NULL); - - /* We actually get some snapshots with CEP set, but before the - * application is set. Since empty application is invalid, we treat - * setting the application from nothing as a CEP change. - */ - if (ast_strlen_zero(old_snapshot->appl) && - !ast_strlen_zero(new_snapshot->appl)) { - return 0; - } - - return old_snapshot->priority == new_snapshot->priority && - strcmp(old_snapshot->context, new_snapshot->context) == 0 && - strcmp(old_snapshot->exten, new_snapshot->exten) == 0; -} - static struct snapshot_manager_event *channel_newexten( struct ast_channel_snapshot *old_snapshot, struct ast_channel_snapshot *new_snapshot) @@ -444,7 +416,7 @@ static struct snapshot_manager_event *channel_newexten( return NULL; } - if (old_snapshot && cep_equal(old_snapshot, new_snapshot)) { + if (old_snapshot && ast_channel_snapshot_cep_equal(old_snapshot, new_snapshot)) { return NULL; } @@ -459,23 +431,6 @@ static struct snapshot_manager_event *channel_newexten( new_snapshot->data); } -/*! - * \brief Compares the callerid info of two snapshots. - * \param old_snapshot Old snapshot - * \param new_snapshot New snapshot - * \return True (non-zero) if callerid are identical. - * \return False (zero) if callerid changed. - */ -static inline int caller_id_equal( - const struct ast_channel_snapshot *old_snapshot, - const struct ast_channel_snapshot *new_snapshot) -{ - ast_assert(old_snapshot != NULL); - ast_assert(new_snapshot != NULL); - return strcmp(old_snapshot->caller_number, new_snapshot->caller_number) == 0 && - strcmp(old_snapshot->caller_name, new_snapshot->caller_name) == 0; -} - static struct snapshot_manager_event *channel_new_callerid( struct ast_channel_snapshot *old_snapshot, struct ast_channel_snapshot *new_snapshot) @@ -485,7 +440,7 @@ static struct snapshot_manager_event *channel_new_callerid( return NULL; } - if (caller_id_equal(old_snapshot, new_snapshot)) { + if (ast_channel_snapshot_caller_id_equal(old_snapshot, new_snapshot)) { return NULL; } @@ -587,19 +542,62 @@ static void channel_varset_cb(void *data, struct stasis_subscription *sub, variable, value); } +/*! + * \brief Callback used to determine whether a key should be skipped when converting a JSON object to a manager blob + * \param key Key from JSON blob to be evaluated + * \retval non-zero if the key should be excluded + * \retval zero if the key should not be excluded + */ +typedef int (*key_exclusion_cb)(const char *key); + +static struct ast_str *manager_str_from_json_object(struct ast_json *blob, key_exclusion_cb exclusion_cb) +{ + struct ast_str *output_str = ast_str_create(32); + struct ast_json_iter *blob_iter = ast_json_object_iter(blob); + if (!output_str || !blob_iter) { + return NULL; + } + + do { + const char *key = ast_json_object_iter_key(blob_iter); + const char *value = ast_json_string_get(ast_json_object_iter_value(blob_iter)); + if (exclusion_cb && exclusion_cb(key)) { + continue; + } + + ast_str_append(&output_str, 0, "%s: %s\r\n", key, value); + if (!output_str) { + return NULL; + } + } while ((blob_iter = ast_json_object_iter_next(blob, blob_iter))); + + return output_str; +} + +static int userevent_exclusion_cb(const char *key) +{ + if (!strcmp("type", key)) { + return 1; + } + if (!strcmp("eventname", key)) { + return 1; + } + return 0; +} + static void channel_user_event_cb(void *data, struct stasis_subscription *sub, struct stasis_topic *topic, struct stasis_message *message) { struct ast_channel_blob *obj = stasis_message_data(message); RAII_VAR(struct ast_str *, channel_event_string, NULL, ast_free); + RAII_VAR(struct ast_str *, body, NULL, ast_free); const char *eventname; - const char *body; eventname = ast_json_string_get(ast_json_object_get(obj->blob, "eventname")); - body = ast_json_string_get(ast_json_object_get(obj->blob, "body")); + body = manager_str_from_json_object(obj->blob, userevent_exclusion_cb); channel_event_string = ast_manager_build_channel_state_string(obj->snapshot); - if (!channel_event_string) { + if (!channel_event_string || !body) { return; } @@ -621,7 +619,7 @@ static void channel_user_event_cb(void *data, struct stasis_subscription *sub, "%s" "UserEvent: %s\r\n" "%s", - ast_str_buffer(channel_event_string), eventname, body); + ast_str_buffer(channel_event_string), eventname, ast_str_buffer(body)); } static void channel_hangup_request_cb(void *data, |