[Asterisk-code-review] app queue: Add option for predial handlers on caller and cal... (asterisk[master])

Joshua Colp asteriskteam at digium.com
Wed Jun 27 05:37:36 CDT 2018


Joshua Colp has submitted this change and it was merged. ( https://gerrit.asterisk.org/9180 )

Change subject: app_queue: Add option for predial handlers on caller and callee channels
......................................................................

app_queue: Add option for predial handlers on caller and callee channels

Add predial handler support to app_queue.  app_dial (ASTERISK_19548) and
app_originate (ASTERISK_26587) have the ability to execute predial
handlers on caller and callee channels.  This patch adds predial handlers
to app_queue and uses the same options as Dial and Originate (b and B).
The caller routine gets executed when the caller first enters the queue.
The callee routine gets executed for each queue member when they are about
to be called.

ASTERISK-27912

Change-Id: I5acf5c32587ee008658d12e8a8049eb8fa4d0f24
---
M CHANGES
M apps/app_queue.c
2 files changed, 76 insertions(+), 1 deletion(-)

Approvals:
  Richard Mudgett: Looks good to me, but someone else must approve
  Joshua Colp: Looks good to me, approved; Approved for Submit



diff --git a/CHANGES b/CHANGES
index e969d85..5cfad79 100644
--- a/CHANGES
+++ b/CHANGES
@@ -67,6 +67,10 @@
    When set the wrapuptime on the member is used instead of the wrapuptime
    defined for the queue itself.
 
+ * Added predial handler support for caller and callee channels with the
+   B and b options respectively.  This is similar to the predial support
+   in app_dial.
+
 res_config_sqlite
 ------------------
  * The res_config_sqlite module is now deprecated, users should migrate to the
diff --git a/apps/app_queue.c b/apps/app_queue.c
index 3047648..052d528 100644
--- a/apps/app_queue.c
+++ b/apps/app_queue.c
@@ -133,6 +133,27 @@
 			<parameter name="queuename" required="true" />
 			<parameter name="options">
 				<optionlist>
+					<option name="b" argsep="^">
+						<para>Before initiating an outgoing call, <literal>Gosub</literal> to the specified
+						location using the newly created channel.  The <literal>Gosub</literal> will be
+						executed for each destination channel.</para>
+						<argument name="context" required="false" />
+						<argument name="exten" required="false" />
+						<argument name="priority" required="true" hasparams="optional" argsep="^">
+							<argument name="arg1" multiple="true" required="true" />
+							<argument name="argN" />
+						</argument>
+					</option>
+					<option name="B" argsep="^">
+						<para>Before initiating the outgoing call(s), <literal>Gosub</literal> to the
+						specified location using the current channel.</para>
+						<argument name="context" required="false" />
+						<argument name="exten" required="false" />
+						<argument name="priority" required="true" hasparams="optional" argsep="^">
+							<argument name="arg1" multiple="true" required="true" />
+							<argument name="argN" />
+						</argument>
+					</option>
 					<option name="C">
 						<para>Mark all calls as "answered elsewhere" when cancelled.</para>
 					</option>
@@ -1325,15 +1346,21 @@
 	OPT_CALLER_AUTOMIXMON =      (1 << 16),
 	OPT_CALLEE_AUTOMON =         (1 << 17),
 	OPT_CALLER_AUTOMON =         (1 << 18),
+	OPT_PREDIAL_CALLEE =         (1 << 19),
+	OPT_PREDIAL_CALLER =         (1 << 20),
 };
 
 enum {
 	OPT_ARG_CALLEE_GO_ON = 0,
+	OPT_ARG_PREDIAL_CALLEE,
+	OPT_ARG_PREDIAL_CALLER,
 	/* note: this entry _MUST_ be the last one in the enum */
 	OPT_ARG_ARRAY_SIZE
 };
 
 AST_APP_OPTIONS(queue_exec_options, BEGIN_OPTIONS
+	AST_APP_OPTION_ARG('b', OPT_PREDIAL_CALLEE, OPT_ARG_PREDIAL_CALLEE),
+	AST_APP_OPTION_ARG('B', OPT_PREDIAL_CALLER, OPT_ARG_PREDIAL_CALLER),
 	AST_APP_OPTION('C', OPT_MARK_AS_ANSWERED),
 	AST_APP_OPTION('c', OPT_GO_ON),
 	AST_APP_OPTION('d', OPT_DATA_QUALITY),
@@ -1545,6 +1572,7 @@
 	char announce[PATH_MAX];               /*!< Announcement to play for member when call is answered */
 	char context[AST_MAX_CONTEXT];         /*!< Context when user exits queue */
 	char digits[AST_MAX_EXTENSION];        /*!< Digits entered while in queue */
+	const char *predial_callee;            /*!< Gosub app arguments for outgoing calls.  NULL if not supplied. */
 	int valid_digits;                      /*!< Digits entered correspond to valid extension. Exited */
 	int pos;                               /*!< Where we are in the queue */
 	int prio;                              /*!< Our priority */
@@ -4559,6 +4587,11 @@
 	ast_channel_unlock(tmp->chan);
 	ast_channel_unlock(qe->chan);
 
+	/* PREDIAL: Run gosub on the callee's channel */
+	if (qe->predial_callee) {
+		ast_pre_call(tmp->chan, qe->predial_callee);
+	}
+
 	/* Place the call, but don't wait on the answer */
 	if ((res = ast_call(tmp->chan, location, 0))) {
 		/* Again, keep going even if there's an error */
@@ -4615,6 +4648,16 @@
 static int ring_one(struct queue_ent *qe, struct callattempt *outgoing, int *busies)
 {
 	int ret = 0;
+	struct callattempt *cur;
+
+	if (qe->predial_callee) {
+		ast_autoservice_start(qe->chan);
+		for (cur = outgoing; cur; cur = cur->q_next) {
+			if (cur->stillgoing && cur->chan) {
+				ast_autoservice_start(cur->chan);
+			}
+		}
+	}
 
 	while (ret == 0) {
 		struct callattempt *best = find_best(outgoing);
@@ -4623,18 +4666,23 @@
 			break;
 		}
 		if (qe->parent->strategy == QUEUE_STRATEGY_RINGALL) {
-			struct callattempt *cur;
 			/* Ring everyone who shares this best metric (for ringall) */
 			for (cur = outgoing; cur; cur = cur->q_next) {
 				if (cur->stillgoing && !cur->chan && cur->metric <= best->metric) {
 					ast_debug(1, "(Parallel) Trying '%s' with metric %d\n", cur->interface, cur->metric);
 					ret |= ring_entry(qe, cur, busies);
+					if (qe->predial_callee && cur->chan) {
+						ast_autoservice_start(cur->chan);
+					}
 				}
 			}
 		} else {
 			/* Ring just the best channel */
 			ast_debug(1, "Trying '%s' with metric %d\n", best->interface, best->metric);
 			ret = ring_entry(qe, best, busies);
+			if (qe->predial_callee && cur->chan) {
+				ast_autoservice_start(best->chan);
+			}
 		}
 
 		/* If we have timed out, break out */
@@ -4643,6 +4691,14 @@
 			ret = 0;
 			break;
 		}
+	}
+	if (qe->predial_callee) {
+		for (cur = outgoing; cur; cur = cur->q_next) {
+			if (cur->stillgoing && cur->chan) {
+				ast_autoservice_stop(cur->chan);
+			}
+		}
+		ast_autoservice_stop(qe->chan);
 	}
 
 	return ret;
@@ -8270,6 +8326,21 @@
 		S_OR(args.url, ""),
 		S_COR(ast_channel_caller(chan)->id.number.valid, ast_channel_caller(chan)->id.number.str, ""),
 		qe.opos);
