commit a3be90bc89ba9ab4968329f49013412b5f2e2af6
parent ecccdbe89ad906f5d995e45ec1ff40117d642b18
Author: TheJackiMonster <thejackimonster@gmail.com>
Date: Thu, 29 Jul 2021 23:01:26 +0200
Implemented dynamic context creation for contacts
Signed-off-by: TheJackiMonster <thejackimonster@gmail.com>
Diffstat:
3 files changed, 86 insertions(+), 11 deletions(-)
diff --git a/src/gnunet_chat_handle_intern.c b/src/gnunet_chat_handle_intern.c
@@ -211,7 +211,7 @@ check_handle_room_members (void* cls,
return GNUNET_YES;
}
-struct GNUNET_CHAT_Context*
+int
request_handle_context_by_room (struct GNUNET_CHAT_Handle *handle,
struct GNUNET_MESSENGER_Room *room)
{
@@ -222,7 +222,7 @@ request_handle_context_by_room (struct GNUNET_CHAT_Handle *handle,
);
if (context)
- return context;
+ return GNUNET_OK;
context = context_create_from_room(handle, room);
context_load_config(context);
@@ -232,14 +232,16 @@ request_handle_context_by_room (struct GNUNET_CHAT_Handle *handle,
GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST))
{
context_destroy(context);
- return NULL;
+ return GNUNET_SYSERR;
}
struct GNUNET_CHAT_CheckHandleRoomMembers check;
check.ignore_key = GNUNET_MESSENGER_get_key(handle->messenger);
check.contact = NULL;
- GNUNET_MESSENGER_iterate_members(room, check_handle_room_members, &check);
+ const int checks = GNUNET_MESSENGER_iterate_members(
+ room, check_handle_room_members, &check
+ );
if (check.contact)
{
@@ -257,11 +259,11 @@ request_handle_context_by_room (struct GNUNET_CHAT_Handle *handle,
if (GNUNET_OK == GNUNET_CONTAINER_multishortmap_put(
handle->contacts, &shorthash, contact,
GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST))
- return context;
+ return GNUNET_OK;
contact_destroy(contact);
}
- else
+ else if (checks >= 2)
{
context->type = GNUNET_CHAT_CONTEXT_TYPE_GROUP;
@@ -277,14 +279,20 @@ request_handle_context_by_room (struct GNUNET_CHAT_Handle *handle,
if (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put(
handle->groups, key, group,
GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST))
- return context;
+ return GNUNET_OK;
group_destroy(group);
}
+ else
+ {
+ context->type = GNUNET_CHAT_CONTEXT_TYPE_UNKNOWN;
+
+ // TODO: handle chats which only contain yourself currently!
+ }
GNUNET_CONTAINER_multihashmap_remove(handle->contexts, key, context);
context_destroy(context);
- return NULL;
+ return GNUNET_SYSERR;
}
int
@@ -293,9 +301,8 @@ find_handle_rooms (void *cls, struct GNUNET_MESSENGER_Room *room,
{
struct GNUNET_CHAT_Handle *handle = cls;
- request_handle_context_by_room(
- handle, room
- );
+ if (GNUNET_OK != request_handle_context_by_room(handle, room))
+ return GNUNET_NO;
return GNUNET_YES;
}
diff --git a/src/gnunet_chat_lib.c b/src/gnunet_chat_lib.c
@@ -171,6 +171,9 @@ GNUNET_CHAT_group_create (struct GNUNET_CHAT_Handle *handle,
handle->messenger, &key
);
+ if (!room)
+ return NULL;
+
struct GNUNET_CHAT_Context *context = context_create_from_room(handle, room);
context->type = GNUNET_CHAT_CONTEXT_TYPE_GROUP;
@@ -290,6 +293,57 @@ GNUNET_CHAT_contact_get_context (struct GNUNET_CHAT_Contact *contact)
if (!contact)
return NULL;
+ if (contact->context)
+ return contact->context;
+
+ struct GNUNET_CHAT_ContactFindRoom find;
+ find.room = NULL;
+ GNUNET_MESSENGER_find_rooms(
+ contact->handle->messenger,
+ contact->member,
+ it_contact_find_room,
+ &find
+ );
+
+ // TODO: Check if the found room is a group or not
+
+ if (!(find.room))
+ return NULL;
+
+ struct GNUNET_HashCode key;
+ GNUNET_CRYPTO_random_block(GNUNET_CRYPTO_QUALITY_WEAK, &key, sizeof(key));
+
+ if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains(
+ contact->handle->contexts, &key))
+ return NULL;
+
+ struct GNUNET_MESSENGER_Room *room = GNUNET_MESSENGER_open_room(
+ contact->handle->messenger, &key
+ );
+
+ if (!room)
+ return NULL;
+
+ struct GNUNET_CHAT_Context *context = context_create_from_room(
+ contact->handle, room
+ );
+
+ if (GNUNET_OK != GNUNET_CONTAINER_multihashmap_put(
+ contact->handle->contexts, &key, context,
+ GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST))
+ {
+ context_destroy(context);
+ return NULL;
+ }
+
+ struct GNUNET_MESSENGER_Message msg;
+ msg.header.kind = GNUNET_MESSENGER_KIND_INVITE;
+ GNUNET_CRYPTO_get_peer_identity(contact->handle->cfg, &(msg.body.invite.door));
+ GNUNET_memcpy(&(msg.body.invite.key), &key, sizeof(msg.body.invite.key));
+
+ GNUNET_MESSENGER_send_message(find.room, &msg, contact->member);
+
+ contact->context = context;
return contact->context;
}
diff --git a/src/gnunet_chat_lib_intern.c b/src/gnunet_chat_lib_intern.c
@@ -68,6 +68,20 @@ it_handle_iterate_groups (void *cls,
return it->cb(it->cls, it->handle, group);
}
+struct GNUNET_CHAT_ContactFindRoom
+{
+ struct GNUNET_MESSENGER_Room *room;
+};
+
+int
+it_contact_find_room (void *cls, struct GNUNET_MESSENGER_Room *room,
+ GNUNET_UNUSED const struct GNUNET_MESSENGER_Contact *member)
+{
+ struct GNUNET_CHAT_ContactFindRoom *find = cls;
+ find->room = room;
+ return GNUNET_NO;
+}
+
struct GNUNET_CHAT_GroupIterateContacts
{
struct GNUNET_CHAT_Group *group;