 So, hi everyone, welcome to the session, I am Rajshankar, I work as a level evangelist for Microsoft. In this session, we are going to very quickly look at some best practices for writing JavaScript, which is asynchronous JavaScript. So, that's, that's, you know, briefly the agenda. So, we'll see, you know, why, why this is important, why we should be worried about async, and especially, you know, from a JavaScript perspective. We'll review, you know, one of some of the problems doing asynchronous development today. And then we'll take a look at a couple of approaches for, you know, implementing asynchronous web applications using a couple of techniques, a couple of frameworks, libraries that are out there. So, you know, one is called as promises, another is a library called RxJs, which is a very interesting library. So, with that, let's see why is, you know, why is this, why is this something that's important, why should we worry about this, right? If you look at it today, you know, asynchronous, you know, it's kind of the order of the day today, right? You know, how many of you have heard of C++ Guru? His name is Herb Sutter. How many of you have heard of Herb Sutter? So, we have a few C++ people there. That's good. So, Herb Sutter is this, you know, the C++ expert who sits on the C++ standard body, you know, he's part of the standardized process. So, I think about three, four years back, he wrote a landmark paper called The Free Lunch is Over. Now, what he meant by that was, you know, for a very long time, if you look at processor technology, right, it would just keep getting faster and faster and faster, right? And we have heard of the Moves law and what not. As application developers, we really didn't have to, you know, perhaps not worry about performance quite as much, right? I mean, I can write bad code. It probably runs very slowly now. Six months later, it's going to run faster anyway, right? We don't have to worry about it. Just throw more hardware at it and it will get better. Now, you know, we got to a point where, you know, we started hitting physical limits where you just can't make processors any faster, right? Now we have multiple cores. Now, you know, you get machines with more and more processors, right? The counter process is increasing. So, as app developers, this means that, you know, we have to introduce some changes in the way we make applications. You know, we just don't rely on the hardware getting better and better. If you want to, you know, hardware is getting better but in a different way, right? If you want to leverage it, it means that you have to write your applications slightly different. You have to start writing applications that leverage multiple cores, multiple CPUs and so on. So, you know, so that's what I mean by no more free launch, right? You don't get better performance for free, right? Fast and fluid interfaces are really kind of, you know, critical for applications today, right? Gone are the days when people would put up with web interfaces which took forever to load, you know, which was not responsive, you hit a button, maybe it worked, maybe it not worked. You know, not happening anymore. We want, you know, web interfaces which respond to user interaction, right? Especially on, for example, mobile devices, right? If you're, you know, really operating in a straight environment, you want your app to run fast, right? To be responsive. Many of the HTML5 APIs that you see are coming out are, you know, missing APIs, right? For example, Index TV, WebSockets, right? Any of, pretty much any API georocation, any API that does my work, and that does input output with some device, the API is asynchronous, right? Why is that? Again, user experience is the key there, right? You don't want to make a call to some API, some browser subsystem, and have that call just, you know, take forever to return, and your browser just, user interfaces hangs, right? That's a poor user experience. Leveraging multiple cores, as I was saying earlier. The basic principle is, if you have ION CPU intensive code in your app, you can delegate that to spam codes or background processes, and so on. So, if you look in, the thing about asynchronous, if you don't like it, bad for you, get used to it. That's what you're going to have in the future, right? The good news is that our, you know, the libraries and the frameworks are catching up, right? So we are getting frameworks libraries, which kind of make this easier to do. Traditionally, the problem with doing asynchronous development is that it's hard to do, right? If you want to create applications which are multi-threaded, you have a significant thing to worry about, right? If you have shared state, you know, good luck with, you know, maintaining integrity of your data, which is shared across your multiple threads and whatnot. So, you know, in this session, we'll be looking at a couple of those approaches, a couple of frameworks. If you look at JavaScript, per se, right, there are some issues with asynchronous development as it is today. It has this tendency to turn your control flow inside out. How many of you have planned AJAX development? So, all of you. So, how does it work, right? So, you create your XML library class. You set a true, you create a handler where you're on ready state, and then, when this thing comes back, you do something in response to it. Now, if you notice, this is very different from synchronous development, right? Where you have step one, step two, step three, your control flow is just, you know, one step after another. Here, you have a case where a few things happen, and then, you know, the continuation, right? The next step is going to happen at some point in the future. But it's not a contiguous flow. This makes it hard. So, if you, you know, managing state can get hard. Handling errors can get harder, right? So, how do you cleanly handle errors in JavaScript? Because you can do try and catch, right? But if it's an asynchronous call, that means that the handler, especially if you use anonymous, you know, functions and so forth, your callbacks will get called sometime in the future. Your try-catches will have no effect on that callback, right? So, which means if you have callbacks, you're going to have to have try-catches and error handling in every single callback. So, if you're doing something in sequence, let's say I'm making a call to a Twitter service in response, once I get the response back, I'm doing something with Facebook, and, you know, then I make a call to indexTV, and then I go to a geolocation, you know, if you're doing all of these, you know, you can imagine how you can get lost in, you know, a bunch of callbacks. So, the two frameworks that we look at today are going to kind of deal with, or kind of help you deal with some of these problems. The first one is promises. So, the best way to talk about promises is to show you how it works. So, it's going to be difficult. I'm going to keep this down and talk really loud. All right, so I have a couple of demos here that kind of want to quickly show you. What I have here is, okay, let's first look at the tweets and I hope the internet works here. So, basically, all that's happening here is just, you know, making a Twitter API call and looking for a hashtag called JS2 and that's the Twitter activity that's happening right now. So, let's see what really happens there, right? So, you know, that's the, nothing major, so I just have a table, I use jQuery templates to, the key piece is over here, right? I'm calling a method called get on an object called tweets and I'm doing something interesting here. So, let me just show you what tweets does. So, that's just a script that I put together here. Very simple. So, just a regular object, you know, tweets has a method called get and I'm just using jQuery to, you know, make the Ajax request. So, I do that. I mean, all this is standard stuff, right? So, if I'm not successful, you know, I handle the, you know, handle the data that I get back from the computer service. Now, how does this communication actually work? So, traditionally what we'd have done is, you know, my API would have been, I would have probably written it like this, right? I would have said, you know, I put a callback there and then probably, you know, I would have done something like CVE of data, right? So, now when I say, you know, tweets.get, I'll pass a callback function to tweets.get and inside that callback function I'll go ahead and do the processing, you know, do the UI. Now, here it's slightly different, right? Now, that's not how it's working here. So, what have I done here? Here I've used an object called as a promise, right? So, promise is basically abstraction that it's just basically abstraction around a contact, right? It basically represents a continuation. It represents some piece of code that needs to execute at some point in the future. So, what am I doing? I'm creating a promise here and I'm returning the promise object from my get method, right? And within my error and success handlers, what I do is I just call resolve or error on my promise object. So, this is the API for generating or handling, you know, callbacks. Now, when I say resolve, I'm hoping that whoever is interested in getting tweets, they will get notified of it. So, if you look at the client code, this is what it looks like, right? So, I say tweets.get and then I say .ten, right? And then I pass a callback there and I handle that. And then, you know, I have an error handle again. Now, the interesting thing here is if you... is that promises allow you to basically escape from nested callback, right? So, here let's say what I want to do is I want to get these tweets, you know, show it on the screen. Maybe I want to take it and put it on to an index db database, right? Which is again an asynchronous call. So, now what you can do is you can say tweets.get and say then and do your processing there. And then you can notice that, you know, you can use... it's like a fluid syntax. Now, I can say on top of that, I can continue that. I can say .ten again and pass, you know, another callback where I do something else. So, here perhaps I'll, you know, go ahead and use an index db API and then, you know, save it to the... save it to my index db. And then I can keep going like that, right? I can say then and, you know, do the next thing. So, basically the promise framework kind of takes care of making sure that your, you know, your callbacks are executed in the correct sequence, right? So, that takes care of nested callbacks, right? You don't have to worry about callbacks inside callbacks inside callbacks. Another thing that it allows you to do is error handling, right? So, how do you do error handling? I mean, you might think that this still doesn't solve the error handling problem, right? I still have to go and say try and all this stuff, right? And probably each callback can do that. Now, it turns out the promise framework is an elegant solution for that as well. What you can do is instead of doing... See, there are a couple of approaches. Here what I've done is in the first call I have passed an error handler to the first callback itself. So, when I say then, I pass second parameter as another function where I do error handling. But here, the issue with this approach is this handles only errors which occur in that particular asynchronous call, right? If my tweet API call fails, then I have a handler. But what if I tend to say to the indexity fails? Let's say here I do something else. And if that fails, you know, does that mean that I have to pass an error handler for every single claim? So, here I have to pass another error handler, here I have to pass another error handler, and so on and so forth, which is probably not very ideal. It turns out that, you know, the promise framework allows you to do something like this. I can say it's not an error and pass an error handler right at the end, right? And then do my error handling here. So, right. So, this is not required. So, you can see how this is very similar to to a try-catch, right? So, it's like you can imagine all these steps as being part of a try-plot, and then the final error is being part of the except the handling part. So, in this case, what happens is all of these would run. If any of those asynchronous calls fail, your error handler is going to get called directly. So, you know, it might look like magic, right? How is all this happening? But the key to understand here is that all of these steps get executed in short, right? As in, when the script engine is running, it's executing this one line. It's just one line of code, right? I just put it in multiple lines. It's just one line of code. T is not get. That gives you a promise object, and I'm saying then, and then that gives you another promise object, and then another promise object, and that. So, if you notice, what essentially I'm doing here is I'm setting up a graph, right? A call graph. Entering. Entering a call graph is getting established, and basically, you know, you can think of this as a roundabout way of setting up a tri-catch. But a tri-catch block which works with asynchronous call. Now, you might be wondering, why are you talking about promises? Promises as a concept is something that has seen wide adoption in the industry. For example, if you're using jQuery, jQuery now supports promises. In fact, you know, for example, what I could do here is I can say return. Let's not mess around with that example. So, let's say, you know, I want to do, here, I have a dollar dot Ajax call, right? Here I'm making a call to the Twitter service. In response to this, I want to do something else. So, here what I've done, I've passed a success call back, right? You don't have to do it this way. This is the old way of doing things. In jQuery, I think one point, probably one point five were up. They have added support for what are known as deferred objects, which means that instead of doing this, I can do this. I can say then, a function. I'm not exactly sure what it is. I think it gives you the XHR object, right? Maybe I'll put a debugger here. I'll have done it nine here. All right, so I'm not sure what that first error is. I'll probably investigate that later. But here you can see that, you know, this particular callback is getting caught, right? And this XHR is the XHR object. So, this is basically the exact same thing that we did earlier. In the tweets example where I created a promise object and returned that, I created my own promise framework, right? So, I'll show you the code in a bit. But here, you know, this is part of jQuery. And jQuery supports then, and you can do all of those things. You can say then, and you can dot error, and you can put the error. This is supported, I think, in Prototype as well. And pretty much, you know, this is gaining my adoption throughout the industry. Even in Windows 8, if you wanted to Windows 8 development and, you know, create desktop, Windows-led applications, pretty much every single asynchronous API, asynchronous call returns a promise object, right? So, this is, you know, kind of very common now. I mean, if you think about what that promise object actually does, you know, it shouldn't, it's not, it's not really that. So, let me just show you what I had. I had just put together a very rough, quick promise framework together. I'm not sure that it handles all the edge cases and whatnot. But it kind of shows you what it does. So, you know, a promise object basically just has a few methods here, right? It obviously has a method called then. It has resolve, and it has error. So, when you call then on it, right? You basically expect it to pass the on-resolve and on-never call back. And in response to it, the key thing here is from the then object, I'm in turn returning another promise object, right? So, this is how we are able to set up that chain of calls. And here, what I do is, I mean, the internal implementation details don't matter. I have an internal resolve and error function which gets invoked appropriately. And in response to that, I call the users function, right? So, basically what happens is, when you call resolve, so in my tweets.get API, once I got the response back from Twitter, I said promise.resolve, right? So, when I do promise.resolve, I had saved the callback that the user had supplied in the then call, right? So, that gets invoked here. The best way to figure this out is to put breakpoints in all the correct places, hit F5, and see how the control flow happens. It's not very complicated. But the idea here is, it allows your code, which is asynchronous to be much more elegant, much more the same, right? So, if you're using jQuery, remember that you have this new way of doing things. You don't have to provide a success in an error callback. You can say .then, and if you're doing more jQuery operations, you can keep chaining that as well. So, that's quickly the promise framework that I want to talk about. The next framework that I want to cover is kind of the more interesting. This is basically RxJS. RxJS is a composable events framework. So, let's see what that is. So, RxJS is a framework that kind of, you know, we saw what promises does, right? This is like promises on steroids. It stands for reactive extensions for JavaScript. This is originally written for Docker and C-SHA and that has been ported to JavaScript as a library from Microsoft. It has direct support for being on the popular frameworks out there. You know, probably the best way to do is to see, you know, kind of work through some samples and see how that actually works. It basically provides an elegant mechanism for composing asynchronous operations. It works at a different level of abstraction. Basically, the idea is there are objects which can be observed and there are objects which are interested in observing the observable object, known as observers, right? So, this is an object which does something interesting, right? And there are other objects which are interested in being notified of it when this object does that interesting thing, right? So, this is called as an observable. That's an observer. An observer subscribes for event notifications on the observable. This thing in that event happens notifies the observer, right? So, what RXJ has done is it basically takes this design pattern and abstracts observable objects on top of event sources. And event sources can be anything. It could be pseudo event sources of your own, right? You might generate some data from that service that can be extracted as an observer. You might create an observable object on top of browser events. So, when I move my mouse, you know, I want to abstract that and do something in response to that as using this framework. Now, the benefit of using this framework is there are a bunch of combinator functions which are available as part of the library which allow me to do interesting things with these event sources as we'll see. But the fundamental premise is this, there are objects which raise events and there are objects which are interested in being notified of it when the events are raised. I will demo chichi here so that I don't forget to show stuff. So, let me just walk you through that. All right. So, to get rid of all this, I shouldn't leave internet on to now. So, I have a little console that I put together. This is, if you have done a previous session, this is likely the same console but with support for RXJS. Let me just show you what I have done in the source here. I hope that's reasonable. Perhaps it's not. So, that's what I have done. So, you can just search for RXJS, David search engine, you should get it. You can go ahead and download it and the core library is basically an RX.js file which I have included in your page. And there are a few extensions that you can add on top of the base library, like support for each library, support for jQuery, support for dojo, like and whatnot. But the base library is that. So, that's all you need to do to get support for RXJS. So, this particular window that you see here is an eval console. Something that you can do with it is you can run right little piece of JavaScript here and it'll run it. So, I can do that. It'll run the script. I can print stuff to a log, I'm triggering a lot of things today. So, you can do that and the messages to up there, I can clear the log and so on and so forth. So, basically I just go through some of the things that you can do with RXJS console and we'll see what exactly RXJS brings to the table. So, I was saying earlier that it is essentially a framework which plays with two kinds of objects, observable and observers. So, let's see how you can create observable objects with RXJS. So, I can say are observable. So, RX is the global object or the namespace inside which all of the other functionalities are scoped under that. So, I can go ahead and say something like this. I can say, rx.observable.create and I can provide a callback function as a parameter. Now, what is the idea here? The function that you're passing is basically the event source. This is the function that's going to generate the data. Whatever it might be. So, right now we just get the fundamental idea, we forget about the actual data that will be generated. We'll just output some values but this particular function is responsible for generating the event source. I mean, generating the event data that is the event source. So, what you can do is this takes one parameter, right? The RX framework will pass an observer. Somebody who is interested in getting being notified of this particular event, right? What you can do is, for example, I can say observer.onNext.temp observer.onCompleted and I'll return a function here. Now, I've done three things, right? I'll explain what the last line is. But the idea is this. Whenever I have some piece of information that's available, that's ready to be sent, right? Here, let's say that information is the number 10. So, I want, over this, listening to this particular event source to receive the value 10, right? How do you make that notification? On the observer, you call onNext and pass the value, right? Very straightforward. And then you give another signal called onCompleted to indicate that your event generation is complete, right? There are no more events to be generated. And the last function is basically a way of disposing of the object which is generating the events. I'll talk about that in a minute. Now, how can you use this, right? So, I can do something like this. You can say observable.subscribe and I can basically pass an object which has all those three features. You might be wondering, you know, what's so great about this? So, I can say onNext, onError. So, we'll see what onError does and you can say onCompleted. And in these three functions, what I'll do is I'll just, here I'll say printOnNext and I'll print that value. I'll say print onError. Here there is, you know, no data. It's just a notification that it's complete, right? And then I just run it. So, on the right-hand side, you can see that onNext.par and onCompleted.par. That's because, you know, it completes successfully. So, at the root, right, what is happening? So, when we look at more complicated examples, it might look like black magic. I mean, where is all this coming from, right? Ultimately, underneath, that's all that's happening. If there are two objects with a verify interface, your observer should have onNext.onCompleted. The observer will, you know, all those, all that. Now, of course, this is a very simple, simplistic example. You can, I mean, you can have multiple observers, right? So, I can do that. And then, you know, I can create another observer here and call this onNext.par or something. And then you can see that, you know, both onNext and onNext.par get called. So, all that works, right? So, if you have one observable object, you can have one or more observers. So, all that works fine. But the interesting thing is what are all the things that you can do with an observable object? Like, how you can compose operations on top of that? So, I'll get rid of the second observer here. What else? So, this thing that I have done here, I'm just returning, like, one single value, right? So, let me introduce the first combinator that you can do. This thing can be written simply like this. So, let me just... So, what it did is, I just called one method, called return, and I pass a single value. So, again, this should be very straightforward, right? It simply does what I just did, right? It basically calls the onNext on my observer, passes the value that I pass here, and onCompleted after that, right, once it completes. What else can I do? I can do something like this. Range of 1, 10. So, now something more interesting happens here, right? So, this particular function notifies the observer for a range of numbers. So, when I say 1 to 10, it calls the onNext from 1 to 10, and then calls onCompleted. So, this is a very simple data source, right? It just generates a bunch of numbers, give it a range, right? So, let's see what else we can do. So, for instance, let's say I have some data as an array, right? So, I have 1, 2, 3, 4, 5, 6. So, there's another variant here where you can save from array like that. So, now you can see that onNext. Basically, now I have created an observable object that abstracts an array as a data source. So, we're just going, like, you know, in small increments. The first we abstracted over a single hard-coded piece of value called number 10. So, we abstracted over, you know, a range. Basically, you provided some input parameters and abstracted a range of values. Now, I'm abstracting over. I'm creating an observable that basically is an abstraction on top of an array, right? And the same thing works, right? OnNext and so on and so forth. The really interesting things you can, you know, start doing when you deal with other kinds of objects. For example, DOM elements, right? So, what I have here is there's another variant here from HTML event. So, you can save from HTML event and pass two parameters to it. One is the DOM element that you are interested in. For example, I'll say document.body. And HTML event that you are interested in. For example, mouse move. So, I'll say mouse move, right? Now, basically here, this observable abstracts over that, right? So, basically what happens here is whenever the mouse move event is raised, all my observers are going to get motivated. Very simple. So, you can mentally visualize what is happening internally, right? So, from HTML event is basically taking a DOM element, doing an add event listener on that particular element. In the handler for that, they're simply calling observer.onNext, right? So, what I'll do is here, here I'll actually get the event object. So, I'll probably say client text v.client1. Now, you can see that every time I move the mouse, your event source is continuously fired. Now, the point of showing you all these examples is that the core RxJ's rainbow itself is agnostic of your event source, right? You can create your own. So, these are something that are supported out of the box in the RxJ's library. But if you have your own unique kind of event sources, you can cut that in, right? And your subscriber and all that code just works. So, okay, so this is interesting. So, you can do this. Now, some of the other cool things that you can do with this is, so let's say, so how many of you have entered the functional programming in JAS prep session? About 40%. So, you know, you might, you might be like, you know, super fast explained throttling and debouncing and all, right? That's a combinator that's supported here. For instance, what I want to do is just copy that and refresh my page. So, what I want to do is, for example, I want to know, you know, the mouse event source, maybe in response to it I'm doing something complicated. Maybe I'm doing network IO in response to every mouse move. And this is not scaling very well, right? So, every time I move the mouse very, very coordinate, my observer is getting notified and my, you know, my server side, service is being invoked and my server is just really struggling. So, how can I, you know, for example, maybe the solution here is to throttle the number of, you know, the frequency at which the event source is getting raised, right? So, you can do something like this. So, I can say dot throttle, let's say it's over here. Now, I'll just run that. So, now you can see that when I move the mouse, it's like a different thing is happening here, right? Now, if you notice, the only piece of code that I added is, I just continue with the fluent area, I just said throttle code, right? Everything else just works as before. Nothing changes in my observer code. Nothing else changes in my source also, right? From HTML event, nothing changes there. That code is as it is as it was before. Basically, I have composed something on top of an event source. And it turns out that you can do this to an internet level, right? So, here what is happening is, whenever I move the mouse, it is actually doing the bouncing. I don't know why it's called throttling. So, basically when the time interval between two consecutive events of mouse move is greater than 250 milliseconds, that's when my observer is going to get modified, right? So, if I move very, very slowly, right, then for every coordinate I'm going to get, I mean, I can't move it so slowly that, you know, it's less than two 30 seconds. Maybe I can increase the duration here every one second, right? And that would have been bombed earlier, right? So, if I do it in the same page now, it will get called twice. So, I'll just run this now. I mean, it's the same thing, right? So, now basically the duration is moved. So, if I move very slowly so that it's one second, it's hard to show you what it does. But you get the idea, right? Basically, the duration, the time duration between two consecutive events is greater than the duration that is supplied. Then your callback is going to get fired. So, if I move it so fast that I get five events within 250 milliseconds, my callback is not going to get called five times. It's going to be called once at 250 milliseconds. It's complete. So, basically I'm throttling the event source by a certain duration. What else can I do? You know, maybe I don't want this, right? In this case, if I do a lot of mouse activity, right, maybe it's like a doodling application. If I do this, then if I draw really really fast, my user experience is going to be less than optimum because imagine that it's a collaborator to complete it. It's a whiteboard, you know, in a WebEx kind of app, right? So, I go and draw stuff on the whiteboard. I want other people to see it. Now, if I do this, then if I do draw a lot of things, then you know, the others are going to have to wait till you complete drawing. Basically, the time difference between two draw operations has to be greater than whatever the duration is. Maybe I don't want that. I want the event source to be created once every two degree seconds. So, that's slightly different, right? So, there's another one called sample. So, I run that. So, now here when I move the mouse, you can see that slightly different behavior is happening, right? It's not happening as frequently as it happened before when I had no collaborator applied at all. But it's not like the throttle case as well, right? Here, basically, every two to three milliseconds, one event goes. That's all, right? So, this is called the sampling. I think that's a better name, right? It samples your mouse move event once every two to three milliseconds. So, no matter how many mouse moves I get within a two to three minutes integration, only one event is going to grow for my observable. This is different from the throttle case. The difference is slightly subtle. So, if that's confusing, just experiment with it, right? It's going to be clear. It's going to be a little wild for me to get it as well. In this sampling thing? There you go. So, if I mouse and make an example in the curve, and there's a point here, I take the mouse here, but only these two points are sampled. So, I get a state here. So, what about that? What do you do? That's a good question. So, basically, the question is, in case of sampling, right? But in a general sense, when you sample, that's the thing with sampling, right? The question is what happens to all the data that was generated during that interval when the callback was not propagated, right? So, I've moved from point A to point B, and the browser has actually raised the event 20 times within a 2-2 millisecond duration. But I'm getting that notification only once. So, what happens to all the coordinates which were generated during those 20 invocations? So, with sampling, you lose it, right? So, isn't the other method much better? Trottling. No. There was this curve in the frame. Default. So, in that library that I showed in the previous case, I handled that. So, I have a debounce, I have a debounce with data, where the callback basically will accumulate all the information and supply that to you. So, you would have to roll. So, that's the thing about this library as well. So, you can roll your own sample routine. Basically, you can probably take that debounce function and port it over here, and it just works. All you have to make sure is that you basically return an observable, right? You create an observable, compose over your source observable event source, implement your logic, and return that observable. So, you just hook it to the chain. Sure. So, those are some of the things that you can do with this. So, I've just scratched the surface of RxJS here. So, if you look at the... If I can find it. So, when you download RxJS, you'll get a documentation like this. It's basically the complete API for RxJS. If you look at the methods that are available in observable, you know, I've just covered, for example, you know, range and what not, from Array, from Achievement. There are a whole bunch of combinators that are available. That do all kinds of fancy things. You know, there is a time interval. There is a time out, time spam. There is a select mini. For example, select mini is an interesting combinator. What select mini will do is... So, if you have two event sources that are happening one after another. One is a mouse move, one is a mouse click. And you want those event callbacks to be coalesced into a single callback. Select mini allows you to do that. So, it takes two separate observable operations and it basically sequences them and makes one single callback for you to observe. In fact, or take another one. Take until. Take until is a combinator. Again, what it does is... Let's say you have two observable sequences. You want the observer to be notified from one particular sequence. Only so long as another observable sequence does not notify. So, you have two sequences. Two observable objects, object A and object B. And I have an observer. I want the observer to be notified of the events generated by observable A. Only so long as observable B does not have to trace an event. That's what take until some other observable. So, I have a little sample here that shows how you can use this. I probably won't explain the sample because I wouldn't have time. But basically this implements... Let me just show you what it does. So, I have this little bib over here. I can just click and drag it around. Now, if you look at how you would have implemented it traditionally. So, this is typically how you would have done it. So, you have the object. I handle mouse down. I handle mouse move. I handle mouse up. I do all the complicated logic to implement a drag object. Now, you can do the same thing with RXJS. And the code might look a little bit more. But essentially, you can see how the different combinators have been applied to do interesting things. So, for example, here mouse move is from HTML event observable on top of my object here. That is basically that particular drag media. I am creating a mouse move on that. I am creating a mouse up observable. And I am creating a mouse down on top. Then I am creating a composed version of that. Basically, what I do is I send mouse back to the skip of one. So, skip is a combinator which what it will do is, in a sequence of events, it will skip the first one. It will skip the first one and cache it. It will keep it with it. And then I compose on top of that another combinator called zip. So, what zip does is, you can see that zip is a call that is happening on top of the object that is written by skip. So, skip will return observable which will have the information that was skipped. So, what does that mean? So, this is mouse move. So, for the first coordinate, skip will get notified. Skip won't propagate into the next one. That is, your zip won't get the first one. Then the second mouse move happens. Now, zip is going to get notified. And skip will return the previous data as well. The mouse move that was skipped. So, in zip, basically what we do is, we provide, so the context, the object on which it is being called is the observable that was skipped. And then this is the other one. This is basically the same mouse move object as being passed here. This will have the current mouse move coordinate. It's probably, you know, getting a little confusing. What you can probably do is, you know, this is just work through it, right? So, I'll share the demo. Just put some break points and step through it and you will see how this goes. Zip will basically take two observable objects. The one that is part of the context that is written by skip. And the other one is another observable object. And then it calls your callback and supplies those two values as two parameters to that function. So, here this basically gives me the two coordinates from two consecutive mouse moves. And then I create another composed one on top of mouse down. Here I use select me to coalesce the two event sources. One is mouse down and one is mouse moves. Because I don't want the events to be raised when I'm simply moving the mouse. I want it to be raised only when I'm mouse down and then move, right? Otherwise, the dragging will keep moving when I just move, right? I want it to be dragged. So, that's what these two lines with. And then finally, my subscriber is on top of the mouse drags. So, you can see that, you know, I have a single subscriber where I, you know, do whatever needs to be done. Basically, I move the clip to the new location. But you can see this whole stack of the operations that are being built on top of each other, right? So, the key with using RXJS is getting familiar with the list of combinators that you can do interesting things with. So, you can kind of transform your data however you like. You can do very, very powerful things with RXJS. And the whole thing works, right? So, if you look at it here, you know, I have included that only, right? So, this is drag.js and this dragging is happening through RXJS. So, with that, I've kind of done with the quick introduction to RXJS. Here are some resources that you might find useful. So, there's a blog post and I thought about promises. January is the official record of this script to learn about promises for January. But RXJS, these are two great resources, especially the blog here by Matthew. So, this is like a whole series of blog posts about RXJS starting from the basics. That's really useful. That's what it's a few questions. You can take that. Or I think we have lunch. Any questions? Promises? With RXJS. So, the first example that I just did. Observable.create and pass the function. So, that's the custom. So, there I just raised 10, right? Instead of that, you can do something more interesting. For example, you might have your own web service. So, maybe there you want to call that web service, get some data back, and call your own web service. So, instead of saying observable.onmix of 10, you will make a rejects call. In the response, you will say observable.onmix of 10. So, any, any, you will say 10 is right. In promise framework, we created a sequence of calls using 10. Is there any way to distinguish the previous calls, whether it is executed successfully or not? So, if you set up a then series of calls and an error, right? If a particular then callback is being called, then that means that the previous was successful. Otherwise, your control would have gone to your case. Even if you don't have an error case, the subsequent then series will be gone. If you have an error case, then you handle it elegantly. Otherwise, that just takes a load. So, yeah. If you want to track another state, then you have to use it. So, for example, in the previous call I want to save some information. Then the next call I want to use that information. In that, you will have a handle of this call. So, that's it then. Thank you very much, guys.