diff options
author | dequis <dx@dxzone.com.ar> | 2014-10-10 23:20:53 -0300 |
---|---|---|
committer | dequis <dx@dxzone.com.ar> | 2014-10-10 23:20:53 -0300 |
commit | 7b40f17f9f514127c8a37c35ac3d1c3bd34c13d5 (patch) | |
tree | 2297eb213f70e0e5cc7ce50e878f805a47f55ad7 | |
parent | 0e35ff67f314fb11522430e17d607ac4f5c13c90 (diff) |
Add support for XEP-0203: Delayed delivery (message timestamps)
Very similar to XEP-0091 which is already supported, but was marked as
obsolete, replaced by XEP-0203. The main differences are the tag name
and the timestamp format.
Due to the similarities, both XEPs are still supported.
-rw-r--r-- | lib/xmltree.c | 15 | ||||
-rw-r--r-- | lib/xmltree.h | 1 | ||||
-rw-r--r-- | protocols/jabber/jabber.h | 3 | ||||
-rw-r--r-- | protocols/jabber/jabber_util.c | 30 |
4 files changed, 38 insertions, 11 deletions
diff --git a/lib/xmltree.c b/lib/xmltree.c index 0726d387..9d84fb7c 100644 --- a/lib/xmltree.c +++ b/lib/xmltree.c @@ -523,6 +523,21 @@ char *xt_find_attr( struct xt_node *node, const char *key ) return node->attr[i].value; } +struct xt_node *xt_find_node_by_attr( struct xt_node *xt, const char *tag, const char *key, const char *value ) { + struct xt_node *c; + char *s; + + for( c = xt; ( c = xt_find_node( c, tag ) ); c = c->next ) + { + if( ( s = xt_find_attr( c, key ) ) && strcmp( s, value ) == 0 ) + { + return c; + } + } + return NULL; +} + + /* Strip a few non-printable characters that aren't allowed in XML streams (and upset some XMPP servers for example). */ void xt_strip_text( char *in ) diff --git a/lib/xmltree.h b/lib/xmltree.h index a41cbac1..aaf49cea 100644 --- a/lib/xmltree.h +++ b/lib/xmltree.h @@ -91,6 +91,7 @@ void xt_free( struct xt_parser *xt ); struct xt_node *xt_find_node( struct xt_node *node, const char *name ); struct xt_node *xt_find_path( struct xt_node *node, const char *name ); char *xt_find_attr( struct xt_node *node, const char *key ); +struct xt_node *xt_find_node_by_attr( struct xt_node *xt, const char *tag, const char *key, const char *value ); struct xt_node *xt_new_node( char *name, const char *text, struct xt_node *children ); void xt_add_child( struct xt_node *parent, struct xt_node *child ); diff --git a/protocols/jabber/jabber.h b/protocols/jabber/jabber.h index e6aa3ba3..eb99f9ca 100644 --- a/protocols/jabber/jabber.h +++ b/protocols/jabber/jabber.h @@ -228,7 +228,8 @@ struct jabber_transfer #define XMLNS_PING "urn:xmpp:ping" /* XEP-0199 */ #define XMLNS_RECEIPTS "urn:xmpp:receipts" /* XEP-0184 */ #define XMLNS_VCARD "vcard-temp" /* XEP-0054 */ -#define XMLNS_DELAY "jabber:x:delay" /* XEP-0091 */ +#define XMLNS_DELAY_OLD "jabber:x:delay" /* XEP-0091 */ +#define XMLNS_DELAY "urn:xmpp:delay" /* XEP-0203 */ #define XMLNS_XDATA "jabber:x:data" /* XEP-0004 */ #define XMLNS_CHATSTATES "http://jabber.org/protocol/chatstates" /* XEP-0085 */ #define XMLNS_DISCO_INFO "http://jabber.org/protocol/disco#info" /* XEP-0030 */ diff --git a/protocols/jabber/jabber_util.c b/protocols/jabber/jabber_util.c index 0fcc8338..fb68c33d 100644 --- a/protocols/jabber/jabber_util.c +++ b/protocols/jabber/jabber_util.c @@ -725,19 +725,29 @@ time_t jabber_get_timestamp( struct xt_node *xt ) struct xt_node *c; char *s = NULL; struct tm tp; - - for( c = xt->children; ( c = xt_find_node( c, "x" ) ); c = c->next ) - { - if( ( s = xt_find_attr( c, "xmlns" ) ) && strcmp( s, XMLNS_DELAY ) == 0 ) - break; + gboolean is_old = TRUE; + const char *format; + + /* XEP-0091 has <x> */ + c = xt_find_node_by_attr( xt->children, "x", "xmlns", XMLNS_DELAY_OLD ); + + if( !c || !( s = xt_find_attr( c, "stamp" ) ) ) { + is_old = FALSE; + + /* XEP-0203 has <delay> */ + c = xt_find_node_by_attr( xt->children, "delay", "xmlns", XMLNS_DELAY ); + if( !c || !( s = xt_find_attr( c, "stamp" ) ) ) { + return 0; + } } - if( !c || !( s = xt_find_attr( c, "stamp" ) ) ) - return 0; - memset( &tp, 0, sizeof( tp ) ); - if( sscanf( s, "%4d%2d%2dT%2d:%2d:%2d", &tp.tm_year, &tp.tm_mon, &tp.tm_mday, - &tp.tm_hour, &tp.tm_min, &tp.tm_sec ) != 6 ) + + /* The other main difference between XEPs is the timestamp format */ + format = (is_old) ? "%4d%2d%2dT%2d:%2d:%2d" : "%4d-%2d-%2dT%2d:%2d:%2dZ"; + + if( sscanf( s, format, &tp.tm_year, &tp.tm_mon, &tp.tm_mday, + &tp.tm_hour, &tp.tm_min, &tp.tm_sec ) != 6 ) return 0; tp.tm_year -= 1900; |