Skip to content
Snippets Groups Projects
Commit b5c98d64 authored by David Vossel's avatar David Vossel
Browse files

adds 'p' option to PickupChan

The 'p' option allows the PickupChan app to pickup
a ringing phone by looking for the first match to a
partial channel name rather than requiring a full match.

(closes issue #16613)
Reported by: syspert
Patches:
      pickipbycallid.patch uploaded by syspert (license 938)
      pickupbycallerid_v2.patch uploaded by dvossel (license 671)
Tested by: dvossel, syspert




git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@250141 65c4cc65-6c06-0410-ace0-fbb531ad65f3
parent 491ea82b
No related branches found
No related tags found
No related merge requests found
......@@ -72,6 +72,8 @@ MGCP Changes
Applications
------------
* Added 'p' option to PickupChan() to allow for picking up channel by the first
match to a partial channel name.
* Added "ready" option to QUEUE_MEMBER counting to count free agents who's wrap-up
timeout has expired.
* Added 'R' option to app_queue. This option stops moh and indicates ringing
......
......@@ -79,6 +79,13 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
<syntax>
<parameter name="channel" required="true" />
<parameter name="channel2" multiple="true" />
<parameter name="options" required="false">
<optionlist>
<option name="p">
<para>Channel name specified partial name. Used when find channel by callid.</para>
</option>
</optionlist>
</parameter>
</syntax>
<description>
<para>This will pickup a specified <replaceable>channel</replaceable> if ringing.</para>
......@@ -303,24 +310,71 @@ static int pickup_exec(struct ast_channel *chan, const char *data)
return res;
}
/* Find channel for pick up specified by partial channel name */
static int find_by_part(void *obj, void *arg, void *data, int flags)
{
struct ast_channel *c = obj;
const char *part = data;
int res = 0;
int len = strlen(part);
ast_channel_lock(c);
if (len <= strlen(c->name)) {
res = !(strncmp(c->name, part, len)) && (can_pickup(c));
}
ast_channel_unlock(c);
return res ? CMP_MATCH | CMP_STOP : 0;
}
/* Attempt to pick up specified by partial channel name */
static int pickup_by_part(struct ast_channel *chan, const char *part)
{
struct ast_channel *target;
int res = -1;
if ((target = ast_channel_callback(find_by_part, NULL, (char *) part, 0))) {
ast_channel_lock(target);
res = pickup_do(chan, target);
ast_channel_unlock(target);
target = ast_channel_unref(target);
}
return res;
}
/* application entry point for PickupChan() */
static int pickupchan_exec(struct ast_channel *chan, const char *data)
{
int res = 0;
char *tmp = ast_strdupa(data);
int partial_pickup = 0;
char *pickup = NULL;
if (ast_strlen_zero(data)) {
char *parse = ast_strdupa(data);
AST_DECLARE_APP_ARGS(args,
AST_APP_ARG(channel);
AST_APP_ARG(options);
);
AST_STANDARD_APP_ARGS(args, parse);
if (ast_strlen_zero(args.channel)) {
ast_log(LOG_WARNING, "PickupChan requires an argument (channel)!\n");
return -1;
return -1;
}
if (!ast_strlen_zero(args.options) && strchr(args.options, 'p')) {
partial_pickup = 1;
}
/* Parse channel */
while (!ast_strlen_zero(tmp) && (pickup = strsep(&tmp, "&"))) {
while (!ast_strlen_zero(args.channel) && (pickup = strsep(&args.channel, "&"))) {
if (!strncasecmp(chan->name, pickup, strlen(pickup))) {
ast_log(LOG_NOTICE, "Cannot pickup your own channel %s.\n", pickup);
} else {
if (!pickup_by_channel(chan, pickup)) {
if (partial_pickup) {
if (!pickup_by_part(chan, pickup)) {
break;
}
} else if (!pickup_by_channel(chan, pickup)) {
break;
}
ast_log(LOG_NOTICE, "No target channel found for %s.\n", pickup);
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment