 So you may have used one of my plugins which are hosted in this site So if you've seen that before but no didn't know that was me Now you know and that's the same name persistence also my Twitter handle, which is also not necessarily off obvious I've been talked to the breakout session yesterday about Qunit and test swarm Which I hope by the next jQuery conference where I've got like a full session about there's some really cool stuff going on there I also work on jQuery UI and the one line beta is finally out and so one line final is not far away but today what I want to talk about is something really else it's about single page applications and Instead of reading out this definition from Wikipedia. I just want to show some examples. This is kind of the Probably the best known example of a web application and then by whatever definition of single page application That's probably a price here like it's Gmail. It's a male client running on the web And you can fully control it with a keyboard if you enable the keyboard shortcuts It's pretty awesome that that's not necessarily something to aim for like this a lot of room between like a Simple page that may have some interactions and the full-blown applications like Gmail something I've worked on Like half last year is the Mobile up SoundCloud website. Yeah, don't know SoundCloud. It's best described as YouTube for audio and What it basically does is let's you listen to audio on the web and Anyone can can upload stuff and shared with friends or shared with other people and the rest of the internet And here on the screen to the left You can see the player page with like a Place big audio and you can see that the progress with your waveform Which is kind of the icon of SoundCloud and Instead of just having to play backstop when you click on somewhere something else because you are looking for some other sounds It'll just continue playing in the background So on the screen to the right you can see the now playing link at the top if you would click on that you get back to the Play and it's still active. So on this case signal page obligation makes a lot of sense because you want to have things Go on in the background while they still browsing content Something else I worked on a few month ago as a control panel for a cloud hosting provider from Berlin This is very different from what SoundCloud is doing, but it's it's interesting application on the left You can manage applications deployments deploy from git to their cloud hosting service can get statistics It's a single page application, but otherwise doesn't really have that much in common with like SoundCloud or Gmail But what both have in common is that they both basically JavaScript application running on the client and they use of JSON API is a screenshot from from flickers API documentation Which is probably one of the oldest and Maybe best known JSON APIs for the sound of mobile site We were using their API and basically you can for any user you can get their tracks or for a track You can get comments or stuff like that It's basically like a wrapper around the database and the database doesn't necessarily have to be like a single database can Like come from different sources Something else these two examples like SoundCloud and this this console had in common that we're both using backbone as the framework Along with jQuery and some other stuff that for like structuring the application Figuring out what to load when and how to display it back bone Was being used It's this is certainly not the only framework Though when we started early 2011 on the sound like sound on mobile site There wasn't that much choice and even backbone was still pretty early in development But now there's ember which who does involved with this angle a JS just like to people with Google are developing and I didn't use any of them yet. So I can't really tell you that much about them But what I can tell you like using one of these frameworks can certainly make a huge difference compared to Starting from scratch, especially if you haven't like build a full JavaScript application before So with those in mind there the opportunities that I like the title mentioned opportunities What are those I give it the first one is that the simple up this is pretty simple application architecture because Basically you have some static files a JSON API on the server and then you build your application on the client and it can run on all these mobile web clients of roses You can get a better user experience because you can get rid of all the page reloads and so Other interaction that become possible that weren't really possible before like playing audio in the background or whatever else you You want to do and this instinct frameworks like like born in the other dimension so that should sound pretty good, right and See I've got a few more of those. I don't know if they're as funny as Dave's bit. I'm trying First thing I want to mention of the like the pitfalls which I'm not going to cover that much You shouldn't underestimate what it means to build a full application in JavaScript So far you've basically like build stuff on the server and then you've sprinkled some jQuery on top That's very different from doing everything in JavaScript. It's a Whole new challenge so Listening to people to talk about application architecture or testing all that stuff or bring it up like trying out these these frameworks It makes sense. It's definitely useful with it. It's not what I'm going to cover here instead I want to cover like a few of these opportunities and see What pitfalls there? to start with first third will be basically about why hashbang sucks and what you should you should use instead Why having a first page load in really slow is not not good And what you should do about error handling and For all of these I have examples I would show some of the code but not all of them Nonetheless the code is all in GitHub So I'll give you a link later on so if you want to to see the example in detail and try them out yourself They were rather than you can can do that later So to start with this first one User experience really getting better because there's actually some room for making good ways so I'll give you an idea of that. Here's Our fake classic page, which is like just a regular website. There's a link there where you can see Kitten details, so if you click on that and get kitten details Just a place order bit important part here is the red underline here the slash details So the rest change because it's just a link and the browser loads another page the dress changes Let's say we built that from scratch as a single application using backbone and whatever else And we've got the same link and then we load some details Maybe the details load we eject but you get Jason back and then show something and If we have been careful or don't pay attention or don't use a framework They already handles that whereas we end up with just the same URL So it doesn't change even though the content chains the UL stays the same and this is Little subtlest that may look like it's actually pretty big problem because it means You know click on the back button nothing happens Maybe we get to the page like the Google search result or something, but we don't get to the start page again if we go back and like do Command or control click depending on the system to open that link in new tab, which pretty much works everywhere It would just do the same thing as the regular click So we can we break like native behavior, which is not a good thing because the few things that people learn about how browsers work if we break those expectations actually make things worse and One more thing by actually addressing this problem We open up in a few other opportunities that I'll get to like in the second part, but for now Let's look at some HTML specifically the HTML 5 history API that can help us address this problem Before we look at the API and the details for that use that chart from can I use comm and pretty awesome site showing you support for all kinds of new features in browsers As you can see I will support in I attend the history API, but current rosas don't so we may need to fall back there Actually, we can get get away with not doing it. I'll talk about that the next part And Android 4 and 3 have kind of a broke implementation, but they're now going to replace the crappy browser anyway with chrome on Android So that's kind of getting addressed as well So overall the support is pretty good like this other HTML 5 features where the situation is much worse But we still need some work around some bug fixes because the vendors can't really agree on some details of this back. So If I look at those options, here's a quick overview of the API, which is actually really simple there's the push state method which When you call that we'll use that fragment that you provide as the last argument this to others which are mostly completely Revolent but they made into the spec and now they can remove it But what this does is add a new history entry to the history stack and change the address Which is something that you there's no way to like do that with JavaScript without The browser supporting it so you can't really like you can't write a poly in true poly for that So that's why it was so frustrating for IE 9 not to support that because the API is really simple There's an alternative replace state which also changed the address But that does not add a history and you just replace the current one. There are a few edge case where that is useful But like push state is really the important method here And in order to know when the for example the user presses the back button We can listen to the pop state event And that's where the inconsistency start because like Mozilla things that everyone else is wrong about how when the pop State event should be triggered and everyone else thinks Mozilla is wrong and they can so far couldn't agree on One way or the other so we have to deal with some inconsistency there So libraries can actually help address those history. Yes, this One from Benjamin Bolipton. He's an Australian and he read this really comprehensive library that pretty much covers all the things there Probably addresses by now too many bugs that we don't even care about more like some regression in Chrome 4 Whatever no one use that anymore if you use backbone, you should opt into the push state support that got landed like about a year ago That makes a lot of sense and what I'm going to use in the example tab here something I actually wrote for this talk It's called simple history. Yes, it's just a thin wrapper around the API Just getting rid of the few inconsistencies but not doing like hash change fallbacks And not being a framework of its own. It's really just a small really small library and the API is pretty simple to What the original history API looks like so pushed every place data pretty much the same except they get rid of the completely useless title argument And instead of binding to a pop state event with at the event listener You just pass a callback to the start method and that'll deal with the normalization of the push pop state event so If you've never like seen push state before I want to show you an example, but that actually looks like in practice See if I can get this Going back to cloning Okay, so I've got this really simple Application here and in order for you to believe me that this is actually like running Stuff as a single page up against not just relearning a page got this audio element here Which should play back when I click on play So can like if you keep an eye on that you can see it's running and if I click on one is images Like this is basically gallery application that will continue running. So and I can go back and Still the same thing. So it's actually replacing content the client But if I do that again, you can see that the URL here actually can change like it's just a regular URL There's no no hash involved It's a separate address and as you can see I can use the back button to go back. So This is basically what the push state API is about once you Understand that it's really stupid simple, but it's extremely useful and something that makes building these type of applications a lot more pleasant and We can just like reload the page and we get the same page again and The same thing also works fine on is so again here should be able to play back the audio thing Okay, so audio also works and again and can change the address and can see Updated and if I go back and still playing back the audio Except now it doesn't show it anymore Yes, and like the native audio element you probably shouldn't use it but Good enough for this demo so They code involved in that It's two pieces. I want to quickly show you so this deals with handling clicks So it assumes that your anchors on the page just point to regular you else You don't make anything special for this JavaScript location just regular URLs And whenever we click on one of these we ignore everything that points to some like other server But if it's in like a local click we'll handle it and the first thing to check is The events has like this meter key shift key or control key property set which basically means The users trying to do something special. So let's ignore that. So just let the browser handle So that actually makes the control click work Like it's supposed to otherwise we prevent in the default just calling event brief event default and then call It simply is to push state passing the href of that link. We just click and That's all the actual handling of what to show next is handle elsewhere so that's when the code you find this this Call to the start method and when you do that whenever push states or the pop set event is triggered then your call begs run and you can Use the URL argument to figure out what what are you supposed to show next? see it's basically Take the URL do some client-side routing and figure out what content to show in this case the actual application is really stupid Simple it basically just figures us this is the index page if show show that otherwise show an image If we show an image use this photos dot look up call to just update an image element It's just an example nothing like production ready, but it does trick so I mentioned has changed before and that they actually not such a great idea and You're most likely to have seen them on Twitter for a year now or something So whenever you go to Twitter comm slash persistence You will end up on this slash hash bang slash persistence Which actually pretty annoying because when you really look that page it'll like open the Twitter homepage and then figure out Hey, there's a hash and I should actually load something else because the the hash parts never available in the server without doing some JavaScript workarounds so might be okay to use as a fallback but Probably shouldn't even do that so I'll show you soon and I have this chance to talk to Dan web who basically was responsible at Twitter for like undoing all the hash bank change stuff on Tuesday and They actually figured out that they don't want to have the hash change for even not even as a fallback so Twitter doesn't do that anymore so and Explain why that actually works. So but what you keep in mind use push date and try to not even bother with hash change So but then we have this other thing about the first page load like Really doesn't have to take 10 seconds or 15 seconds to load like a Twitter status update where it's just 140 characters that shouldn't take that long and This guy says if you like load a page then you should make a good impression So and what it comes down to is going back to the server and rendering content on the server Which may sound like a bad idea because now our simple application architecture actually gets not so simple because now We have to do things on the client and on the server So but it actually it's not even that bad because there are few opportunities to to make make use of this dual thing On the one hand assuming that you have this Jason API already just use it on this server There's no reason why your server should use a different API from your client Just use the same thing and you basically just have less network latency in between Whenever you have like templates it should be just matter of HTML with a few placeholders show There's no reason why you shouldn't be able to render those on the server as well and Where it gets even more interesting if you have a platform on the server that also runs JavaScript You might even be able to share a lot more code with the client and Luckily, we now have no JS and while this isn't the official logo. I like it much more We can actually run this stuff on the server just and share share code between client and server and again I'll switch to showing you a quick example and For that it's basically just show the same stuff that before this time around I'll show you this the source of each page, so Just reload once and then this thing about your source here is It's always Rendering stuff from the server so you don't will like doesn't show any DOM modifications So what you can see here is pretty much just like the list of images and that below here There's this placeholder with an empty empty image element might be not such a great design But it makes it some like the JavaScript update this makes it pretty simple now if we go back Click on one of these links and you use source again It's still run this at that same list because it was lazy But the difference is now will actually have the image element in the markup again. So Because it the same stuff on the Coming down from the server just with content this time around we can still just use that and money fight from JavaScript So if I go back and load another page, it'll just use that same image element and put something else in there and I'm going to skip over the note parts of this like if you if you work with no JS before It's would probably be pretty boring if you had never seen it before Probably like showing you just a few code slide probably wouldn't help either so Again the code is available on GitHub What I'm going to show here is just a bit of JavaScript that is explicitly shared between the two two sides here So you can see this if type of exports Not equal to undefined. This is basically detecting Hey, we're running in a Node.js environment because node has this export object So let's yet use that to export our data and methods and otherwise It'll just declare a new variable in this case just global and export stuff through that So in the end we can use that same photos dot lookup method both on the client and server Which in this case is not extremely helpful because it's just doing some filtering but again Again, this is just an example. So in the extra application you might be able to share a ton of code between client and server and Instead of trying to figure out all of that from scratch There's actually quite a few frameworks available now that Explicitly about let's build this application once and run it both on the client and server I haven't used any of them so I can't really talk much about that But along with this all the example source codes I've also have a list of links where I can find a few of these But for now, let's just keep in mind so the set rendering can be really helpful to address the slow first page And that's pretty much what Twitter is doing like in IE. They just always have Like servers that rendering they basically don't do anything too much anymore on the client Which also actually helps address stuff like search up to search engine optimization where Someone comes up. Hey, we've got the single page application They has changed and like Google the Google bot doesn't see our content So rendering content on the server means you don't have to do anything special for that stupid crawler That's that what could possibly go wrong and I've got a little illustration here Except this is not the quote I was looking for so I adopted that slightly In browsers, no one can hear your code screen Basically when this happens Like something throws up This might happen except it's like the tree falling in the forest when no one is looking you don't see it And your client probably won't like your users don't look at the console to see what your application is doing except they happen to be up developers So what can we do about that like? This is actually a big deal because whenever something goes wrong You won't know about it your client might complain. Maybe not maybe just goes on to your competition So it's really important to deal with error handling. I'm just basically Catch errors on the client send them back to to the server to your server or some third-party server And you forget a lot of these errors. You actually have to deal with aggregation To get back to in a little bit to start what what type of errors do we have to deal with? There's syntax errors in JavaScript, which should be really easy to catch even before any of you just see application So if you like test locally and then like build your applications Maybe some JavaScript notification deploy it to a staging server even to your left server and take a look yourself There's something really wrong. You get in syntax error and you'll notice so nothing really we really have to worry about at runtime Though what we have to worry about is type errors because those are much more like to cure under some random conditions Which we can't necessarily test for so dealing with those is pretty important and the same goes about Ajax errors, which depends like can depend a lot of network But it might also be just like use it mistyped a URL or a server may have something maybe doing something wrong Which we don't know about so Being aware at least what errors occur and then to sign into ignore certain errors. That's also important here's Some little scope snippet to test like a Ajax and a type error because the Ajax request is actually asynchronous the 404 that this causes will come afterwards and and so let's see how we can we can handle the type errors and While I generally try to avoid the term best practice I think this is pretty much at least the best current practice on on handling errors You should not use jcrease bind or on method to bind to error event because you actually use that those three arguments message File in line, which are really really useful just knowing that an error queue it is completely useless if you don't have any context about it and You may notice the first line in the handle itself actually kills itself So if like something in the loop occurs, we only get notified about it once otherwise a single client may spam our Logging service, which is generally not useful You can do the same thing with Ajax errors Of course, you're assuming that you use jcrease and using the one method to bind just a single Ajax error event and then just using the arguments that you get to lock an error And the lock error method that these two using could look like this again using jcrease You just post something back to the server Which of course won't work when the network is down So if you're dealing with Ajax errors that are triggered by Ajax like network problem Then sending back to the same server or we won't help I'll skip the example here because it's not really that interesting but What I want to talk a little bit more about and the aggregation options so Mention before if you're dealing with it like that that's that cloud hosting application There's like another 20 people using that right now. So there's not a lot of errors So aggregation is not really important But on the other hand with sundot mobile which like went from 70,000 to like a 200,000 views per day We ended up with a few thousand errors in a few days So like figuring out which of those are the same and which are unique and which should we deal with They turned out to be pretty important So either you just roll your own solution or if you're using something like Google Analytics or some other analytics software You may be able to to use that. So for example by triggering custom events Which are kind of like jcre custom events except with its analytics tools and If you want to use that here's an adapted log error method which uses Google Analytics weirds area-based API where the first argument is basically method calls So we want to track an event and then we just pass on these other arguments and we can She didn't know this was supposed to have a screenshot what that looks like sorry other tools available are for example outbreak and bug sends Those are third-party service mostly about tracking errors from your server side application But you can actually use them to track client side errors as well. Here's a screenshot from air break And again along with the code examples. I've got a few resources There's someone at sound that had to write a blog post about how we were using I think but like covering both air break and bug sends For doing this kind of logging, but what whatever you end up using It's the most important point is to actually catch all those errors and bringing out to deal with them So that said Is that all worse to the trouble? and to recap like the better user experience But by removing pay tree loads As long as you pay attention to other things that you might break in the process and fix those Yeah, we can get a better user experience and we can still make a good first impression If that's important for our particular application, which is not always the case for Twitter Obviously is for others might not be but it's generally good idea to have a first good first page load And if we deal with errors, we can also Provide a pretty stable product. So yeah, I think it's worth it and with that I'm pretty much done. Yeah, so here's here the links for the examples There's something forgot here if you got feedback for this particular talk Welcome to have any feedback for this survey or just ping on Twitter or something emo and we have like six minutes left for questions So if you have any let me know I have a question about the error handling Um So the In JavaScript if you catch the exception will it still be caught by the window when you do on-air? so if JavaScript developers trying to prevent the console from logging the exception to be visible to the user Would it still be caught and sent to the server so if you Like if all your code is wrapped into the tripod and you catch all exceptions then no it won't pop bubble up so if you have a tripod and catch catching all exceptions and The global handle would but if you have that try blocking place You might as well just use the catch block to lock the error instead of having it bubble up So that should make that much of a difference just the approach to how to deal with the errors slightly different But generally I think it's not a really good idea to have everything wrapped in a trial block because if you're dealing with like modern Jt engines like v8 They actually opt out of a lot of optimizations if you have everything in the tri-trip lock, so That's generally not such a great idea So I think you mentioned that Twitter has figured out a way to avoid using the hash bang hack But I don't know that you mentioned what that method is I'm wondering if you could share that with us So what they're basically doing it now is they don't use hash bank anymore And if they like find a hash on the client that's supposed to be like an old-style URL They're just rewrite that to a proper URL and they don't have the test change fallback at all Which basically means if you use Twitter at least Sooner they they actually done with those changes on like I nine It'll basically do fall back to always do service at rendering and because they actually optimized for that to some degree. It's Pretty fast anyway So it's not that much of a difference and like Twitter doesn't have to play big audio in the background So they don't really care about I nine not supporting has changed. I'm sorry not supporting push state So I'm actually working in a full full request Environment and I've been switching over and right now I'm kind of in a hybrid environment where some pages have our single our single page applications But I have multiple like small single page applications Okay, and I've been wondering about you said Twitter. They do a single page app But they had also falls back the the back-end will serve up the entire thing I was wondering if there's any like good solutions out there to help It seems like you have to get a lot of communication Are you almost doubling all your code that you would have had on the front end on the back end so that you can have this fallback Behavior or if somebody renders the page and I was wondering if there's any good solutions or ways to make that a little bit smoother for me so there's Their frameworks available that basically helped you like share the code So like I think one is like meteor.js, which is basically all about writing stuff once and then having it run on both sides I think what Twitter is now doing is basically when you click on the Like push state enabled link they actually send wall as the same request that it would otherwise send to the server with a regular Request and that looks at the headers sees hey, this is a true request So let's only send like the the body of the page and skip the like the headers and stuff They just dump dump that into the page and they even I think what they also do is Use the push state state argument to just reference this this blob of HTML And if you use the back button and we actually look that content again So they basically just use the same like they don't really don't even run a template on the client. They just Render them all those in the server and use Ajax to look them Which is I get I mean it's it's probably a pretty simple solution. So that's that's generally good idea But then Twitter is not necessarily the typical single-page application either So I have a question that I'm hoping you can help me with how tall are you I? Don't know in foot or inches because we don't use that silly system in Germany 194 very I think I think that's it so one more round of applause for yarn