rakeshpai
Joined 17 years ago
Joined 17 years ago
XMPP is a connection-oriented stateful protocol. The connection setup process is very expensive: Connect, authenticate, advertise the list of supported client features, get the roster (contacts), and IIRC presence exchange, etc. Therefore, once you've established a connection, you really don't want it to break. Even just reconnecting is very expensive.
However, in the mobile scenario, regular connection breakage is the norm. What most mobile based clients will then do is proxy the XMPP connection on the server-side and connect to the client over HTTP instead. This is well defined in the BoSH spec (XEP:124). BoSH was originally designed for web-based clients, but happens to meet the need of the mobile use-case.
However, when it comes down to implementation, there are several optimizations that can be applied:
1. The roster exchange at the connection time is very expensive, and usually only sends data to the client that the client probably has already stored locally from a pervious session. Connection overhead can be reduced drastically if there was some way of versioning the roster and only transferring deltas. This was the OP was referring to. (Roster versioning, XEP:273).
2. Presence packets are one of the most chatty aspects of the protocol (x went offline, x is now online, etc). I've heard someone say that it constitutes about 80% of the packets on a typical connection, but this is anecdotal. In cases where the user isn't actively interacting with the client, having presence packets being sent all the time seems wasteful. One way to tackle this is to buffer up and de-duplicate the presence packets on the server, and send them in batches only when necessary. (For example, if x goes online, then offline, then online again, and then goes 'busy', the client only needs to know that x is busy.) I think this is what the OP was referring to when he mentioned the google:queue for delayed presence delivery. This alone can be a huge win for battery and bandwidth, since transferring data and processing it can be reduced drastically.
Aside: Presence is so chatty, that some mobile clients simply don't handle presence at all. Take WhatsApp for example. It doesn't show whether every person in your list of contacts is online. The assumption is that every user is online by the nature of the device, and this assumption works in the common cases. In the edge cases is where you'd need to buffer up messages. This reduces chattiness drastically, making the protocol seem much more lightweight. (WhatsApp is based on XMPP, but have spun it off into their own thing.)
Just thought I'd add these points to the discussion here, since there seemed to be some lack of understanding of the protocol. IMHO, the XML, as verbose as it is, isn't really the problem. The protocol itself is verbose and whether the transport uses XML or whatever else is of comparatively little consequence. This verbosity of the protocol (and not so much the format of data transfer) has its effect on battery life and bandwidth usage.
If it weren't for the fact that we don't get column numbers in window.error, I would have already supported source maps in http://errorception.com/ by now. I'm still looking actively for ways to include support though.
"Script Error" at line 0 only occurs in Firefox - I know, I'm in the business of collecting errors ;). It seems to happen when the JS file couldn't be parsed correctly. The cause for this usually partially downloaded files on the client trying to be passed through the interpreter.
Other than some little HTTP tweaks that can be done, there's very little else that you can do with "Script Error"s. So, we don't even bother sending "Script Error at line 0" errors to the server. For all practical purposes, it's a meaningless error.
http://floitsch.blogspot.in/2012/03/optimizing-for-v8-introd... "It turns out that some constructs are not yet supported by Crankshaft. In particular, try/catch turns off all optimizations in a function."
As chrisacky mentioned, making one HTTP post for every error is very wasteful. It's much better to buffer up such errors (Errorception does it in memory, since localStorage can be unavailable and/or full), and post them every once in a while.
As masklinn pointed out, window.onerror _is_ complete shit, so Errorception does a couple of tricks to make this slightly better. Firstly, on IE, the stack isn't lost when window.onerror is called, so it's possible to get the call stack and arguments at each level of the stack. Secondly, it's very easy to get other kind of details (browser, version, page, etc.), which helps a great deal in aiding debugging.
However, masklinn's suggestion about wrapping code in try/catch blocks is probably not a good idea. This is because some interpreters (I know v8 does this) don't compile the code in such code-paths. May cause a performance hit.
As DavidPP mentioned, depending on the nature of your application, it might be a good idea to not record too much sensitive information. For example, Errorception doesn't record function arguments if the page is served over SSL.
troels is right - this does create a massive flood of errors. There are several ways to deal with this. What we do for example, is hide away errors from most third-parties - Facebook, Twitter, GoogleBot, GoogleAnalytics, etc. The rest of the errors can still be huge in number, so we group similar errors together based on several parameters like browsers, browser versions, possible variation in inline code line-numbers because of dynamic content, etc.
Also, as Kartificial pointed out, this is probably something you don't want to do on your own server. You want to move this out of your infrastructure, and distribute it if possible.
There are other concerns - some that come to mind are page load time, ensuring that your error catching code itself doesn't raise errors (or if it does, it doesn't affect your app in any way), and that of managing data-growth on the server. These are fun problems, but it's probably not worth re-inventing the wheel.
</plug>