* implement originate() and bridge() methods in CoreSession.  
* api changes for originate() : no longer passes 11 arguments


git-svn-id: http://svn.freeswitch.org/svn/freeswitch/trunk@5410 d0543943-73ff-0310-b7d9-9358b9ac24b2
This commit is contained in:
Michael Jerris
2007-06-20 08:56:34 +00:00
parent b7910ac8f9
commit e028f2691c
7 changed files with 758 additions and 557 deletions
+24 -19
View File
@@ -53,32 +53,32 @@ console_clean_log = _freeswitch.console_clean_log
api_execute = _freeswitch.api_execute
api_reply_delete = _freeswitch.api_reply_delete
process_callback_result = _freeswitch.process_callback_result
class input_callback_state(_object):
class input_callback_state_t(_object):
__swig_setmethods__ = {}
__setattr__ = lambda self, name, value: _swig_setattr(self, input_callback_state, name, value)
__setattr__ = lambda self, name, value: _swig_setattr(self, input_callback_state_t, name, value)
__swig_getmethods__ = {}
__getattr__ = lambda self, name: _swig_getattr(self, input_callback_state, name)
__getattr__ = lambda self, name: _swig_getattr(self, input_callback_state_t, name)
__repr__ = _swig_repr
__swig_setmethods__["function"] = _freeswitch.input_callback_state_function_set
__swig_getmethods__["function"] = _freeswitch.input_callback_state_function_get
if _newclass:function = _swig_property(_freeswitch.input_callback_state_function_get, _freeswitch.input_callback_state_function_set)
__swig_setmethods__["threadState"] = _freeswitch.input_callback_state_threadState_set
__swig_getmethods__["threadState"] = _freeswitch.input_callback_state_threadState_get
if _newclass:threadState = _swig_property(_freeswitch.input_callback_state_threadState_get, _freeswitch.input_callback_state_threadState_set)
__swig_setmethods__["extra"] = _freeswitch.input_callback_state_extra_set
__swig_getmethods__["extra"] = _freeswitch.input_callback_state_extra_get
if _newclass:extra = _swig_property(_freeswitch.input_callback_state_extra_get, _freeswitch.input_callback_state_extra_set)
__swig_setmethods__["funcargs"] = _freeswitch.input_callback_state_funcargs_set
__swig_getmethods__["funcargs"] = _freeswitch.input_callback_state_funcargs_get
if _newclass:funcargs = _swig_property(_freeswitch.input_callback_state_funcargs_get, _freeswitch.input_callback_state_funcargs_set)
__swig_setmethods__["function"] = _freeswitch.input_callback_state_t_function_set
__swig_getmethods__["function"] = _freeswitch.input_callback_state_t_function_get
if _newclass:function = _swig_property(_freeswitch.input_callback_state_t_function_get, _freeswitch.input_callback_state_t_function_set)
__swig_setmethods__["threadState"] = _freeswitch.input_callback_state_t_threadState_set
__swig_getmethods__["threadState"] = _freeswitch.input_callback_state_t_threadState_get
if _newclass:threadState = _swig_property(_freeswitch.input_callback_state_t_threadState_get, _freeswitch.input_callback_state_t_threadState_set)
__swig_setmethods__["extra"] = _freeswitch.input_callback_state_t_extra_set
__swig_getmethods__["extra"] = _freeswitch.input_callback_state_t_extra_get
if _newclass:extra = _swig_property(_freeswitch.input_callback_state_t_extra_get, _freeswitch.input_callback_state_t_extra_set)
__swig_setmethods__["funcargs"] = _freeswitch.input_callback_state_t_funcargs_set
__swig_getmethods__["funcargs"] = _freeswitch.input_callback_state_t_funcargs_get
if _newclass:funcargs = _swig_property(_freeswitch.input_callback_state_t_funcargs_get, _freeswitch.input_callback_state_t_funcargs_set)
def __init__(self, *args):
this = _freeswitch.new_input_callback_state(*args)
this = _freeswitch.new_input_callback_state_t(*args)
try: self.this.append(this)
except: self.this = this
__swig_destroy__ = _freeswitch.delete_input_callback_state
__swig_destroy__ = _freeswitch.delete_input_callback_state_t
__del__ = lambda self : None;
input_callback_state_swigregister = _freeswitch.input_callback_state_swigregister
input_callback_state_swigregister(input_callback_state)
input_callback_state_t_swigregister = _freeswitch.input_callback_state_t_swigregister
input_callback_state_t_swigregister(input_callback_state_t)
class CoreSession(_object):
__swig_setmethods__ = {}
@@ -106,6 +106,8 @@ class CoreSession(_object):
def hangup(*args): return _freeswitch.CoreSession_hangup(*args)
def setVariable(*args): return _freeswitch.CoreSession_setVariable(*args)
def getVariable(*args): return _freeswitch.CoreSession_getVariable(*args)
def setCallerData(*args): return _freeswitch.CoreSession_setCallerData(*args)
def originate(*args): return _freeswitch.CoreSession_originate(*args)
def playFile(*args): return _freeswitch.CoreSession_playFile(*args)
def setDTMFCallback(*args): return _freeswitch.CoreSession_setDTMFCallback(*args)
def speak(*args): return _freeswitch.CoreSession_speak(*args)
@@ -118,9 +120,12 @@ class CoreSession(_object):
def execute(*args): return _freeswitch.CoreSession_execute(*args)
def begin_allow_threads(*args): return _freeswitch.CoreSession_begin_allow_threads(*args)
def end_allow_threads(*args): return _freeswitch.CoreSession_end_allow_threads(*args)
def get_uuid(*args): return _freeswitch.CoreSession_get_uuid(*args)
def get_cb_args(*args): return _freeswitch.CoreSession_get_cb_args(*args)
CoreSession_swigregister = _freeswitch.CoreSession_swigregister
CoreSession_swigregister(CoreSession)
bridge = _freeswitch.bridge
PythonDTMFCallback = _freeswitch.PythonDTMFCallback
class PySession(CoreSession):
__swig_setmethods__ = {}
@@ -1,6 +1,22 @@
#include "freeswitch_python.h"
#define sanity_check(x) do { if (!session) { switch_log_printf(SWITCH_CHANNEL_LOG,SWITCH_LOG_ERROR, "session is not initalized\n"); return x;}} while(0)
#define init_vars() do { caller_profile.source = "mod_python"; } while(0)
PySession::PySession() : CoreSession()
{
init_vars();
}
PySession::PySession(char *uuid) : CoreSession(uuid)
{
init_vars();
}
PySession::PySession(switch_core_session_t *new_session) : CoreSession(new_session)
{
init_vars();
}
void PySession::setDTMFCallback(PyObject *pyfunc, char *funcargs)
@@ -34,15 +50,16 @@ void PySession::setDTMFCallback(PyObject *pyfunc, char *funcargs)
void PySession::begin_allow_threads(void) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "PySession::begin_allow_threads() called\n");
// swap out threadstate and store in instance variable
threadState = (void *) PyEval_SaveThread();
cb_state.threadState = threadState;
// cb_state.extra = &fh;
args.buf = &cb_state;
ap = &args;
}
void PySession::end_allow_threads(void) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "PySession::end_allow_threads() called\n");
// swap in threadstate from instance variable saved earlier
PyEval_RestoreThread(((PyThreadState *)threadState));
}
@@ -52,4 +69,88 @@ PySession::~PySession() {
}
/* ----- functions not bound to PySession instance ------ */
switch_status_t PythonDTMFCallback(switch_core_session_t *session,
void *input,
switch_input_type_t itype,
void *buf,
unsigned int buflen)
{
PyObject *func, *arglist;
PyObject *result;
char *resultStr;
char *funcargs;
input_callback_state_t *cb_state;
switch_file_handle_t *fh = NULL;
PyThreadState *threadState = NULL;
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "PythonDTMFCallback\n");
if (!buf) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "buf pointer is null");
return SWITCH_STATUS_FALSE;
}
cb_state = (input_callback_state *) buf;
func = (PyObject *) cb_state->function;
if (!func) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "cb_state->function is null\n");
return SWITCH_STATUS_FALSE;
}
else {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "cb_state->function is NOT null\n");
}
if (!PyCallable_Check(func)) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "function not callable\n");
return SWITCH_STATUS_FALSE;
}
funcargs = (char *) cb_state->funcargs;
arglist = Py_BuildValue("(sis)", input, itype, funcargs);
if (!arglist) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "error building arglist");
return SWITCH_STATUS_FALSE;
}
threadState = (PyThreadState *) cb_state->threadState;
if (!threadState) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "error, invalid threadstate\n");
return SWITCH_STATUS_FALSE;
}
else {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "restoring threadstate: %p\n", threadState);
}
PyEval_RestoreThread(threadState); // nasty stuff happens when py interp has no thread state
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "restored threadstate, calling python function: %p\n", func);
result = PyEval_CallObject(func, arglist);
threadState = PyEval_SaveThread();
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "called python function\n");
Py_DECREF(arglist); // Trash arglist
if (result && result != Py_None) {
resultStr = (char *) PyString_AsString(result);
Py_XDECREF(result);
return process_callback_result(resultStr, cb_state, session);
}
else {
return SWITCH_STATUS_FALSE;
}
}
@@ -14,12 +14,12 @@ extern "C" {
// declaration for function that is defined in mod_python.i
extern switch_status_t PythonDTMFCallback(switch_core_session *session,
void *input,
switch_input_type_t itype,
void *buf,
unsigned int buflen);
switch_status_t PythonDTMFCallback(switch_core_session *session,
void *input,
switch_input_type_t itype,
void *buf,
unsigned int buflen);
void console_log(char *level_str, char *msg);
void console_clean_log(char *msg);
@@ -30,8 +30,9 @@ class PySession : public CoreSession {
private:
void *threadState;
public:
PySession(char *uuid) : CoreSession(uuid) {}
PySession(switch_core_session_t *session) : CoreSession(session) {}
PySession();
PySession(char *uuid);
PySession(switch_core_session_t *session);
~PySession();
void setDTMFCallback(PyObject *pyfunc, char *funcargs);
void begin_allow_threads();
@@ -39,6 +40,7 @@ class PySession : public CoreSession {
};
#ifdef __cplusplus
}
#endif
+8 -205
View File
@@ -1,218 +1,21 @@
%module freeswitch
%include "cstring.i"
%cstring_bounded_mutable(char *dtmf_buf, 128);
%cstring_bounded_mutable(char *terminator, 8);
/** insert the following includes into generated code so it compiles */
%{
#include "switch_cpp.h"
#include "freeswitch_python.h"
%}
/**
* tell swig to grok everything defined in these header files and
* build all sorts of c wrappers and python shadows of the c wrappers.
*/
%include switch_cpp.h
%include freeswitch_python.h
%{
/** hmm .. dunno why this is here */
%cstring_bounded_mutable(char *dtmf_buf, 128);
%cstring_bounded_mutable(char *terminator, 8);
switch_status_t PythonDTMFCallback(switch_core_session_t *session,
void *input,
switch_input_type_t itype,
void *buf,
unsigned int buflen)
{
PyObject *func, *arglist;
PyObject *result;
char *resultStr;
char *funcargs;
struct input_callback_state *cb_state;
switch_file_handle_t *fh = NULL;
PyThreadState *threadState = NULL;
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "PythonDTMFCallback\n");
if (!buf) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "buf pointer is null");
return SWITCH_STATUS_FALSE;
}
cb_state = (input_callback_state *) buf;
func = (PyObject *) cb_state->function;
if (!func) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "cb_state->function is null\n");
return SWITCH_STATUS_FALSE;
}
else {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "cb_state->function is NOT null\n");
}
if (!PyCallable_Check(func)) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "function not callable\n");
return SWITCH_STATUS_FALSE;
}
funcargs = (char *) cb_state->funcargs;
arglist = Py_BuildValue("(sis)", input, itype, funcargs);
if (!arglist) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "error building arglist");
return SWITCH_STATUS_FALSE;
}
threadState = (PyThreadState *) cb_state->threadState;
if (!threadState) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "error, invalid threadstate\n");
return SWITCH_STATUS_FALSE;
}
else {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "restoring threadstate: %p\n", threadState);
}
PyEval_RestoreThread(threadState); // nasty stuff happens when py interp has no thread state
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "restored threadstate, calling python function: %p\n", func);
result = PyEval_CallObject(func, arglist);
threadState = PyEval_SaveThread();
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "called python function\n");
Py_DECREF(arglist); // Trash arglist
if (result && result != Py_None) {
resultStr = (char *) PyString_AsString(result);
Py_XDECREF(result);
return process_callback_result(resultStr, cb_state, session);
}
else {
return SWITCH_STATUS_FALSE;
}
}
switch_status_t process_callback_result(char *ret,
struct input_callback_state *cb_state,
switch_core_session_t *session)
{
switch_file_handle_t *fh = NULL;
fh = (switch_file_handle_t *) cb_state->extra;
if (!fh) {
return SWITCH_STATUS_FALSE;
}
if (!ret) {
return SWITCH_STATUS_FALSE;
}
if (!strncasecmp(ret, "speed", 4)) {
char *p;
if ((p = strchr(ret, ':'))) {
p++;
if (*p == '+' || *p == '-') {
int step;
if (!(step = atoi(p))) {
step = 1;
}
fh->speed += step;
} else {
int speed = atoi(p);
fh->speed = speed;
}
return SWITCH_STATUS_SUCCESS;
}
return SWITCH_STATUS_FALSE;
} else if (!strcasecmp(ret, "pause")) {
if (switch_test_flag(fh, SWITCH_FILE_PAUSE)) {
switch_clear_flag(fh, SWITCH_FILE_PAUSE);
} else {
switch_set_flag(fh, SWITCH_FILE_PAUSE);
}
return SWITCH_STATUS_SUCCESS;
} else if (!strcasecmp(ret, "stop")) {
return SWITCH_STATUS_FALSE;
} else if (!strcasecmp(ret, "restart")) {
unsigned int pos = 0;
fh->speed = 0;
switch_core_file_seek(fh, &pos, 0, SEEK_SET);
return SWITCH_STATUS_SUCCESS;
} else if (!strncasecmp(ret, "seek", 4)) {
switch_codec_t *codec;
unsigned int samps = 0;
unsigned int pos = 0;
char *p;
codec = switch_core_session_get_read_codec(session);
if ((p = strchr(ret, ':'))) {
p++;
if (*p == '+' || *p == '-') {
int step;
if (!(step = atoi(p))) {
step = 1000;
}
if (step > 0) {
samps = step * (codec->implementation->samples_per_second / 1000);
switch_core_file_seek(fh, &pos, samps, SEEK_CUR);
} else {
samps = step * (codec->implementation->samples_per_second / 1000);
switch_core_file_seek(fh, &pos, fh->pos - samps, SEEK_SET);
}
} else {
samps = atoi(p) * (codec->implementation->samples_per_second / 1000);
switch_core_file_seek(fh, &pos, samps, SEEK_SET);
}
}
return SWITCH_STATUS_SUCCESS;
}
if (!strcmp(ret, "true") || !strcmp(ret, "undefined")) {
return SWITCH_STATUS_SUCCESS;
}
return SWITCH_STATUS_FALSE;
}
void console_log(char *level_str, char *msg)
{
switch_log_level_t level = SWITCH_LOG_DEBUG;
if (level_str) {
level = switch_log_str2level(level_str);
}
switch_log_printf(SWITCH_CHANNEL_LOG, level, msg);
}
void console_clean_log(char *msg)
{
switch_log_printf(SWITCH_CHANNEL_LOG_CLEAN,SWITCH_LOG_DEBUG, msg);
}
char *api_execute(char *cmd, char *arg)
{
switch_stream_handle_t stream = { 0 };
SWITCH_STANDARD_STREAM(stream);
switch_api_execute(cmd, arg, NULL, &stream);
return (char *) stream.data;
}
void api_reply_delete(char *reply)
{
if (!switch_strlen_zero(reply)) {
free(reply);
}
}
%}
File diff suppressed because it is too large Load Diff