Imagine you have a REST API endpoint that returns a JSON object. Can you see that JSON response in a Cypress test? In the blog post Test Plain Or Markdown File Using Cypress I have shown how to request a plain text resource using cy.request and write the received response into the empty application document using document.write
. In this blog post I will show an alternative approach using cy.visit + cy.intercept commands.
🎁 You can find the code shown in this blog post in my Cypress Basics Workshop.
Let's say we set our backend with the data items from the fixture file. The initial code looks like this:
1 | beforeEach(() => { |
Now we want to visit the /todos/1
resource to confirm the JSON is returned.
1 | it('tries to visit JSON resource', () => { |
We get an error.
Hmm, how do we "convince" Cypress that the received response should be treated as HTML text? By intercepting and overwriting the response content type header!
1 | it('visits the todo JSON response', function () { |
The above works.
I like showing the response using this approach because it becomes visible in the test video, and can be captured using cy.screenshot command.
Let's confirm the title of the first todo is shown on the page. Because we have used function () { ... }
syntax as the test callback, we can access the alias todos
using this.todos
inside the test.
1 | cy.visit('/todos/1') |
If you hover over the CONTAINS
command, notice the found DOM element on the page is not highlighted.
This is because the response does not include the <body>
element. Let's wrap our JSON response in some markup and make it prettier.
1 | cy.intercept('GET', '/todos/*', (req) => { |
Now the element is highlighted correctly.
The last part I want to show is how to validate the URL using regular expression named captured groups. The URL should have the todo ID "1". We could split the pathname and get the id by index, but that is hard to maintain.
1 | cy.location('pathname') |
If the resources move from /todos/1
to /api/todos/1
finding all the test places where we get the ID part is going to be tricky. Instead let's use a regular expression to grab the ID via named capture group.
1 | cy.location('pathname') |
Beautiful.