Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to init a group discussion? #44

Closed
jimijon opened this issue Apr 29, 2017 · 10 comments
Closed

How to init a group discussion? #44

jimijon opened this issue Apr 29, 2017 · 10 comments

Comments

@jimijon
Copy link

jimijon commented Apr 29, 2017

Hello -

Have chat working and exploring. Now I need to have a group chat discussion. Basically I want to make a chat room for each of my brands. How do I pop open a chat with the group already initialized say with the brand code?

Thanks

@jimijon
Copy link
Author

jimijon commented Apr 29, 2017

Ok so I was trying 👍

BNetworkManager.shared().a.core().createThread(withUsers: [user], name: tile.symbol!, threadCreated: {(_ error: Error?, _ thread: PThread?) -> Void in
        if error == nil {
            let chatViewController: UIViewController? = BInterfaceManager.shared().a.chatViewController(with: thread)
            self.navigationController?.pushViewController(chatViewController!, animated: true)            }
        else {
            UIView.alert(withTitle: "Error", withMessage: Bundle.t("Cant create Symbol Thread"))
        }
        MBProgressHUD.hide(for: self.view, animated: true)
    })

And I see this in the source code for .createThread:

    // If there are only two users check to see if a thread already exists

If the thread doesn't exist yet and I am click since I am the only "user" at the time viewing the thread it will always create a new one. Why are you checking for "two users" ?

@bensmiley
Copy link
Contributor

bensmiley commented May 1, 2017

Imagine a user User A is chatting to User B. Now User B exists the thread and creates a new thread and adds User A. In this situation we would have two threads between User A and User B which doesn't make sense. In this case, the app will just return the existing thread rather than creating a new one.

This is only the case with 1-to-1 threads because group threads are naturally flexible and it would make sense to have two different group threads even if they had the same users - maybe about different topics.

@jimijon
Copy link
Author

jimijon commented May 1, 2017

ok, right. So..... how do I create a group thread? What is the syntax? I swear I looked all around the code (which is a good thing). I need to have open topic chats that don't go away.

Thanks

@bensmiley
Copy link
Contributor

You just need to pass in more than two users.

@simonsmiley64
Copy link
Contributor

simonsmiley64 commented May 1, 2017

Just to extend:

You can see below that you are creating a thread with only a single other user. You can use an array with more users to create a group chat: [userA, userB, userC].

BNetworkManager.shared().a.core().createThread(withUsers: [userA, userB, userC], name: tile.symbol!, threadCreated: {(_ error: Error?, _ thread: PThread?) -> Void in
        if error == nil {

You can also see the duplicate code logic in the BFirebaseCoreHandler.m:

// If there are only two users check to see if a thread already exists
    if (usersToAdd.count == 2) {
        // Check to see if we already have a chat with this user
        id<PThread> jointThread = Nil;
        id<PUser> otherUser = Nil;
        for (id<PUser> user in usersToAdd) {
            if (![user isEqual:currentUser]) {
                otherUser = user;
                break;
            }
        }
        
        // Check to see if a thread already exists with these
        // two users
        for (id<PThread> thread in [[BNetworkManager sharedManager].a.core threadsWithType:bThreadType1to1]) {
            if (thread.users.count == 2 && [thread.users containsObject:currentUser] && [thread.users containsObject:otherUser]) {
                jointThread = thread;
                break;
            }
        }
        
        // Complete with the thread
        if(jointThread) {
            [jointThread setDeleted: @NO];
            if (threadCreated != Nil) {
                threadCreated(Nil, jointThread);
                
                // We've found the thread so return
                RXPromise * promise = [RXPromise new];
                [promise resolveWithResult:Nil];
                return promise;
            }
        }
    }

You can see the logic of checking whether this thread already exists. This would be the code to modify if you wanted to change the functionality regarding this.

Simon

@jimijon
Copy link
Author

jimijon commented May 1, 2017

In my use case, I want to have say lobbies. A lobby needs to be created and not destroyed no matter how many "users" are currently in that lobby chatting.

The question becomes, how do I bootstrap the lobby? It would seem I need a method to create a chat group with a specific unique string code. What happens in your code then if it is an empty lobby at the moment and a user wants to chat?

My other chat had: FIRDatabase.database().reference().child("channels/INDX420") which allowed easy chat group creation.

Maybe another method like:
createGroupChat ( stringID: "MyGroupChat") etc.

Would this cause other downstream problems?

@bensmiley
Copy link
Contributor

bensmiley commented May 2, 2017

Actually this functionality would be better provided using the public chat type. Public chats are like lobbies - when a user joins, they are added to the room's user list. When they leave, they are removed from the list.

-(RXPromise *) createPublicThreadWithName:(NSString *)name

There are a number of ways to create these rooms initially, you could just hard code it into the app so if the public room doesn't already exist, the app tries to create it. Or you could just replicate this code:

[[BStorageManager sharedManager].a beginUndoGroup];
id<PThread> threadModel = [[BStorageManager sharedManager].a createEntity:bThreadEntity];
    
threadModel.creationDate = [NSDate date];
    
id<PUser> currentUserModel = [BNetworkManager sharedManager].a.core.currentUserModel;
    
threadModel.creator = currentUserModel;
threadModel.type = @(bThreadTypePublic);
threadModel.name = name;
    
[[BStorageManager sharedManager].a endUndoGroup];
    
// Create the CC object
CCThreadWrapper * thread = [CCThreadWrapper threadWithModel:threadModel];
    
return [thread push].thenOnMain(...

You can explicitly set the thread's entity id before you push it. This approach has the added benefit that the thread would never be added to the public threads list so it would essentially be a hidden public chat room. You could provide the list of lobby IDs from a server API or a config file accessed by the app.

@jimijon
Copy link
Author

jimijon commented May 4, 2017

I could use a Swift Version as I am not familiar with RXPromise.

    public func createPublicThread(withName name: String!) -> RXPromise!

How does a promise get turned to a Thread?

Anyway, my confusion also lies in the concept of the entityID. Where is that being set? It wasn't obvious to me perusing the code.

Also do I first need to check for this thread.entityID before I create?

Thanks

@bensmiley
Copy link
Contributor

I added a new function to the codebase so your code would look like this:

let promise = BNetworkManager.shared().a.publicThread().createPublicThread(withName: "Name", entityID: "entity id", isHidden: true)
        
 _ = promise!.promiseKitThen().then { (result: Any?) in
    if let error = result as! Error? {
            
    }
    else {
        if let thread = result as! PThread? {
            
        }
    }
    return AnyPromise.promiseWithValue(result)
}

There is also a function that converts an RXPromise to a PKPromise which has nicer Swift syntax.

@jimijon
Copy link
Author

jimijon commented May 8, 2017

Yes! Thank you.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants