Alpine Fetch Overview1:03
And if I take a look at that, we have an Alpine component here. If you're not familiar with Alpine, you don't need to be. Just have a look here. When the component loads, make a fetch request to this endpoint. Then once you have the posts, update this piece of data, and then this will re-render. We iterate over the posts, and we display each title within a heading 1. So let's have a look at that endpoint, because this, for the example, is what we will be stubbing. If you hit this endpoint, we return a collection of hard-coded post titles. Okay, let's look in the browser. We give it a load, and sure enough, it works.
Start Cypress Test1:36
Okay, let's look in the browser. We give it a load, and sure enough, it works. If I go to the Network tab, there we go. Here's our response from that endpoint. The page re-renders, and pretty 101 stuff, right? All right, now let's pipe this into Cypress. We'll go back to, I think I called it Demo, and I'll just say it stubs a network request for the tutorial. Okay, so we're going to begin by visiting the blog. And if I switch over, looking good, and it is making that real request.
Stub Requests with Routes2:02
Okay, so we're going to begin by visiting the blog. And if I switch over, looking good, and it is making that real request. Okay, now let's stub it out. We can do this in two steps. First, I'm going to boot up a server, and this will begin piping any XHR requests through to the second call you can declare, cypress.route. So think of it like this. We can register an endpoint, in this case, /posts. And this is our way of saying, well, if you detect any XHR request to /posts, don't actually make that request.
And this is our way of saying, well, if you detect any XHR request to /posts, don't actually make that request. Instead, I'm going to return fake data here, and you might call this a fixture. To start, it'll be an empty array. But what about if the XHR request is for something that has not been declared here? Well, in that case, it behaves as it normally would. We're not faking anything. Okay, let's give it a shot, because we think this should work. But we run it, and there's no indication here. I do see a route, which is useful, but we can tell that we're still hitting that actual
Enable Fetch Polyfill3:59
Up until this point, we've only registered a base URL. But we're going to add that new one. ExperimentalFetchPolyfill is true. So now when we update this, Cypress should close. And if I switch back, yeah, it bounced me back to this section. OK. Run it again, and now we can see support. And it looks like it works because I no longer see those titles on the page. Have a look. Here's our routes.
Have a look. Here's our routes. This endpoint is being stubbed. And specifically, if we have a look at the console, here's what we're returning. Response body is an empty array. So I'm no longer making an actual request to my server. Notice the actual request here is to cypress/xhrs. So that's what cypress.server allows for. We now give it the full path, and it's going to check, well, do we... If I switch back, do we have anything registered for that endpoint?
We now give it the full path, and it's going to check, well, do we... If I switch back, do we have anything registered for that endpoint? If so, just return this data here. Let's comment that out and try again. One more time. And we have a look. And yeah, notice now we didn't register anything, so it behaves as it normally would. OK, cool. Let's bring that back. So let's say we'll do $title is my fake post.
Let's bring that back. So let's say we'll do title is myFakePost. Come back, give it a refresh, and there we go. So if you think about it, this is actually pretty cool. With Cypress, we are hitting a page. That page is using the Fetch API to fetch the necessary posts. However, using Cypress, we've intercepted that request. And instead, we've said, well, when you make a request here, let's just fake it. This is the data I actually want you to use. So don't forget, this is a trivial example.
Create and Use Fixtures5:40
This is the data I actually want you to use. So don't forget, this is a trivial example. I don't see any valid reason you would reach for it. But in the case where maybe this is a third-party API that you don't want to ping over and over and over, you would reach for this approach. So if I switch back, now I could say, visit the blog, and that should contain my fake post. Come back, have a look, it works. Now, here's where fixtures come into play. You'll notice in my Cypress directory, we have a fixtures folder, and then you have an example one here ready to go.
You'll notice in my Cypress directory, we have a fixtures folder, and then you have an example one here ready to go. I could just as well create a new one called posts.json. This could be an array, title, my first fake post. And then let's do another one here. My second fake post. Okay, now we have some fixture data for a collection of posts. So now, rather than hard-coding it here, let's get rid of that. Instead, I'm going to use this magic string here, fixture, and the name was posts. So when we write this, we're telling Cypress, okay, fill this with the fixture in your fixtures
Instead, I'm going to use this magic string here, fixture, and the name was posts. So when we write this, we're telling Cypress, okay, fill this with the fixture in your fixtures folder, but specifically the one called posts.json. So now, if we want our assertion, what do we have here? My first fake post. Let's come on back and paste it in. And that should return true as well. Great, now we're using fixture data. Now, we can even interact with that XHR response.
Alias, Wait, Inspect XHR7:07
Great, now we're using fixture data. Now, we can even interact with that XHR response. For example, I could give this a name. Think of this sort of like an alias, a way to refer to the faked request. In this case, how about getPosts? Okay, now I can say cypress.wait until that getPosts request is complete. And notice I do precede it with an @ symbol. That's another way to think of it as an alias. Once we're done, why don't we, we'll have an XHR object. Why don't we just pass that to cypress.log and have a look.
Once we're done, why don't we, we'll have an XHR object. Why don't we just pass that to cypress.log and have a look. All right, give it a shot. Now, you can see we have given it an alias. And if we wait for get posts, we then log the result. Have a look here. Let's clear it out and click it one more time. And there we go. Here's our request. Notice the methods get the status is 200.
Here's our request. Notice the methods get the status is 200. Of course, any of that can be stepped. And then here is your response that came from our fixture data. So I could do things like with that response cy.log XHR to response.body. And this would give us the fixture data. Or you can grab just showing you lots of different options here. You could manually grab it cy.fixture posts. And then once we have that data, once again, let's just log it. There you go.
And then once we have that data, once again, let's just log it. There you go. And that's another way to load in the data. And again, that's only if you need it. So I'm going to get rid of all of this. What else? Maybe one last thing. So again, with posts, this is such a trivial example. But often you're going to be faking some kind of response JSON returned by a third-party tool that you use.
Record Response to Fixture9:20
You instead work with that fixture data. So here's a couple of ways to do that. I'm going to get rid of all of this. I'm going to get rid of our fixture data. And at this point, all we're doing is registering a route endpoint for posts. But we're not associating any fixture data. So when that's the case, it still behaves as it normally will. So now I'm going to say, wait for that get posts request to be made. Intercept it. And then, once again, with that XHR request, we're going to write it to a file.
Intercept it. And then, once again, with that XHR request, we're going to write it to a file. Cypress offers a useful method called writeFile. So it's going to be in the cypress/fixtures directory post.json. And the contents of that file will be the response body that I just showed you a couple minutes ago. All right. Are we all clear? Boot up a server. Begin piping XHR requests through to cypress.route.
Boot up a server. Begin piping XHR requests through to cypress.route. If there's an endpoint, and if that endpoint has fixture data associated with it, fake the request. Otherwise, we're going to record that the request was made. But we're not faking anything. It'll still hit our server. However, we do have an alias here. So wait for that request to complete. And then write the response body to this JSON file.
So wait for that request to complete. And then write the response body to this JSON file. OK. Let's come back. We run it. And there you go. It wrote. Let's see what it wrote to the file. It wrote this bit of data to the file. And if I come back, there it is.
It wrote this bit of data to the file. And if I come back, there it is. So now we're saving an actual response as a fixture. So now at this point, what you might even do, you could save this to a snippet or just write it out by hand when you need to fake it and then get rid of it. Now I can just say stub out that endpoint with the fixture that we created for it. Like this. Now, if I need an assertion, my first Post, let's go back. Contains, or don't forget, we talked about this. Get the body.
This was only a basic example. In real life, you only reach for it in cases where you think to yourself, I really don't want to hit that endpoint every single time I run this test. Or it's not practical. The setup required to hit that endpoint and gather the response, it's just not necessary. So instead, we're going to do it exactly once. And then we will save the response to a fixture file. And from then on, I will load that data rather than the real time data that would be returned. So I'll let you take a look at this real quick. Boot up a server.
So I'll let you take a look at this real quick. Boot up a server. Register an endpoint. Associate a fixture with it. And then get started.
