All right, so we've now got our user logged in. We've got their token here in local storage, as well as their profile. So we've got those things in place. Now what we need to do is set things up so that Angular can send our token as an authorization header to access our private resources from our server. So let's maybe just take a step back and talk again about how we're going to access these private resources. So let's take a look at this in Postman.
So Postman is an application that allows us to send and inspect our HTTP requests really easily. So let's send a get request to the public endpoint. And as you see here, we've got our message coming back. And that's what we would expect. We don't need to have any kind of authentication to get at this message, but if we tried to go to the private endpoint, because we've set up middleware, we get "no authorization token was found".
And so that's also what we'd expect. We don't want to let just anybody through this private endpoint. So why don't we go ahead and see what it looks like to attach an authorization header? So let's go over to headers here, and we can choose authorization from the list here. And what we want to do is use the Bearer scheme. So this is the scheme that's used along with our authorization header to send our JSON web token.
So what we need next is to put our token just after this space here. So coming back over to our local storage, let's grab the token and put it next to Bearer here. And we need to get rid of these quotes that show up at the end. That's just how things are stored in local storage. But we don't want to send those through Postman. Back up at the front, we'll get rid of that first quote. And now, if we send this request again, we see "Hello from a private endpoint. You do need to be authenticated." And the reason we're getting through, the reason we're passing through that JWT authentication middleware is because we've got our token as an authorization header here. So now what we need is a way for Angular to attach authorization headers for us when we make our HTTP requests. And to do that, we're actually going to need to make use of this JWT interceptor provider that we see here.
And to get a sense for what this JWT interceptor provider does, let's head over to the Node modules folder here. Let's go to Angular JWT. And then within Angular JWT.js, let's take a look at this JWT interceptor provider right here. And the way that this works is it makes use of Angular's HTTP interceptors. So and HTTP interceptor in Angular is basically a way for requests to be intercepted and transformed before they go out.
And likewise, when responses come back, they can be intercepted and transformed as well. And the transformation that we want to make in this case is that we want to attach our JWT as an authorization header before the request goes out. And essentially, what this gives us is a way to have our JWT authorization header automatically attach to all our requests. So let's configure things with our JWT interceptor provider.
Back over in app.js, let's come over here and we want to do JWT interceptor provider and we need to set the token getter function, so token getter. It's going to be equal to a function that has ahold of Angular storage, so we want to inject store there. And all we want to do is return the JWT from local storage. So we'll say return store get ID token. And so this will go to local storage and it will return that token and give it to the JWT interceptor provider to attach as an authorization header on our requests.
So now that we've got our configuration set up here, we actually need to push this interceptor onto the array of HTTP interceptors that comes from Angular. So down below here, let's go down just to the bottom here, under our stay provider. And let's tap into HTTP provider. And we'll say that we want the interceptor's array and we want to push onto it our JWT interceptor. And so just a note here, we're actually pushing on the JWT interceptor, which is the name of the interceptor as defined in Angular JWT and not actually the provider that we just configured.
Okay, so let's save that. And now what we can do is start working on our profile. So if we come back over here to our profile controller. So we've got our message coming through right now in our controller. Let's get rid of that. And let's give this controller a few more things. We're going to want a couple functions to get our messages. So let's do vm get message and that's going to be a function that we'll define in just a second that is going to be responsible for going to our public endpoint and getting our public message.
And then we're going to want a very similar function down below, but this one is going to get secret messages. So in this case, we'll say we want to get secret message. All right, so then we want a property that's going to hold our messages. So we can say "vm.message" and that's going to be where we assign the data that comes back from the endpoint. And now why don't we set up the profile for our users? So we'll have a profile property.
And let's say that we'll go to store get profile to get our user's profile. And we need to inject store up here to make use of it. So this will get the profile object from local storage. And now this profile is going to give us access to properties like the user's nickname and their email and their profile photo so we can use that in our template. All right, so let's set up our functions now for getting our messages.
The first one is going to be the one for getting public messages, so we'll say "get message". And what we'll do is we'll make an HTTP request. We'll do an HTTP get request to our HTTP local host 3001, API public endpoint. So now before we actually go handle the response for this, what we can do is set up some configuration that tells HTTP not to include the authorization header in this case.
Remember, this is going to our public endpoint and we don't really need to send our JWT to that endpoint. We could, and it wouldn't really hurt a whole lot, but we might as well forego it. It'll save us a bit of room in the request that goes out. So let's put in skip authorization as true here. So now we can use the promise response to get ahold of the data that comes back. So we'll put in a function that has a response.
And then let's set vm message equal to the response data message. So this message property is going to be coming back from the data in the response, and it will be assigned to vm message. And then let's not worry too much about handling errors just for the time being. We'll come down here and we'll say function get secret message and that's going to be much the same thing, except this time we won't skip authorization because for this endpoint we're actually going to need that authorization header to be present.
So let's do HTTP get. It'll go to HTTP local host 3001. And it's going to go to API private. And now what we can do, because we're not passing any kind of configuration to skip the authorization header, let's do then we'll get our function in there with a response. And the response can, again, be assigned to vm message. Vm message equals response data message. All right, so that looks pretty good. I think we're all set here in our controller. So let's save that.
And now let's do some work in our template. So we can get rid of this message that we had coming through earlier. And now let's use some of the features from Angular material to set up our page. So we want the outer element to be md content. And within that element, let's set a class. Let's give it md padding. And that's going to put some padding around everything. And we'll set layout as column. And this will align things in a column fashion.
Within md content, let's give it a card. We want an md card. And in there we want md card title. And then md card title media. Then, within this element, let's give it a div and let's give it a class of md media, and also card media. We'll want layout padding as an attribute there. And this is where we can put the image for our user. So we'll want an image tag and we'll use the ng source directive. And the length that we want here is going to come from our user profile picture.
So we've got this picture property coming from our user's profile and that's the link to their avatar. Then, within the alt for now, let's just give it a profile picture. And that'll be good for now. All right, so then down below here, let's give it md card actions. And we'll want layout as column in this case, so layout column. And then let's give it some alignment, so layout align should be end center.
And this is the spot within the md card actions where we can put some buttons for getting our messages. So let's do an md button and this one will be get message. And then the ng click within here can be pointing to our get message function. So we'll do ng click and that'll point to user get message. Now we can just copy this button over and paste it below. And this will be for our secret message, so we'll say get secret message there and get secret message there as well.
All right, down below the md card title media, let's put in another element. This one is going to be md card title text, so md card title text. And within this element, let's put in some user info and also this will be the spot where we can put our message. So let's maybe put a span here and let's give it a class of md headline. And then within the span we can just template out our user's nickname, so it'll be user profile nickname. And then let's go down below.
We'll give it a span with a class of subhead now. And in this case, let's template out the user's email, so user profile email. And then finally, below, we can maybe give it an H3 and this is where we can put the message that comes through, so this will be user message. So these properties, nickname and email, they're coming from the profile that we set up, which is coming from local storage.
And then the message that comes through here is what's being assigned to that message property as the result of the HTTP requests that go through from the click of these buttons here. So let's check this out. Let's see if everything works out. We'll come over to Chrome and go back to our application, give it a refresh. And as you see here, everything's coming through. The profile photo is quite large so we can fix that up.
What we'll do is we'll come over and let's just tack on large there. So let's come back over and that should shrink things up well. It does. And so now we've got our photo, our nickname, and also the email coming through in our profile area. And so now let's check to see if our requests go through. If we hit get message, we see we've got our message coming back. And then if we test out our secret message, we click secret message, there we go.
We've got our private endpoint's message coming through. And why don't we actually take a look at that request that just went out. Over here in the network tab, if we take a look at the latest request there it is, our authorization header with the Bearer scheme and our JSON web token. Okay, so we've got the user's profile information coming through and we also have a way to get at our private endpoints with our JSON web token, but there's still a problem with our Angular app.
And that is if somebody refreshes the page, what happens here is that we kind of lose our state. We've got our login button back now because that is authenticated Boolean from the auth service kind of gets reset. And so this obviously isn't what we want to happen. We want to persist our state. We want to let the application know that the user is still authenticated. We can set up some logic to do that and we'll take a look at it in the next lecture.