+
+	/* PREDIAL: Preprocess any callee gosub arguments. */
+	if (ast_test_flag(&opts, OPT_PREDIAL_CALLEE)
+		&& !ast_strlen_zero(opt_args[OPT_ARG_PREDIAL_CALLEE])) {
+		ast_replace_subargument_delimiter(opt_args[OPT_ARG_PREDIAL_CALLEE]);
+		qe.predial_callee = opt_args[OPT_ARG_PREDIAL_CALLEE];
+	}
+
+	/* PREDIAL: Run gosub on the caller's channel */
+	if (ast_test_flag(&opts, OPT_PREDIAL_CALLER)
+		&& !ast_strlen_zero(opt_args[OPT_ARG_PREDIAL_CALLER])) {
+		ast_replace_subargument_delimiter(opt_args[OPT_ARG_PREDIAL_CALLER]);
+		ast_app_exec_sub(NULL, chan, opt_args[OPT_ARG_PREDIAL_CALLER], 0);
+	}
+
 	copy_rules(&qe, args.rule);
 	qe.pr = AST_LIST_FIRST(&qe.qe_rules);
 check_turns:

-- 
To view, visit https://gerrit.asterisk.org/9180
To unsubscribe, visit https://gerrit.asterisk.org/settings

Gerrit-Project: asterisk
Gerrit-Branch: master
Gerrit-MessageType: merged
Gerrit-Change-Id: I5acf5c32587ee008658d12e8a8049eb8fa4d0f24
Gerrit-Change-Number: 9180
Gerrit-PatchSet: 4
Gerrit-Owner: Kristian Høgh <kfh at uni-tel.dk>
Gerrit-Reviewer: Jenkins2
Gerrit-Reviewer: Joshua Colp <jcolp at digium.com>
Gerrit-Reviewer: Richard Mudgett <rmudgett at digium.com>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.digium.com/pipermail/asterisk-code-review/attachments/20180627/2598b8f2/attachment.html>


More information about the asterisk-code-review mailing list