Merge branch 'master' into belle-sip

Conflicts:
	build/android/common.mk
	coreapi/linphonecore.h
This commit is contained in:
Yann Diorcet 2013-03-12 13:30:13 +01:00
commit 8dd4ee3ee2
15 changed files with 303 additions and 165 deletions

View file

@ -51,7 +51,7 @@ LOCAL_SRC_FILES := \
conference.c \
ec-calibrator.c \
linphone_tunnel_config.c \
message_storage.c
message_storage.c
ifndef LINPHONE_VERSION
LINPHONE_VERSION = "Devel"

View file

@ -666,21 +666,31 @@ if test x$enable_tunnel = xtrue; then
fi
AC_ARG_ENABLE(msg-storage,
[AS_HELP_STRING([--enable-msg-storage=[yes/no]], [Turn on compilation of message storage (default=yes)])],
[AS_HELP_STRING([--enable-msg-storage=[yes/no]], [Turn on compilation of message storage (default=auto)])],
[case "${enableval}" in
yes) enable_msg_storage=true ;;
no) enable_msg_storage=false ;;
*) AC_MSG_ERROR(bad value ${enableval} for --enable-msg-storage) ;;
esac],
[enable_msg_storage=true]
[enable_msg_storage=auto]
)
echo "enable_msg_storage = $enable_msg_storage"
AM_CONDITIONAL(BUILD_MSG_STORAGE, test x$enable_msg_storage = xtrue)
if test x$enable_msg_storage = xtrue; then
PKG_CHECK_MODULES(SQLITE3,[ sqlite3 >= 3.7.0],[],[
AC_MSG_ERROR([sqlite3 required for message storage not found.])] )
SQLITE3_CFLAGS+="-DMSG_STORAGE_ENABLED"
AC_SUBST(SQLITE3_CFLAGS)
AC_SUBST(SQLITE3_LIBS)
if test x$enable_msg_storage != xfalse; then
PKG_CHECK_MODULES(SQLITE3,[ sqlite3 >= 3.7.0],[
SQLITE3_CFLAGS+="-DMSG_STORAGE_ENABLED"
AC_SUBST(SQLITE3_CFLAGS)
AC_SUBST(SQLITE3_LIBS)
enable_msg_storage=true
],[
if test x$enable_msg_storage = xtrue; then
AC_MSG_ERROR([sqlite3 required for message storage not found.])
fi
enable_msg_storage=false
] )
fi
SIPSTACK_CFLAGS=
SIPSTACK_LIBS=

View file

