MUC How-to with XMPPFramework

10,936

Solution 1

Below is how I got my own problem solved. Note that this solution does not involve XMPPRoom at all. First, I created a method that, depending on the situation, either creates or enters a room. (Per XMPP documentation, the XML request for creating is the same is the same as the one you would send to enter a room; that is, if the room has does not exist yet when you enter it, the service will create it for you.)

Here we go. This is the method that creates/enters a room. What this method does is send a presence to the room which you intend to create/enter. If you are the first to enter a room and the room has not been created yet, you automatically become its owner and moderator.

- (void)createOrEnterRoom:(NSString *)roomName
{
//here we enter a room, or if the room does not yet exist, this method creates it
//per XMPP documentation: "If the room does not yet exist, the service SHOULD create the room"
//this method accepts an argument which is what you would baptize the room you wish created
NSXMLElement *presence = [NSXMLElement elementWithName:@"presence"];
NSString *room = [roomName stringByAppendingString:@"@conference.jabber.com/iMac"];
[presence addAttributeWithName:@"to" stringValue:room];
 NSXMLElement *x = [NSXMLElement elementWithName:@"x" xmlns:@"http://jabber.org/protocol/muc"];
NSXMLElement *history = [NSXMLElement elementWithName:@"history"];
 [history addAttributeWithName:@"maxstanzas" stringValue:@"50"];
 [x addChild:history];
 [presence addChild:x];
 [[self xmppStream] sendElement:presence];
}

Next, in the AppDelegate where XMPPStream methods are declared we filter the XML response we receive in the didReceivePresence method by checking the status code sent by the server. If the status code is 201, bingo! The room creation went just fine. Status codes other than 201 mean different things, but let's focus on 201 for our purpose.

- (void)xmppStream:(XMPPStream *)sender didReceivePresence:(XMPPPresence *)presence
{
     NSXMLElement *x = [presence elementForName:@"x" xmlns:@"http://jabber.org/protocol/muc#user"];
    for (NSXMLElement *status in [x elementsForName:@"status"])
    {
        switch ([status attributeIntValueForName:@"code"])
        {
            case 201: [self notifyRoomCreationOk:room];
        }
    }
 }

Then, we tell the server that what we are creating a room of the type "instant," which means that we will send an IQ element telling it room defaults. notifyRoomCreationOk is a delegate method called in a different view when the room creation succeeds, after all I have to record the room in a text file to make it persistent so that the next time I open the app the room I created before will be visible. In my notifyRoomCreationOk method, I have sendDefaultRoomConfig which, basically, describes what is stated in the first sentence of this paragraph.

-(void)sendDefaultRoomConfig:(NSString *)room
{
NSXMLElement *x = [NSXMLElement elementWithName:@"x" xmlns:@"jabber:x:data"];
[x addAttributeWithName:@"type" stringValue:@"submit"];
NSXMLElement *query = [NSXMLElement elementWithName:@"query" xmlns:@"http://jabber.org/protocol/muc#owner"];
[query addChild:x];
XMPPIQ *iq = [XMPPIQ iq];
[iq addAttributeWithName:@"id" stringValue:[NSString stringWithFormat:@"inroom-cr%@", room]];
[iq addAttributeWithName:@"to" stringValue:room];
[iq addAttributeWithName:@"type" stringValue:@"set"];
[iq addChild:query];
[[self xmppStream ] sendElement:iq];
}

Make sure that you have XMPPStream enabled on the views that call the above methods, otherwise, these won't work. That's all there is to it. Have fun XMPP-ing!

Solution 2

    XMPPRoom *room = [[XMPPRoom alloc] initWithRoomName:@"[email protected]/room" nickName:@"room"];
    [room createOrJoinRoom];
    [room sendInstantRoomConfig];
    [room setInvitedUser:@"[email protected]"];
    [room activate:[self xmppStream]];    
    [room inviteUser:jid1 withMessage:@"hello please join."];
    [room sendMessage:@"HELLO"];

the user [email protected] should receive the invite message

Share:
10,936
Ten Go
Author by

Ten Go

Developer of 'Dubai Culture' iOS app - awarded 'Best M-Government Service' in tourism sector by the Dubai Government. Dubai Culture is an iOS app that helps tourists get around key spots and learn about history in the beautiful emirate of Dubai, United Arab Emirates. The app utilises Apple's iBeacon technology to notify users of interesting spots nearby when they are in supported locations. App Store - https://itunes.apple.com/us/app/dubai-culture/id926793557?mt=8

Updated on June 09, 2022

Comments

  • Ten Go
    Ten Go about 2 years

    I am developing an iOS XMPP chat app that utilizes Robbie Hanson's XMPPFramework.

    The most important functionalities have been implemented - sending and receiving messages. Basically, I've built a basic functional chat app already, with a little eye candy of course.

    Now, the problem I have is regarding MUC. The codes I saw from other websites show that there is a method initWithRoomName in XMPPRoom. However, this method is absent in the git repo I cloned. So, what is the alternative to this? Or, if there is none, how do I go about creating rooms using XMPPFramework?

    Thanks.

  • Ten Go
    Ten Go about 12 years
    thank you for the answer but this is the same code that I had tried. Method 'initWithRoomName' is absent in the current master branch of XMPPFramework. I looked for this particular method everywhere to no avail. Pray tell how did you manage to get this method and which version of the framework are you using? Can you point me to a link where I can get it (framework) from? If I have the correct branch I can manage it from there. Thank you.
  • freelancer
    freelancer about 12 years
    @TenGo r u bilding chat app for local area connection or for remote?
  • Ten Go
    Ten Go about 12 years
    The app I am building works over the Internet as it will be used by team mates on the other side of the world.
  • Suresh D
    Suresh D over 11 years
    hey @Ten Go, can you share some example code for this? it's very urgent for me... Thanks in advance
  • Ten Go
    Ten Go over 11 years
    @Suresh.D, are you creating a room? I have one suggestion: read the documentation found in xmpp.org/extensions/xep-0045.html so you get an idea of how the whole room creation process goes. It's very tricky at first but once you understand the room creation sequence you will find it very simple. Afterwards, plug the code above I wrote above in your app.
  • Suresh D
    Suresh D over 11 years
    Yeah, i did samething what you said, but code state will return always 0.but when i use one to one chat, the code state will return 12.
  • greenhouse
    greenhouse almost 11 years
    @TenGo, the XMPPRoom is indeed included in the framework, it is just a little hard to find. here is the path: XMPP/Extensions/XEP-0045/XMPPRoom.h
  • Ten Go
    Ten Go almost 11 years
    @greenhouse The header I was looking for was buried deep in a branch the repo came with. I only figured it out after tinkering with Git. I was able to create a multi-user room by following documentation at xmpp.org and manually creating XML which I describe in the answer above.
  • Kishore Suthar
    Kishore Suthar about 9 years
    After that what should i do for add friends in this group or invite friends to join this group
  • Gagan Joshi
    Gagan Joshi about 9 years
    i am getting three status code . <x xmlns="jabber.org/protocol/muc#user"><item jid="[email protected]/yaye" affiliation="owner" role="moderator"></item><status code="110"></status><status code="100"></status><status code="201"></status></x>
  • Gagan Joshi
    Gagan Joshi about 9 years
    @TenGo, i ma getting status code 110, 100 and 201 at a same time what to do
  • abarisone
    abarisone about 8 years
    Please edit with more information. Code-only and "try this" answers are discouraged, because they contain no searchable content, and don't explain why someone should "try this". We make an effort here to be a resource for knowledge.