Introduction to PUT Requests & Better Templating
All right, this is our last video of building a basic jQuery Ajax app. We can now get orders, we can add orders, we can delete orders. All that's left is to edit orders. And for that, we are going to use a PUT request. Uh, kind of if you're, you've probably heard the term restful APIs, and that's kind of a standard way of putting together an API where you use GET request to access things. Your back end is looking for POST request to add new items. Uh, and if an item has an ID and you want to edit it, then you use a PUT request to, it's basically the same as a POST, but you add the ID on the URL, and then you do a PUT request and you will update that resource. And then delete, which we've already done, which you can do by ID.
We're going to be doing the PUT request. It's the most involved and so we're going to take our templating to a whole new level. Uh, show you a better way of templating other than scratching out lines in JavaScript. That's going to be the first thing we want to do. This is pretty much as far as I will ever go with plunking out, you know, uh, string lines concatenated together in JavaScript. It's kind of messy. It's a whole lot of quotes. It's just stuff we don't want to do beyond this. This is as far as I'm going to go. Any more than this, we got to go one of two routes: we either got to put a template tag in our HTML, uh, which is a quick easy way and that's what we're going to do for this, or you can say you have a lot of templates, you can create an HTML file for each template and then you can use something like Grunt to automatically turn those into JavaScript strings for you. That's way more involved than we need for this. So we're not going to do that in this. Uh, but let's go ahead and take this. We're going to copy it out.
Using the HTML Tag
And what you can do is you can add a template tag. And so we're just going to paste this in here. I'm going to use my Apple+D multiple cursors in Sublime to get rid of all my quotes. And same thing to get rid of all my pluses. There we go. Now, if I give this an ID, order-template, and then I can, instead of stringing all this out right here, I can go orderTemplate = and I can grab it with jQuery html(). Did I do order-template? Yes, I did. Okay, so this should work exactly as I have it before. Let's save and refresh. Excellent. So this is working perfectly and it's much cleaner. You get syntax highlighting here. Uh, you know, you see all the pretty colors that you should see when you're coding HTML and it just works.
Uh, one, one thing to mention, if you're using IE8 or older, uh, it may just be a safer way to just go script. Uh, this is kind of the old way we used to do it. You do a script tag and you give it a type of text/template. And what that's going to do is it's going to tell the browser... type text/template, the browser doesn't know what that is. It knows it's not JavaScript, so it's going to ignore this block of code. Uh, and you you're safe to put anything you want inside of it. Uh, you're not going to blow up your JavaScript on the page because it doesn't think it's JavaScript. So that's kind of the old way to do it. Uh, I'll just stick to the template tag uh for now, since I'm only supporting HTML5 browsers with my application. And yay, now we can move forward.
Structuring HTML for Edit Mode
So what we're going to do is we want an edit mode for this li. I'm going to go clean up my HTML a little bit. Uh, we want an edit mode. So what we're going to do is we're going to add a class of edit to this li when we're editing it. And then we want some stuff to be hidden and we want other stuff to be shown when that edit tag is there. So I'm going to go ahead and bump this down. I'm going to make it a span, and this span will get hidden when we're in edit mode. And I'm going to make an input. And the input will get shown when we're in edit mode. And the way I'm going to do that is with a class, class="edit". So the class edit, and I'm also going to get a class of drink, uh, name, so I know how to access the name there. And this class will get no-edit. So whenever edit exists on the li, anything with no-edit will get hidden. Anything with edit will get shown. Yeah, very simple, sounds easy enough.
Let's do the same thing here for drink. And this just becomes drink. There we go. So that's covered. And then we need some other buttons here. We got the remove button, we'll leave you there. We need an edit button. And this one will have, let's see, class="edit-order". And I'm also going to add a no-edit to this, cuz I don't want to show this when we're currently editing. Um, and then let's make a cancel button. This will have edit, so it'll get shown only when we're editing. And we'll call this one cancel-edit. There's a lot that goes into editing. It's a lot simpler to just create and delete. Um, and I think that's it. Edit and cancel. Awesome. Uh, we also need a save button, now won't we? So let's go save. Um, this will be called save-edit, maybe. And this one will have an edit class, so we show this only on edit. So if I hit save here, we should see everything. Yep. So now everything is plunked out.
CSS Rules for Toggling Edit State
Let's add some CSS rules here to just hide what we need. So when we're on edit. I'll actually do this, so any edit within the li gets a display: none. There we go. Now anything that is only going to show on edit is gone. And so then you li.edit .edit. So when the li is in edit mode anything with edit gets a display: initial, which is what it would have shown had we not added a display: none. And then no-edit get a display: none. There we go. That should work. So now if I refresh, I see an edit button. And if I were to inspect this element here and add a class, there we go. Now we see save, cancel, and they are inputs. Awesome.
Now let's just wire this in with JavaScript. So moving on, uh, we want to add down here another delegate because if you remember, delegate is going to apply to anything that hasn't been created yet, as well as things that are currently existing. So I'm going to delegate... what was the name of it? I think it was called edit-order. Yes, edit-order right there. So when edit-order gets clicked, we are going to, let's see, let's cache this li just like we did up here. This I can actually probably copy and paste that for me. There we go. So now we're grabbing the closest li and we are going to copy the name of the value into the value of the input for editing purposes.
So we are going to go li.find('input.name'). The input with the name class, that's going to be this guy, and I want to set the value to be the content of this guy. So oh, I'm going to add a name class here and I'm going to add a drink class here. So I'm going to basically set the value of span.name to be the value of input.name, if that makes sense. So let's go input.name.val(), which means I'm setting the value or getting the value, and that will go li.find('span.name').html(). So that's we are setting the input to the same value as the span. Let's do the same thing with drink. So now input class drink. I love the sublime multiple cursors right there. Apple+D, it's just, ah, it's great. Okay. So setting that, and then we're just going to add the edit class. So once again, caching the li right here is a great move because I can do several operations and I don't have to search the DOM each time. So let's see if that works. Hit edit, and awesome! We populate our two values and we turn into edit mode, which means our save and cancel are there.
Let's go and add our cancel item. I'm going to actually copy and paste because this is probably a lot more similar than anything else. cancel-edit. And then all cancel-edit is going to do is remove class edit. So I'm just going to grab that li again, remove the class of edit. Let's see if that works. Edit, cancel. Edit, cancel. Nice. So that works. Um, add my semicolons there.
And then the last thing we need to do is the save operation. So here we go. Same thing. Orders. What did I call that? save-edit is the name of my save button. So when save-edit is clicked, I'm going to have to grab those two values and put together my PUT request. Let's just do a very similar thing to what we did here. order = { name: ... }. And in this in this case I'm actually going to grab the li, kind of same thing I've been doing. And then going to go li.find('input').val(). So there we go. I'm going to grab the value of whatever that input is. And order will be the same, or drink will be the same way. Drink will be grab input.drink value for that. So there we go. I've got my order put together.
Let's post this thing to the back end. I'm going to do some copy and paste to make it a little easier. This is going to be a PUT request. And instead of posting to /api/orders, we're doing a PUT to /api/orders and we're also going to add the ID here. So this is going to be... let me make this easy. I'm going to add the ID here. There we go. Love Mustache templating, makes it easy to throw stuff in there. So now I can just go li.data('id'). So there we go. We've grabbed the ID off of what that entry is. We're going to PUT it to orders/ID. We're going to pass the order object. And on success we are basically going to populate our values. Let's see what's going to happen. So when we hit save, we change this, 'william', I hit save. I can't just go back to here cuz this span now needs to be updated. I'll show you over here in the HTML, we've put a new value in here. When the save comes through as successful, we need to take that value, throw it in here, and then take edit off of our edit mode.
So that's easy to do. We're just going to go li.find('span.name').html(order.name). There we go. I'll do the same thing for drink. And then I'm going to remove the class of edit, which I think I have right there. And so get that edit class removed. And then error, let's do error updating order. There we go. Let's see if our API works. Refresh. So I can go 'Will I Am', save. Not right click. And there we go, it's saved. Let's look at our network to make sure that happened. We did a PUT request to /api/orders/1, got a 200 okay on that. And if I refresh, it should say 'william' instead of 'will'. Awesome. Let's change it back to 'will'. Change my order to a frap. I keep right-clicking for some reason. There you go. We got it.
So I know I kind of sped through that, may need to rewatch it again. That's kind of how you're going to take your templating to a higher level. That's how you're going to add a PUT request. Um, and that's an easy way to toggle any kind of visual thing into an order mode, is just add hidden, you know, hidden input elements and then toggle them on and off. So hope you had a great time watching this and catch you around.