@ -960,10 +960,11 @@ static void text_delivery_update(SalOp *op, SalTextDeliveryStatus status){
LinphoneChatMessage *chat_msg=(LinphoneChatMessage* )sal_op_get_user_pointer(op);
const MSList* calls = linphone_core_get_calls(chat_msg->chat_room->lc);
linphone_core_set_message_state(chat_msg->chat_room,chat_msg->message,chatStatusSal2Linphone(status),chat_msg->time);
chat_msg->state=chatStatusSal2Linphone(status);
linphone_chat_message_store_state(chat_msg);
if (chat_msg && chat_msg->cb) {
chat_msg->cb(chat_msg
,chatStatusSal2Linphone(status)
,chat_msg->state
,chat_msg->cb_ud);
}
if (status != SalTextDeliveryInProgress) { /*don't release op if progress*/

View file

@ -62,16 +62,7 @@ void linphone_chat_room_destroy(LinphoneChatRoom *cr){
ms_free(cr->peer);
}
#ifdef WIN32
static inline char *my_ctime_r(const time_t *t, char *buf){
strcpy(buf,ctime(t));
return buf;
}
#else
#define my_ctime_r ctime_r
#endif
static void _linphone_chat_room_send_message(LinphoneChatRoom *cr, LinphoneChatMessage* msg){
const char *route=NULL;
@ -80,8 +71,6 @@ static void _linphone_chat_room_send_message(LinphoneChatRoom *cr, LinphoneChatM
LinphoneCall *call;
char* content_type;
time_t t=time(NULL);
char buf[26];
char *to;
if (lp_config_get_int(cr->lc->config,"sip","chat_use_call_dialogs",0)){
if((call = linphone_core_get_call_by_remote_address(cr->lc,cr->peer))!=NULL){
@ -109,15 +98,14 @@ static void _linphone_chat_room_send_message(LinphoneChatRoom *cr, LinphoneChatM
}
if (msg->external_body_url) {
content_type=ms_strdup_printf("message/external-body; access-type=URL; URL=\"%s\"",msg->external_body_url);
sal_message_send(op,identity,cr->peer,content_type, NULL,my_ctime_r(&t,buf));
sal_message_send(op,identity,cr->peer,content_type, NULL);
ms_free(content_type);
} else {
sal_text_send(op, identity, cr->peer,msg->message,my_ctime_r(&t,buf));
sal_text_send(op, identity, cr->peer,msg->message);
}
to=linphone_address_as_string_uri_only (cr->peer_url);
linphone_core_set_history_message(cr,identity,to,OUTGOING,msg->message,
my_ctime_r(&t,buf),READ,LinphoneChatMessageStateInProgress);
ms_free(to);
msg->dir=LinphoneChatMessageOutgoing;
msg->from=linphone_address_new(identity);
linphone_chat_message_store(msg);
}
/**
@ -144,19 +132,15 @@ void linphone_chat_room_message_received(LinphoneChatRoom *cr, LinphoneCore *lc,
}
void linphone_core_message_received(LinphoneCore *lc, SalOp *op, const SalMessage *sal_msg){
MSList *elem;
/**
* Retrieve an existing chat room whose peer is the supplied address, if exists.
* @param lc the linphone core
* @param add a linphone address.
* @returns the matching chatroom, or NULL if no such chatroom exists.
**/
LinphoneChatRoom *linphone_core_get_chat_room(LinphoneCore *lc, const LinphoneAddress *addr){
LinphoneChatRoom *cr=NULL;
LinphoneAddress *addr;
char *cleanfrom;
const char *to;
char *from;
LinphoneChatMessage* msg;
const SalCustomHeader *ch;
char buf[26];
addr=linphone_address_new(sal_msg->from);
linphone_address_clean(addr);
MSList *elem;
for(elem=lc->chatrooms;elem!=NULL;elem=ms_list_next(elem)){
cr=(LinphoneChatRoom*)elem->data;
if (linphone_chat_room_matches(cr,addr)){
@ -164,7 +148,21 @@ void linphone_core_message_received(LinphoneCore *lc, SalOp *op, const SalMessag
}
cr=NULL;
}
to=linphone_core_get_identity(lc);
return cr;
}
void linphone_core_message_received(LinphoneCore *lc, SalOp *op, const SalMessage *sal_msg){
LinphoneChatRoom *cr=NULL;
LinphoneAddress *addr;
char *cleanfrom;
char *from;
LinphoneChatMessage* msg;
const SalCustomHeader *ch;
addr=linphone_address_new(sal_msg->from);
linphone_address_clean(addr);
cr=linphone_core_get_chat_room(lc,addr);
cleanfrom=linphone_address_as_string(addr);
from=linphone_address_as_string_uri_only(addr);
if (cr==NULL){
@ -173,8 +171,16 @@ void linphone_core_message_received(LinphoneCore *lc, SalOp *op, const SalMessag
}
msg = linphone_chat_room_create_message(cr, sal_msg->text);
linphone_chat_message_set_from(msg, cr->peer_url);
{
LinphoneAddress *to;
to=sal_op_get_to(op) ? linphone_address_new(sal_op_get_to(op)) : linphone_address_new(linphone_core_get_identity(lc));
msg->to=to;
}
msg->time=sal_msg->time;
msg->state=LinphoneChatMessageStateDelivered;
msg->is_read=FALSE;
ch=sal_op_get_custom_header(op);
if (ch) msg->custom_headers=sal_custom_header_clone(ch);
@ -182,9 +188,7 @@ void linphone_core_message_received(LinphoneCore *lc, SalOp *op, const SalMessag
linphone_chat_message_set_external_body_url(msg, sal_msg->url);
}
linphone_address_destroy(addr);
linphone_core_set_history_message(cr,to,from,INCOMING,
msg->message,my_ctime_r(&msg->time,buf),NOT_READ,
LinphoneChatMessageStateDelivered);
linphone_chat_message_store(msg);
linphone_chat_room_message_received(cr,lc,msg);
ms_free(cleanfrom);
ms_free(from);
@ -230,6 +234,7 @@ LinphoneChatMessage* linphone_chat_room_create_message(LinphoneChatRoom *cr, con
LinphoneChatMessage* msg = ms_new0(LinphoneChatMessage,1);
msg->chat_room=(LinphoneChatRoom*)cr;
msg->message=message?ms_strdup(message):NULL;
msg->is_read=TRUE;
return msg;
}
@ -327,10 +332,32 @@ void linphone_chat_message_set_from(LinphoneChatMessage* message, const Linphone
*@param message #LinphoneChatMessage obj
*@return #LinphoneAddress
*/
LinphoneAddress* linphone_chat_message_get_from(const LinphoneChatMessage* message) {
const LinphoneAddress* linphone_chat_message_get_from(const LinphoneChatMessage* message) {
return message->from;
}
/**
* Get destination of the message
*@param message #LinphoneChatMessage obj
*@return #LinphoneAddress
*/
const LinphoneAddress* linphone_chat_message_get_to(const LinphoneChatMessage* message){
if (message->to) return message->to;
if (message->dir==LinphoneChatMessageOutgoing){
return message->chat_room->peer_url;
}
return NULL;
}
/**
* Returns the origin address of a message if it was a outgoing message, or the destination address if it was an incoming message.
*@param message #LinphoneChatMessage obj
*@return #LinphoneAddress
*/
LinphoneAddress *linphone_chat_message_get_local_address(const LinphoneChatMessage* message){
return message->dir==LinphoneChatMessageOutgoing ? message->from : message->to;
}
/**
* Get the time the message was sent.
*/

View file

@ -1309,9 +1309,6 @@ static void linphone_core_init (LinphoneCore * lc, const LinphoneCoreVTable *vta
#ifdef TUNNEL_ENABLED
lc->tunnel=linphone_core_tunnel_new(lc);
if (lc->tunnel) linphone_tunnel_configure(lc->tunnel);
#endif
#ifdef MSG_STORAGE_ENABLED
lc->db=linphone_message_storage_init();
#endif
if (lc->vtable.display_status)
lc->vtable.display_status(lc,_("Ready"));
@ -5383,6 +5380,8 @@ static void linphone_core_uninit(LinphoneCore *lc)
}
linphone_core_free_payload_types(lc);
linphone_core_message_storage_close(lc);
ortp_exit();
linphone_core_set_state(lc,LinphoneGlobalOff,"Off");
#ifdef TUNNEL_ENABLED
@ -5919,3 +5918,24 @@ void linphone_core_set_video_dscp(LinphoneCore *lc, int dscp){
int linphone_core_get_video_dscp(const LinphoneCore *lc){
return lp_config_get_int(lc->config,"rtp","video_dscp",0x2e);
}
/**
* Sets the database filename where chat messages will be stored.
* If the file does not exist, it will be created.
* @ingroup initializing
* @param lc the linphone core
* @param path filesystem path
**/
void linphone_core_set_chat_database_path(LinphoneCore *lc, const char *path){
if (lc->chat_db_file){
ms_free(lc->chat_db_file);
lc->chat_db_file=NULL;
}
if (path) {
lc->chat_db_file=ms_strdup(path);
linphone_core_message_storage_init(lc);
}
}

View file

@ -671,12 +671,17 @@ typedef enum _LinphoneChatMessageStates {
*/
typedef void (*LinphoneChatMessageStateChangeCb)(LinphoneChatMessage* msg,LinphoneChatMessageState state,void* ud);
void linphone_core_set_chat_database_path(LinphoneCore *lc, const char *path);
LINPHONE_PUBLIC LinphoneChatRoom * linphone_core_create_chat_room(LinphoneCore *lc, const char *to);
LinphoneChatRoom *linphone_core_get_chat_room(LinphoneCore *lc, const LinphoneAddress *addr);
void linphone_chat_room_destroy(LinphoneChatRoom *cr);
LINPHONE_PUBLIC LinphoneChatMessage* linphone_chat_room_create_message(LinphoneChatRoom *cr,const char* message);
const LinphoneAddress* linphone_chat_room_get_peer_address(LinphoneChatRoom *cr);
LINPHONE_PUBLIC void linphone_chat_room_send_message(LinphoneChatRoom *cr, const char *msg);
LINPHONE_PUBLIC void linphone_chat_room_send_message2(LinphoneChatRoom *cr, LinphoneChatMessage* msg,LinphoneChatMessageStateChangeCb status_cb,void* ud);
MSList *linphone_chat_room_get_history(LinphoneChatRoom *cr,int nb_message);
void linphone_chat_room_mark_as_read(LinphoneChatRoom *cr);
void linphone_chat_room_delete_history(LinphoneChatRoom *cr);
LinphoneCore* linphone_chat_room_get_lc(LinphoneChatRoom *cr);
void linphone_chat_room_set_user_data(LinphoneChatRoom *cr, void * ud);
void * linphone_chat_room_get_user_data(LinphoneChatRoom *cr);
@ -685,15 +690,17 @@ LINPHONE_PUBLIC const char* linphone_chat_message_state_to_string(const Linphone
LinphoneChatMessageState linphone_chat_message_get_state(const LinphoneChatMessage* message);
LinphoneChatMessage* linphone_chat_message_clone(const LinphoneChatMessage* message);
void linphone_chat_message_set_from(LinphoneChatMessage* message, const LinphoneAddress* from);
LINPHONE_PUBLIC LinphoneAddress* linphone_chat_message_get_from(const LinphoneChatMessage* message);
LINPHONE_PUBLIC const char* linphone_chat_message_get_external_body_url(const LinphoneChatMessage* message);
LINPHONE_PUBLIC void linphone_chat_message_set_external_body_url(LinphoneChatMessage* message,const char* url);
LINPHONE_PUBLIC const char * linphone_chat_message_get_text(const LinphoneChatMessage* message);
const LinphoneAddress* linphone_chat_message_get_from(const LinphoneChatMessage* message);
const LinphoneAddress* linphone_chat_message_get_to(const LinphoneChatMessage* message);
const char* linphone_chat_message_get_external_body_url(const LinphoneChatMessage* message);
void linphone_chat_message_set_external_body_url(LinphoneChatMessage* message,const char* url);
const char * linphone_chat_message_get_text(const LinphoneChatMessage* message);
time_t linphone_chat_message_get_time(const LinphoneChatMessage* message);
void* linphone_chat_message_get_user_data(const LinphoneChatMessage* message);
void linphone_chat_message_set_user_data(LinphoneChatMessage* message,void*);
LinphoneChatRoom* linphone_chat_message_get_chat_room(LinphoneChatMessage *msg);
const LinphoneAddress* linphone_chat_message_get_peer_address(LinphoneChatMessage *msg);
LinphoneAddress *linphone_chat_message_get_local_address(const LinphoneChatMessage* message);
void linphone_chat_message_add_custom_header(LinphoneChatMessage* message, const char *header_name, const char *header_value);
const char * linphone_chat_message_get_custom_header(LinphoneChatMessage* message, const char *header_name);
@ -1426,9 +1433,7 @@ int linphone_core_get_audio_dscp(const LinphoneCore *lc);
void linphone_core_set_video_dscp(LinphoneCore *lc, int dscp);
int linphone_core_get_video_dscp(const LinphoneCore *lc);
MSList *linphone_chat_room_get_history(const char *to,LinphoneChatRoom *cr,int nb_message);
void linphone_core_set_messages_flag_read(LinphoneChatRoom *cr,const char *from, int read);
void linphone_core_delete_history(LinphoneCore *lc,const char *from);
#ifdef __cplusplus
}

View file

@ -38,44 +38,22 @@ static inline char *my_ctime_r(const time_t *t, char *buf){
static const char *days[]={"Sun","Mon","Tue","Wed","Thu","Fri","Sat"};
static const char *months[]={"Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"};
#define CONFIG_FILE ".linphone-history.db"
char *linphone_message_storage_get_config_file(const char *filename){
const int path_max=1024;
char *config_file=(char *)malloc(path_max*sizeof(char));
if (filename==NULL) filename=CONFIG_FILE;
/*try accessing a local file first if exists*/
if (access(CONFIG_FILE,F_OK)==0){
snprintf(config_file,path_max,"%s",filename);
}else{
#ifdef WIN32
const char *appdata=getenv("APPDATA");
if (appdata){
snprintf(config_file,path_max,"%s\\%s",appdata,LINPHONE_CONFIG_DIR);
CreateDirectory(config_file,NULL);
snprintf(config_file,path_max,"%s\\%s\\%s",appdata,LINPHONE_CONFIG_DIR,filename);
}
#else
const char *home=getenv("HOME");
if (home==NULL) home=".";
snprintf(config_file,path_max,"%s/%s",home,filename);
#endif
}
return config_file;
}
void create_chat_message(char **argv, void *data){
static void create_chat_message(char **argv, void *data){
LinphoneChatRoom *cr = (LinphoneChatRoom *)data;
LinphoneChatMessage* new_message = linphone_chat_room_create_message(cr,argv[4]);
LinphoneAddress *from;
struct tm ret={0};
char tmp1[80]={0};
char tmp2[80]={0};
if(atoi(argv[3])==INCOMING){
linphone_chat_message_set_from(new_message,linphone_address_new(argv[2]));
if(atoi(argv[3])==LinphoneChatMessageIncoming){
from=linphone_address_new(argv[2]);
} else {
linphone_chat_message_set_from(new_message,linphone_address_new(argv[1]));
from=linphone_address_new(argv[1]);
}
linphone_chat_message_set_from(new_message,from);
linphone_address_destroy(from);
if(argv[5]!=NULL){
int i,j;
@ -91,7 +69,7 @@ void create_chat_message(char **argv, void *data){
}
new_message->time=argv[5]!=NULL ? mktime(&ret) : time(NULL);
new_message->state=atoi(argv[7]);
cr->messages_hist=ms_list_prepend(cr->messages_hist,(void *)new_message);
cr->messages_hist=ms_list_prepend(cr->messages_hist,new_message);
}
static int callback(void *data, int argc, char **argv, char **colName){
@ -99,58 +77,84 @@ static int callback(void *data, int argc, char **argv, char **colName){
return 0;
}
void linphone_sql_request_message(sqlite3 *db,const char *stmt,void *data){
void linphone_sql_request_message(sqlite3 *db,const char *stmt,LinphoneChatRoom *cr){
char* errmsg;
int ret;
ret=sqlite3_exec(db,stmt,callback,data,&errmsg);
ret=sqlite3_exec(db,stmt,callback,cr,&errmsg);
if(ret != SQLITE_OK) {
printf("Error in creation: %s.\n", errmsg);
}
}
void linphone_sql_request(sqlite3* db,const char *stmt){
char* errmsg;
char* errmsg=NULL;
int ret;
ret=sqlite3_exec(db,stmt,0,0,&errmsg);
if(ret != SQLITE_OK) {
printf("Error in creation: %s.\n", errmsg);
ms_error("linphone_sql_request: error sqlite3_exec(): %s.\n", errmsg);
sqlite3_free(errmsg);
}
}
void linphone_core_set_history_message(LinphoneChatRoom *cr,const char *local_contact,const char *remote_contact,
int direction, const char *message,const char *date, int read, int state){
LinphoneCore *lc=linphone_chat_room_get_lc(cr);
char *buf=sqlite3_mprintf("insert into history values(NULL,%Q,%Q,%i,%Q,%Q,%i,%i);",
local_contact,remote_contact,direction,message,date,read,state);
linphone_sql_request(lc->db,buf);
void linphone_chat_message_store(LinphoneChatMessage *msg){
LinphoneCore *lc=linphone_chat_room_get_lc(msg->chat_room);
if (lc->db){
const char *peer=msg->chat_room->peer;
char *local_contact=linphone_address_as_string_uri_only(linphone_chat_message_get_local_address(msg));
char datebuf[26];
char *buf=sqlite3_mprintf("insert into history values(NULL,%Q,%Q,%i,%Q,%Q,%i,%i);",
local_contact,peer,msg->dir,msg->message,my_ctime_r(&msg->time,datebuf),msg->is_read,msg->state);
linphone_sql_request(lc->db,buf);
sqlite3_free(buf);
ms_free(local_contact);
}
}
void linphone_core_set_message_state(LinphoneChatRoom *cr,const char *message, int state, time_t date){
LinphoneCore *lc=linphone_chat_room_get_lc(cr);
char time_str[26];
char *buf=sqlite3_mprintf("update history set status=%i where message = %Q and time = %Q;",
state,message,my_ctime_r(&date,time_str));
linphone_sql_request(lc->db,buf);
void linphone_chat_message_store_state(LinphoneChatMessage *msg){
LinphoneCore *lc=msg->chat_room->lc;
if (lc->db){
char time_str[26];
char *buf=sqlite3_mprintf("update history set status=%i where message = %Q and time = %Q;",
msg->state,msg->message,my_ctime_r(&msg->time,time_str));
linphone_sql_request(lc->db,buf);
sqlite3_free(buf);
}
}
void linphone_core_set_messages_flag_read(LinphoneChatRoom *cr,const char *from, int read){
void linphone_chat_room_mark_as_read(LinphoneChatRoom *cr){
LinphoneCore *lc=linphone_chat_room_get_lc(cr);
int read=1;
if (lc->db==NULL) return ;
char *buf=sqlite3_mprintf("update history set read=%i where remoteContact = %Q;",
read,from);
read,cr->peer);
linphone_sql_request(lc->db,buf);
sqlite3_free(buf);
}
void linphone_core_delete_history(LinphoneCore *lc,const char *from){
char *buf=sqlite3_mprintf("delete from history where remoteContact = %Q;",from);
void linphone_chat_room_delete_history(LinphoneChatRoom *cr){
LinphoneCore *lc=cr->lc;
if (lc->db==NULL) return ;
char *buf=sqlite3_mprintf("delete from history where remoteContact = %Q;",cr->peer);
linphone_sql_request(lc->db,buf);
sqlite3_free(buf);
}
MSList *linphone_chat_room_get_history(const char *to,LinphoneChatRoom *cr,int nb_message){
MSList *linphone_chat_room_get_history(LinphoneChatRoom *cr,int nb_message){
LinphoneCore *lc=linphone_chat_room_get_lc(cr);
MSList *ret;
if (lc->db==NULL) return NULL;
cr->messages_hist = NULL;
char *buf=sqlite3_mprintf("select * from history where remoteContact = %Q order by id DESC limit %i ;",to,nb_message);
linphone_sql_request_message(lc->db,buf,(void *)cr);
return cr->messages_hist;
char *buf=sqlite3_mprintf("select * from history where remoteContact = %Q order by id DESC limit %i ;",cr->peer,nb_message);
linphone_sql_request_message(lc->db,buf,cr);
sqlite3_free(buf);
ret=cr->messages_hist;
cr->messages_hist=NULL;
return ret;
}
void linphone_close_storage(sqlite3* db){
@ -167,36 +171,49 @@ void linphone_create_table(sqlite3* db){
}
}
sqlite3 * linphone_message_storage_init(){
void linphone_core_message_storage_init(LinphoneCore *lc){
int ret;
char *errmsg;
char *errmsg=NULL;
sqlite3 *db;
char *filename;
filename=linphone_message_storage_get_config_file(NULL);
ret=sqlite3_open(filename,&db);
ret=sqlite3_open(lc->chat_db_file,&db);
if(ret != SQLITE_OK) {
printf("Error in the opening: %s.\n", errmsg);
sqlite3_close(db);
sqlite3_free(errmsg);
}
linphone_create_table(db);
return db;
lc->db=db;
}
void linphone_core_message_storage_close(LinphoneCore *lc){
if (lc->db){
sqlite3_close(lc->db);
lc->db=NULL;
}
}
#else
void linphone_core_set_history_message(LinphoneChatRoom *cr,const char *local_contact,const char *remote_contact,
int direction, const char *message,const char *date, int read, int state){
void linphone_chat_message_store(LinphoneChatMessage *cr){
}
void linphone_core_set_message_state(LinphoneChatRoom *cr,const char *message, int state, time_t date){
void linphone_chat_message_store_state(LinphoneChatMessage *cr){
}
void linphone_core_set_messages_flag_read(LinphoneChatRoom *cr,const char *from, int read){
void linphone_chat_room_mark_as_read(LinphoneChatRoom *cr){
}
MSList *linphone_chat_room_get_history(const char *to,LinphoneChatRoom *cr,int nb_message){
MSList *linphone_chat_room_get_history(LinphoneChatRoom *cr,int nb_message){
return NULL;
}
void linphone_core_delete_history(LinphoneCore *lc,const char *from){
void linphone_chat_room_delete_history(LinphoneChatRoom *cr){
}
#endif
void linphone_core_message_storage_init(LinphoneCore *lc){
}
void linphone_core_message_storage_close(LinphoneCore *lc){
}
#endif

View file

@ -119,17 +119,25 @@ typedef struct _CallCallbackObj
static const int linphone_call_magic=0x3343;
typedef enum _LinphoneChatMessageDir{
LinphoneChatMessageIncoming,
LinphoneChatMessageOutgoing
} LinphoneChatMessageDir;
struct _LinphoneChatMessage {
char* message;
LinphoneChatRoom* chat_room;
LinphoneChatMessageDir dir;
char* message;
LinphoneChatMessageStateChangeCb cb;
void* cb_ud;
void* message_userdata;
char* external_body_url;
LinphoneAddress* from;
LinphoneAddress *from;
LinphoneAddress *to;
time_t time;
SalCustomHeader *custom_headers;
LinphoneChatMessageState state;
bool_t is_read;
};
typedef struct StunCandidate{
@ -623,6 +631,7 @@ struct _LinphoneCore
LinphoneTunnel *tunnel;
char* device_id;
MSList *last_recv_msg_ids;
char *chat_db_file;
#ifdef MSG_STORAGE_ENABLED
sqlite3 *db;
#endif
@ -707,19 +716,13 @@ void linphone_call_params_uninit(LinphoneCallParams *params);
int linphone_upnp_init(LinphoneCore *lc);
void linphone_upnp_destroy(LinphoneCore *lc);
#define OUTGOING 0
#define INCOMING 1
#define NOT_READ 0
#define READ 1
#ifdef MSG_STORAGE_ENABLED
sqlite3 * linphone_message_storage_init();
#endif
void linphone_core_set_history_message(LinphoneChatRoom *cr,const char *local_contact,const char *remote_contact,
int direction, const char *message,const char *date, int read, int state);
void linphone_core_set_message_state(LinphoneChatRoom *cr,const char *message, int state,time_t date);
void linphone_chat_message_store(LinphoneChatMessage *msg);
void linphone_chat_message_store_state(LinphoneChatMessage *msg);
void linphone_core_message_storage_init(LinphoneCore *lc);
void linphone_core_message_storage_close(LinphoneCore *lc);
#ifdef __cplusplus
}

View file

@ -81,8 +81,23 @@ void sal_remove_in_subscribe(Sal *sal, SalOp *op){
sal->in_subscribes=ms_list_remove(sal->in_subscribes,op);
}
int sal_message_send(SalOp *op, const char *from, const char *to, const char* content_type, const char *msg, const char *t){
#ifdef WIN32
static inline char *my_ctime_r(const time_t *t, char *buf){
strcpy(buf,ctime(t));
return buf;
}
#else
#define my_ctime_r ctime_r
#endif
int sal_message_send(SalOp *op, const char *from, const char *to, const char* content_type, const char *msg){
osip_message_t *sip=NULL;
char t[26];
time_t curtime=time(NULL);
my_ctime_r(&curtime,t);
if(op->cid == -1)
{
@ -120,6 +135,8 @@ int sal_message_send(SalOp *op, const char *from, const char *to, const char* co
eXosip_unlock();
return -1;
}
sal_exosip_add_custom_headers(sip,op->base.custom_headers);
osip_message_set_date(sip,t);
osip_message_set_content_type(sip,content_type);
if (msg) osip_message_set_body(sip,msg,strlen(msg));
eXosip_call_send_request(op->did,sip);
@ -128,8 +145,8 @@ int sal_message_send(SalOp *op, const char *from, const char *to, const char* co
return 0;
}
int sal_text_send(SalOp *op, const char *from, const char *to, const char *msg,const char *t) {
return sal_message_send(op,from,to,"text/plain",msg,t);
int sal_text_send(SalOp *op, const char *from, const char *to, const char *msg) {
return sal_message_send(op,from,to,"text/plain",msg);
}
/*presence Subscribe/notify*/
int sal_subscribe_presence(SalOp *op, const char *from, const char *to){

View file

@ -111,22 +111,22 @@ void linphone_upnp_config_remove_port_binding(UpnpContext *lupnp, const UpnpPort
int linphone_upnp_context_send_remove_port_binding(UpnpContext *lupnp, UpnpPortBinding *port, bool_t retry);
int linphone_upnp_context_send_add_port_binding(UpnpContext *lupnp, UpnpPortBinding *port, bool_t retry);
static int linphone_upnp_strncmpi(const char *str1, const char *str2, int len) {
int i = 0;
char char1, char2;
while(*str1 != '\0' && *str2 != '\0' && i < len) {
while(i < len) {
char1 = toupper(*str1);
char2 = toupper(*str2);
if(char1 != char2) {
if(char1 == '\0' || char1 != char2) {
return char1 - char2;
}
str1++;
str2++;
len++;
i++;
}
return 0;
}
static int linphone_upnp_str_min(const char *str1, const char *str2) {
int len1 = strlen(str1);
int len2 = strlen(str2);
@ -135,6 +135,7 @@ static int linphone_upnp_str_min(const char *str1, const char *str2) {
}
return len1;
}
char * linphone_upnp_format_device_id(const char *device_id) {
char *ret = NULL;
char *tmp;

View file

@ -25,6 +25,37 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#define NB_MSG_HIST 250
#define CONFIG_FILE ".linphone-history.db"
const char *linphone_gtk_message_storage_get_db_file(const char *filename){
const int path_max=1024;
static char *db_file=NULL;
if (db_file) return db_file;
db_file=(char *)malloc(path_max*sizeof(char));
if (filename==NULL) filename=CONFIG_FILE;
/*try accessing a local file first if exists*/
if (access(CONFIG_FILE,F_OK)==0){
snprintf(db_file,path_max,"%s",filename);
}else{
#ifdef WIN32
const char *appdata=getenv("APPDATA");
if (appdata){
snprintf(db_file,path_max,"%s\\%s",appdata,LINPHONE_CONFIG_DIR);
CreateDirectory(db_file,NULL);
snprintf(db_file,path_max,"%s\\%s\\%s",appdata,LINPHONE_CONFIG_DIR,filename);
}
#else
const char *home=getenv("HOME");
if (home==NULL) home=".";
snprintf(db_file,path_max,"%s/%s",home,filename);
#endif
}
return db_file;
}
void linphone_gtk_quit_chatroom(LinphoneChatRoom *cr) {
GtkWidget *main_window=linphone_gtk_get_main_window ();
GtkWidget *nb=linphone_gtk_get_widget(main_window,"viewswitch");
@ -92,16 +123,16 @@ void udpate_tab_chat_header(GtkWidget *chat_view,const LinphoneAddress *uri,Linp
void linphone_gtk_push_text(GtkWidget *w, const LinphoneAddress *from,
gboolean me,LinphoneChatRoom *cr,LinphoneChatMessage *msg, gboolean hist){
GtkTextView *text=GTK_TEXT_VIEW(linphone_gtk_get_widget(w,"textview"));
GtkTextBuffer *buffer=gtk_text_view_get_buffer(text);
GtkTextIter iter,begin;
GtkTextView *text=GTK_TEXT_VIEW(linphone_gtk_get_widget(w,"textview"));
GtkTextBuffer *buffer=gtk_text_view_get_buffer(text);
GtkTextIter iter,begin;
int off;
char *from_str=linphone_address_as_string_uri_only(from);
char *from_message=(char *)g_object_get_data(G_OBJECT(w),"from_message");
GList *list=g_object_get_data(G_OBJECT(w),"list");
time_t t;
gtk_text_buffer_get_start_iter(buffer,&begin);
gtk_text_buffer_get_start_iter(buffer,&begin);
gtk_text_buffer_get_end_iter(buffer,&iter);
off=gtk_text_iter_get_offset(&iter);
if(g_strcmp0(from_message,from_str)!=0){
@ -148,7 +179,7 @@ void linphone_gtk_push_text(GtkWidget *w, const LinphoneAddress *from,
gtk_text_buffer_get_end_iter(buffer,&iter);
gtk_text_buffer_insert(buffer,&iter,"\n",-1);
GtkTextMark *mark=gtk_text_buffer_create_mark(buffer,NULL,&iter,FALSE);
gtk_text_view_scroll_mark_onscreen(text,mark);
gtk_text_view_scroll_mark_onscreen(text,mark);
}
const LinphoneAddress* linphone_gtk_get_used_identity(){
@ -160,8 +191,8 @@ const LinphoneAddress* linphone_gtk_get_used_identity(){
}
void update_chat_state_message(LinphoneChatMessageState state,LinphoneChatMessage *msg){
GtkWidget *main_window=linphone_gtk_get_main_window();
GtkWidget *friendlist=linphone_gtk_get_widget(main_window,"contact_list");
GtkWidget *main_window=linphone_gtk_get_main_window();
GtkWidget *friendlist=linphone_gtk_get_widget(main_window,"contact_list");
GtkWidget *page=(GtkWidget*)g_object_get_data(G_OBJECT(friendlist),"chatview");
GList *list=g_object_get_data(G_OBJECT(page),"list");
@ -277,7 +308,7 @@ GtkWidget* linphone_gtk_init_chatroom(LinphoneChatRoom *cr, const LinphoneAddres
colorb.blue = 61952;
with_str=linphone_address_as_string_uri_only(with);
linphone_core_set_messages_flag_read(cr,with_str,1);
linphone_chat_room_mark_as_read(cr);
gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(text),GTK_WRAP_WORD_CHAR);
gtk_text_view_set_editable(GTK_TEXT_VIEW(text),FALSE);
gtk_notebook_append_page(notebook,chat_view,create_tab_chat_header(cr,with));
@ -304,7 +335,7 @@ GtkWidget* linphone_gtk_init_chatroom(LinphoneChatRoom *cr, const LinphoneAddres
"margin","indent",10,NULL);
gtk_text_buffer_create_tag(gtk_text_view_get_buffer(GTK_TEXT_VIEW(text)),
"bg","paragraph-background-gdk",&colorb,NULL);
messages = linphone_chat_room_get_history(with_str,cr,NB_MSG_HIST);
messages = linphone_chat_room_get_history(cr,NB_MSG_HIST);
display_history_message(chat_view,messages,with);
button = linphone_gtk_get_widget(chat_view,"send");
g_signal_connect_swapped(G_OBJECT(button),"clicked",(GCallback)linphone_gtk_send_text,NULL);
@ -325,23 +356,22 @@ void linphone_gtk_load_chatroom(LinphoneChatRoom *cr,const LinphoneAddress *uri,
LinphoneChatRoom *cr2=(LinphoneChatRoom *)g_object_get_data(G_OBJECT(chat_view),"cr");
char *from_str=linphone_address_as_string(linphone_chat_room_get_peer_address (cr2));
char *uri_str=linphone_address_as_string(uri);
char *uri_only=linphone_address_as_string_uri_only(uri);
MSList *messages=NULL;
linphone_core_set_messages_flag_read(cr,uri_only,1);
if(g_strcmp0(from_str,uri_str)!=0){
GtkTextView *text_view=GTK_TEXT_VIEW(linphone_gtk_get_widget(chat_view,"textview"));
GtkTextIter start;
GtkTextIter end;
linphone_chat_room_mark_as_read(cr);
if(g_strcmp0(from_str,uri_str)!=0){
GtkTextView *text_view=GTK_TEXT_VIEW(linphone_gtk_get_widget(chat_view,"textview"));
GtkTextIter start;
GtkTextIter end;
GtkTextBuffer *text_buffer;
text_buffer=gtk_text_view_get_buffer(text_view);
gtk_text_buffer_get_bounds(text_buffer, &start, &end);
gtk_text_buffer_delete (text_buffer, &start, &end);
text_buffer=gtk_text_view_get_buffer(text_view);
gtk_text_buffer_get_bounds(text_buffer, &start, &end);
gtk_text_buffer_delete (text_buffer, &start, &end);
udpate_tab_chat_header(chat_view,uri,cr);
g_object_set_data(G_OBJECT(chat_view),"cr",cr);
g_object_set_data(G_OBJECT(linphone_gtk_get_widget(main_window,"contact_list")),"chatview",(gpointer)chat_view);
messages = linphone_chat_room_get_history(uri_only,cr,NB_MSG_HIST);
messages = linphone_chat_room_get_history(cr,NB_MSG_HIST);
g_object_set_data(G_OBJECT(chat_view),"from_message",uri_str);
display_history_message(chat_view,messages,uri);
}

View file

@ -174,8 +174,10 @@ void linphone_gtk_delete_history(GtkWidget *button){
select = gtk_tree_view_get_selection(GTK_TREE_VIEW(linphone_gtk_get_widget(w,"contact_list")));
if (gtk_tree_selection_get_selected (select, &model, &iter))
{
LinphoneChatRoom *cr;
gtk_tree_model_get (model, &iter,FRIEND_ID , &lf, -1);
linphone_core_delete_history(linphone_gtk_get_core(),linphone_address_as_string_uri_only(linphone_friend_get_address(lf)));
cr=linphone_core_get_chat_room(linphone_gtk_get_core(),linphone_friend_get_address(lf));
linphone_chat_room_delete_history(cr);
linphone_gtk_show_friends();
}
}

View file

@ -58,6 +58,8 @@ GtkWidget *linphone_gtk_create_window(const char *window_name);
GtkWidget *linphone_gtk_get_widget(GtkWidget *window, const char *name);
GtkWidget *linphone_gtk_create_widget(const char *filename, const char *widget_name);
const char *linphone_gtk_message_storage_get_db_file(const char *filename);
void linphone_gtk_show_assistant(void);
void linphone_gtk_close_assistant(void);

View file

@ -216,7 +216,7 @@ static const char *linphone_gtk_get_factory_config_file(){
}
static void linphone_gtk_init_liblinphone(const char *config_file,
const char *factory_config_file) {
const char *factory_config_file, const char *db_file) {
LinphoneCoreVTable vtable={0};
gchar *secrets_file=linphone_gtk_get_config_file(SECRETS_FILE);
@ -248,6 +248,7 @@ static void linphone_gtk_init_liblinphone(const char *config_file,
_linphone_gtk_enable_video(FALSE);
linphone_gtk_set_ui_config_int("videoselfview",0);
}
if (db_file) linphone_core_set_chat_database_path(the_core,db_file);
}
LinphoneCore *linphone_gtk_get_core(void){
@ -1840,6 +1841,7 @@ int main(int argc, char *argv[]){
GdkPixbuf *pbuf;
const char *app_name="Linphone";
LpConfig *factory;
const char *db_file;
#if !GLIB_CHECK_VERSION(2, 31, 0)
g_thread_init(NULL);
@ -1946,7 +1948,8 @@ int main(int argc, char *argv[]){
linphone_gtk_create_log_window();
linphone_core_enable_logs_with_cb(linphone_gtk_log_handler);
linphone_gtk_init_liblinphone(config_file, factory_config_file);
db_file=linphone_gtk_message_storage_get_db_file(NULL);
linphone_gtk_init_liblinphone(config_file, factory_config_file, db_file);
g_set_application_name(app_name);
pbuf=create_pixbuf(linphone_gtk_get_ui_config("icon",LINPHONE_ICON));

View file

@ -481,8 +481,8 @@ int sal_register_refresh(SalOp *op, int expires);
int sal_unregister(SalOp *h);
/*Messaging */
int sal_text_send(SalOp *op, const char *from, const char *to, const char *text, const char*t);
int sal_message_send(SalOp *op, const char *from, const char *to, const char* content_type, const char *msg, const char*t);
int sal_text_send(SalOp *op, const char *from, const char *to, const char *text);
int sal_message_send(SalOp *op, const char *from, const char *to, const char* content_type, const char *msg);
/*presence Subscribe/notify*/
int sal_subscribe_presence(SalOp *op, const char *from, const char *to);