From e682a3b1f54d3d36040ecd1822884bfe9e062282 Mon Sep 17 00:00:00 2001 From: Ghislain MARY Date: Wed, 16 May 2018 15:27:47 +0200 Subject: [PATCH] Fix issue 4893: After being re-invited in a chat room, when the device is restarted nothing can be done in the chat room. Store the conference created event in DB and update the notify id in DB if insertion of the chat room is requested but it is already stored. --- src/chat/chat-room/client-group-chat-room.cpp | 8 +-- src/db/main-db.cpp | 8 ++- tester/group_chat_tester.c | 50 +++++++++++++++++-- 3 files changed, 55 insertions(+), 11 deletions(-) diff --git a/src/chat/chat-room/client-group-chat-room.cpp b/src/chat/chat-room/client-group-chat-room.cpp index fbad53fed..e6e932ac9 100644 --- a/src/chat/chat-room/client-group-chat-room.cpp +++ b/src/chat/chat-room/client-group-chat-room.cpp @@ -598,17 +598,13 @@ void ClientGroupChatRoom::onFirstNotifyReceived (const IdentityAddress &addr) { LinphoneChatRoom *cr = d->getCChatRoom(); _linphone_chat_room_notify_all_information_received(cr); - d->bgTask.stop(); - - // TODO: Bug. Event is inserted many times. - // Avoid this in the future. Deal with signals/slots system. - #if 0 d->addEvent(make_shared( EventLog::Type::ConferenceCreated, time(nullptr), d->chatRoomId )); - #endif + + d->bgTask.stop(); } void ClientGroupChatRoom::onParticipantAdded (const shared_ptr &event, bool isFullState) { diff --git a/src/db/main-db.cpp b/src/db/main-db.cpp index b69d9f8c9..f96a6e14d 100644 --- a/src/db/main-db.cpp +++ b/src/db/main-db.cpp @@ -328,8 +328,12 @@ long long MainDbPrivate::insertChatRoom (const shared_ptr &cha const long long &localSipAddressId = insertSipAddress(chatRoomId.getLocalAddress().asString()); long long id = selectChatRoomId(peerSipAddressId, localSipAddressId); - if (id >= 0) + if (id >= 0) { + // The chat room is already stored in DB, but still update the notify id that might have changed + *dbSession.getBackendSession() << "UPDATE chat_room SET last_notify_id = :lastNotifyId WHERE id = :chatRoomId", + soci::use(notifyId), soci::use(id); return id; + } lInfo() << "Insert new chat room in database: " << chatRoomId << "."; @@ -715,6 +719,8 @@ long long MainDbPrivate::insertConferenceEvent (const shared_ptr &even if (eventLog->getType() == EventLog::Type::ConferenceTerminated) *session << "UPDATE chat_room SET flags = 1, last_notify_id = 0 WHERE id = :chatRoomId", soci::use(curChatRoomId); + else if (eventLog->getType() == EventLog::Type::ConferenceCreated) + *session << "UPDATE chat_room SET flags = 0 WHERE id = :chatRoomId", soci::use(curChatRoomId); } if (chatRoomId) diff --git a/tester/group_chat_tester.c b/tester/group_chat_tester.c index 1d72414bb..3eddc1aa7 100644 --- a/tester/group_chat_tester.c +++ b/tester/group_chat_tester.c @@ -1484,7 +1484,7 @@ static void group_chat_room_create_room_with_disconnected_friends_and_initial_me group_chat_room_create_room_with_disconnected_friends_base(TRUE); } -static void group_chat_room_reinvited_after_removed_base (bool_t offline_when_removed, bool_t offline_when_reinvited) { +static void group_chat_room_reinvited_after_removed_base (bool_t offline_when_removed, bool_t offline_when_reinvited, bool_t restart_after_reinvited) { LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc"); LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc"); LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc"); @@ -1579,6 +1579,43 @@ static void group_chat_room_reinvited_after_removed_base (bool_t offline_when_re BC_ASSERT_PTR_EQUAL(newLaureCr, laureCr); BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(newLaureCr), 2, int, "%d"); BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(newLaureCr), initialSubject); + BC_ASSERT_FALSE(linphone_chat_room_has_been_left(newLaureCr)); + + unsigned int nbLaureConferenceCreatedEventsBeforeRestart = 0; + bctbx_list_t *laureHistory = linphone_chat_room_get_history_events(newLaureCr, 0); + for (bctbx_list_t *item = laureHistory; item; item = bctbx_list_next(item)) { + LinphoneEventLog *event = (LinphoneEventLog *)bctbx_list_get_data(item); + if (linphone_event_log_get_type(event) == LinphoneEventLogTypeConferenceCreated) + nbLaureConferenceCreatedEventsBeforeRestart++; + } + bctbx_list_free_with_data(laureHistory, (bctbx_list_free_func)linphone_event_log_unref); + BC_ASSERT_EQUAL(nbLaureConferenceCreatedEventsBeforeRestart, 2, unsigned int, "%u"); + + if (restart_after_reinvited) { + coresList = bctbx_list_remove(coresList, laure->lc); + linphone_core_manager_reinit(laure); + bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, laure); + bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList); + bctbx_list_free(tmpCoresManagerList); + coresList = bctbx_list_concat(coresList, tmpCoresList); + linphone_core_manager_start(laure, TRUE); + laureIdentity = linphone_core_get_device_identity(laure->lc); + laureAddr = linphone_address_new(laureIdentity); + newLaureCr = linphone_core_find_chat_room(laure->lc, confAddr, laureAddr); + linphone_address_unref(laureAddr); + wait_for_list(coresList,0, 1, 2000); + BC_ASSERT_FALSE(linphone_chat_room_has_been_left(newLaureCr)); + + unsigned int nbLaureConferenceCreatedEventsAfterRestart = 0; + bctbx_list_t *laureHistory = linphone_chat_room_get_history_events(newLaureCr, 0); + for (bctbx_list_t *item = laureHistory; item; item = bctbx_list_next(item)) { + LinphoneEventLog *event = (LinphoneEventLog *)bctbx_list_get_data(item); + if (linphone_event_log_get_type(event) == LinphoneEventLogTypeConferenceCreated) + nbLaureConferenceCreatedEventsAfterRestart++; + } + bctbx_list_free_with_data(laureHistory, (bctbx_list_free_func)linphone_event_log_unref); + BC_ASSERT_EQUAL(nbLaureConferenceCreatedEventsAfterRestart, nbLaureConferenceCreatedEventsBeforeRestart, unsigned int, "%u"); + } // Clean db from chat room linphone_core_manager_delete_chat_room(marie, marieCr, coresList); @@ -1593,15 +1630,19 @@ static void group_chat_room_reinvited_after_removed_base (bool_t offline_when_re } static void group_chat_room_reinvited_after_removed (void) { - group_chat_room_reinvited_after_removed_base(FALSE, FALSE); + group_chat_room_reinvited_after_removed_base(FALSE, FALSE, FALSE); +} + +static void group_chat_room_reinvited_after_removed_2 (void) { + group_chat_room_reinvited_after_removed_base(FALSE, FALSE, TRUE); } static void group_chat_room_reinvited_after_removed_while_offline (void) { - group_chat_room_reinvited_after_removed_base(TRUE, FALSE); + group_chat_room_reinvited_after_removed_base(TRUE, FALSE, FALSE); } static void group_chat_room_reinvited_after_removed_while_offline_2 (void) { - group_chat_room_reinvited_after_removed_base(TRUE, TRUE); + group_chat_room_reinvited_after_removed_base(TRUE, TRUE, FALSE); } static void group_chat_room_reinvited_after_removed_with_several_devices (void) { @@ -3686,6 +3727,7 @@ test_t group_chat_tests[] = { TEST_ONE_TAG("Create chat room with disconnected friends", group_chat_room_create_room_with_disconnected_friends, "LeaksMemory"), TEST_ONE_TAG("Create chat room with disconnected friends and initial message", group_chat_room_create_room_with_disconnected_friends_and_initial_message, "LeaksMemory"), TEST_NO_TAG("Reinvited after removed from group chat room", group_chat_room_reinvited_after_removed), + TEST_ONE_TAG("Reinvited after removed from group chat room 2", group_chat_room_reinvited_after_removed_2, "LeaksMemory"), TEST_ONE_TAG("Reinvited after removed from group chat room while offline", group_chat_room_reinvited_after_removed_while_offline, "LeaksMemory"), TEST_ONE_TAG("Reinvited after removed from group chat room while offline 2", group_chat_room_reinvited_after_removed_while_offline_2, "LeaksMemory"), TEST_NO_TAG("Reinvited after removed from group chat room with several devices", group_chat_room_reinvited_after_removed_with_several_devices),