Add a class for handling JIDs.

This commit is contained in:
Florian Zeitz 2011-02-13 01:36:25 +01:00
parent b64ae746e6
commit 6dc9e5e217
5 changed files with 200 additions and 4 deletions

View file

@ -1,6 +1,6 @@
all: tests/tests all: tests/tests
tests/tests: tests/test.m src/XMPPConnection.m src/XMPPStanza.m tests/tests: tests/test.m src/XMPPConnection.m src/XMPPStanza.m src/XMPPJID.m
objfw-compile -o $@ $^ -lidn -Wall -Werror -Isrc objfw-compile -o $@ $^ -lidn -Wall -Werror -Isrc
clean: clean:

View file

@ -1,4 +1,5 @@
#import <ObjFW/ObjFW.h> #import <ObjFW/ObjFW.h>
#import <XMPPJID.h>
@class XMPPConnection; @class XMPPConnection;
@class XMPPIQ; @class XMPPIQ;
@ -25,7 +26,7 @@
OFXMLElementBuilder *elementBuilder; OFXMLElementBuilder *elementBuilder;
/** /**
* The username (local part of the JID) to connect with * The username to connect with
*/ */
OFString *username; OFString *username;
@ -44,6 +45,11 @@
*/ */
OFString *resource; OFString *resource;
/**
* The JID bound to this connection (this is determined by the server)
*/
XMPPJID *JID;
/** /**
* The port to connect to * The port to connect to
*/ */
@ -61,6 +67,7 @@
@property (copy) OFString *password; @property (copy) OFString *password;
@property (copy) OFString *server; @property (copy) OFString *server;
@property (copy) OFString *resource; @property (copy) OFString *resource;
@property (readonly) XMPPJID *JID;
@property (assign) short port; @property (assign) short port;
@property (assign) BOOL useTLS; @property (assign) BOOL useTLS;
@property (retain) id <XMPPConnectionDelegate> delegate; @property (retain) id <XMPPConnectionDelegate> delegate;

View file

@ -13,6 +13,7 @@
@synthesize password; @synthesize password;
@synthesize server; @synthesize server;
@synthesize resource; @synthesize resource;
@synthesize JID;
@synthesize port; @synthesize port;
@synthesize useTLS; @synthesize useTLS;
@synthesize delegate; @synthesize delegate;
@ -218,8 +219,9 @@
if ([bindElem.name isEqual: @"bind"] && if ([bindElem.name isEqual: @"bind"] &&
[bindElem.namespace isEqual: NS_BIND]) { [bindElem.namespace isEqual: NS_BIND]) {
OFXMLElement *jidElem = bindElem.children.firstObject; OFXMLElement *jidElem = bindElem.children.firstObject;
of_log(@"Bound to JID: %@", [jidElem.children.firstObject JID = [[XMPPJID alloc] initWithString:
stringValue]); [jidElem.children.firstObject stringValue]];
of_log(@"Bound to JID: %@", [JID fullJID]);
} }
} }

60
src/XMPPJID.h Normal file
View file

@ -0,0 +1,60 @@
#import <ObjFW/ObjFW.h>
/**
* \brief A class for easy handling of JIDs
*/
@interface XMPPJID: OFObject
{
/**
* The JID's localpart
*/
OFString *node;
/**
* The JID's domainpart
*/
OFString *domain;
/**
* The JID's resourcepart
*/
OFString *resource;
}
@property (copy) OFString *node;
@property (copy) OFString *domain;
@property (copy) OFString *resource;
/**
* Creates a new XMPPJID
*
* \return A new autoreleased XMPPJID
*/
+ JID;
/**
* Creates a new XMPPJID from a OFString
*
* \param str The string to parse into a JID object
* \return A new autoreleased XMPPJID
*/
+ JIDWithString: (OFString*)str;
/**
* Initializes an already allocated XMPPJID using a OFString
*
* \param str The string to parse into a JID object
* \return A initialized XMPPJID
*/
- initWithString: (OFString*)str;
/**
* \return A OFString containing the bare JID
*/
- (OFString*)bareJID;
/**
* \return A OFString containing the full JID
*/
- (OFString*)fullJID;
@end

127
src/XMPPJID.m Normal file
View file

@ -0,0 +1,127 @@
#include <assert.h>
#include <stringprep.h>
#import "XMPPJID.h"
@implementation XMPPJID
@synthesize node;
@synthesize domain;
@synthesize resource;
+ JID
{
return [[[self alloc] init] autorelease];
}
+ JIDWithString: (OFString*)str
{
return [[[self alloc] initWithString: str] autorelease];
}
- initWithString: (OFString*)str
{
self = [super init];
size_t nodesep, resourcesep;
nodesep = [str indexOfFirstOccurrenceOfString: @"@"];
resourcesep = [str indexOfFirstOccurrenceOfString: @"/"];
if (nodesep == -1)
[self setNode: @""];
else
[self setNode: [str substringFromIndex: 0
toIndex: nodesep]];
if (resourcesep == -1) {
[self setResource: @""];
resourcesep = [str length];
} else
[self setResource: [str substringFromIndex: resourcesep + 1
toIndex: [str length]]];
[self setDomain: [str substringFromIndex: nodesep + 1
toIndex: resourcesep]];
return self;
}
- (void)setNode: (OFString*)node_
{
OFString *old = node;
char *nodepart;
Stringprep_rc rc;
if ((rc = stringprep_profile([node_ cString], &nodepart, "Nodeprep", 0))
!= STRINGPREP_OK) {
of_log(@"Nodeprep failed: %s", stringprep_strerror(rc));
assert(0);
}
@try {
node = [[OFString alloc] initWithCString: nodepart];
} @finally {
free(nodepart);
}
[old release];
}
- (void)setDomain: (OFString*)domain_
{
OFString *old = domain;
char *srv;
Stringprep_rc rc;
if ((rc = stringprep_profile([domain_ cString], &srv, "Nameprep", 0))
!= STRINGPREP_OK) {
of_log(@"Nameprep failed: %s", stringprep_strerror(rc));
assert(0);
}
@try {
domain = [[OFString alloc] initWithCString: srv];
} @finally {
free(srv);
}
[old release];
}
- (void)setResource: (OFString*)resource_
{
OFString *old = resource;
char *res;
Stringprep_rc rc;
if ((rc = stringprep_profile([resource_ cString], &res,
"Resourceprep", 0)) != STRINGPREP_OK) {
of_log(@"Resourceprep failed: %s", stringprep_strerror(rc));
assert(0);
}
@try {
resource = [[OFString alloc] initWithCString: res];
} @finally {
free(res);
}
[old release];
}
- (OFString*)bareJID
{
if ([node length])
return [OFString stringWithFormat: @"%@@%@", node, domain];
else
return [OFString stringWithFormat: @"%@", domain];
}
- (OFString*)fullJID
{
if ([node length])
return [OFString stringWithFormat: @"%@@%@/%@",
node, domain, resource];
else
return [OFString stringWithFormat: @"%@/%@",
domain, resource];
}
@end