diff --git a/src/include/switch_cpp.h b/src/include/switch_cpp.h index f4a0922e58..e9f5c29d92 100644 --- a/src/include/switch_cpp.h +++ b/src/include/switch_cpp.h @@ -312,7 +312,8 @@ SWITCH_DECLARE(bool) email(char *to, char *from, char *headers = NULL, char *bod int max_digits, int max_tries, int timeout, char *terminators, char *audio_files, char *bad_input_audio_files, - char *digits_regex, const char *var_name = NULL, int digit_timeout = 0); + char *digits_regex, const char *var_name = NULL, int digit_timeout = 0, + const char *transfer_on_failure = NULL); /** \brief Play a file that resides on disk into the channel * diff --git a/src/include/switch_ivr.h b/src/include/switch_ivr.h index 37940daf90..76ce542429 100644 --- a/src/include/switch_ivr.h +++ b/src/include/switch_ivr.h @@ -407,7 +407,8 @@ SWITCH_DECLARE(switch_status_t) switch_play_and_get_digits(switch_core_session_t const char *bad_input_audio_file, const char *var_name, char *digit_buffer, uint32_t digit_buffer_length, const char *digits_regex, - uint32_t digit_timeout); + uint32_t digit_timeout, + const char *transfer_on_failure); SWITCH_DECLARE(switch_status_t) switch_ivr_speak_text_handle(switch_core_session_t *session, switch_speech_handle_t *sh, diff --git a/src/mod/applications/mod_dptools/mod_dptools.c b/src/mod/applications/mod_dptools/mod_dptools.c index 8c260ddf7f..271421a9d3 100755 --- a/src/mod/applications/mod_dptools/mod_dptools.c +++ b/src/mod/applications/mod_dptools/mod_dptools.c @@ -2022,7 +2022,7 @@ SWITCH_STANDARD_APP(read_function) SWITCH_STANDARD_APP(play_and_get_digits_function) { char *mydata; - char *argv[10] = { 0 }; + char *argv[11] = { 0 }; int argc; int32_t min_digits = 0; int32_t max_digits = 0; @@ -2035,6 +2035,7 @@ SWITCH_STANDARD_APP(play_and_get_digits_function) const char *var_name = NULL; const char *valid_terminators = NULL; const char *digits_regex = NULL; + const char *transfer_on_failure = NULL; if (!zstr(data) && (mydata = switch_core_session_strdup(session, data))) { argc = switch_separate_string(mydata, ' ', argv, (sizeof(argv) / sizeof(argv[0]))); @@ -2084,6 +2085,10 @@ SWITCH_STANDARD_APP(play_and_get_digits_function) } } + if (argc > 10) { + transfer_on_failure = argv[10]; + switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_DEBUG, "Transfer on failure = [%s].\n", transfer_on_failure); + } if (min_digits <= 1) { min_digits = 1; @@ -2102,7 +2107,8 @@ SWITCH_STANDARD_APP(play_and_get_digits_function) } switch_play_and_get_digits(session, min_digits, max_digits, max_tries, timeout, valid_terminators, - prompt_audio_file, bad_input_audio_file, var_name, digit_buffer, sizeof(digit_buffer), digits_regex, digit_timeout); + prompt_audio_file, bad_input_audio_file, var_name, digit_buffer, sizeof(digit_buffer), + digits_regex, digit_timeout, transfer_on_failure); } #define SAY_SYNTAX "[:] [] " @@ -3904,7 +3910,7 @@ SWITCH_MODULE_LOAD_FUNCTION(mod_dptools_load) " ", SAF_NONE); SWITCH_ADD_APP(app_interface, "play_and_get_digits", "Play and get Digits", "Play and get Digits", play_and_get_digits_function, - " []", SAF_NONE); + "\n\t [] [' [failure_dp [failure_context]]']", SAF_NONE); SWITCH_ADD_APP(app_interface, "stop_record_session", "Stop Record Session", STOP_SESS_REC_DESC, stop_record_session_function, "", SAF_NONE); SWITCH_ADD_APP(app_interface, "record_session", "Record Session", SESS_REC_DESC, record_session_function, " [+]", SAF_MEDIA_TAP); SWITCH_ADD_APP(app_interface, "record", "Record File", "Record a file from the channels input", record_function, diff --git a/src/switch_cpp.cpp b/src/switch_cpp.cpp index 3ffc6a3a9d..044612792b 100644 --- a/src/switch_cpp.cpp +++ b/src/switch_cpp.cpp @@ -825,7 +825,8 @@ SWITCH_DECLARE(char *) CoreSession::playAndGetDigits(int min_digits, char *bad_input_audio_files, char *digits_regex, const char *var_name, - int digit_timeout) + int digit_timeout, + const char *transfer_on_failure) { switch_status_t status; sanity_check((char *)""); @@ -844,7 +845,8 @@ SWITCH_DECLARE(char *) CoreSession::playAndGetDigits(int min_digits, dtmf_buf, sizeof(dtmf_buf), digits_regex, - (uint32_t) digit_timeout); + (uint32_t) digit_timeout, + transfer_on_failure); end_allow_threads(); return dtmf_buf; diff --git a/src/switch_ivr_play_say.c b/src/switch_ivr_play_say.c index c5200d0e0e..f941ff85c8 100644 --- a/src/switch_ivr_play_say.c +++ b/src/switch_ivr_play_say.c @@ -1981,7 +1981,8 @@ SWITCH_DECLARE(switch_status_t) switch_play_and_get_digits(switch_core_session_t char *digit_buffer, uint32_t digit_buffer_length, const char *digits_regex, - uint32_t digit_timeout) + uint32_t digit_timeout, + const char *transfer_on_failure) { switch_channel_t *channel = switch_core_session_get_channel(session); @@ -2031,7 +2032,45 @@ SWITCH_DECLARE(switch_status_t) switch_play_and_get_digits(switch_core_session_t } memset(digit_buffer, 0, digit_buffer_length); - return SWITCH_STATUS_FALSE; + + /* If we get here then check for transfer-on-failure ext/dp/context */ + /* split this arg on spaces to get ext, dp, and context */ + + if (!zstr(transfer_on_failure)) { + const char *failure_ext = NULL; + const char *failure_dialplan = NULL; + const char *failure_context = NULL; + char *target[4]; + char *mydata = switch_core_session_strdup(session, transfer_on_failure); + int argc; + + argc = switch_separate_string(mydata, ' ', target, (sizeof(target) / sizeof(target[0]))); + + if ( argc < 1 ) { + switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_ERROR,"Bad target for PAGD failure: [%s]\n", transfer_on_failure); + return SWITCH_STATUS_FALSE; + } + + if ( argc > 0 ) { + failure_ext = target[0]; + } + + if ( argc > 1 ) { + failure_dialplan = target[1]; + } + + if ( argc > 2 ) { + failure_context = target[2]; + } + + switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_WARNING, + "PAGD failure! Transfer to: %s / %s / %s\n", failure_ext, failure_dialplan, failure_context); + + switch_ivr_session_transfer(session,failure_ext, failure_dialplan, failure_context); + return SWITCH_STATUS_FALSE; + } + + return SWITCH_STATUS_FALSE; } SWITCH_DECLARE(switch_status_t) switch_ivr_speak_text_handle(switch_core_session_t *session,