DEV Community

Cover image for To Puppeteer, or to Cypress
Jalal πŸš€
Jalal πŸš€

Posted on

To Puppeteer, or to Cypress

Working on a layout is not easy when there are too many possibilities and it gets more complicated if it's related to mouse direction. It's not just up and down, you literally need to test all horizontal and vertical possibilities. Imagine you also study elements getting effected by mouse movement, where things getting harder and harder.

In the nutshell, I am a hard unit-test believer, but in this case, you definitely need to do testing and not a unit test we are talking here about an end-to-end test where you see elements moving virtually and experience each case individually.

The big question is how you do it, taking into consideration that your project already uses a unit test with Jest.


Puppeteer it

The wise decision in my case is to use, Puppeteer. You integrate Puppeteer with Jest in jest.integration.config.js a whole new config and start writing your first integration test.

{
  "preset": "jest-puppeteer"
}
Enter fullscreen mode Exit fullscreen mode

Everything is async in Puppeteer so you go by something like this to get your element:

const element = await page.waitForSelector("#id-something");
Enter fullscreen mode Exit fullscreen mode

I need to get element box size so I added:

const elmBox = await element.boundingBox();

const {x, y, width, height} = elmBox

// do something here...
Enter fullscreen mode Exit fullscreen mode

You immediately start to notice that's Puppeteer is natural. I am not learning something new, it's easy to use and you supposedly can go further. Let's try mouse events.

// move the mouse to new coordinates 
await page.mouse.move(100, 200);

// triggers mouse down
await page.mouse.down();

// move the mouse to new horizontal position
await page.mouse.move(500, 200);

// triggers mouse up
await page.mouse.up();
Enter fullscreen mode Exit fullscreen mode

Very easy. Very handy. Except there's a configuration related. you can't keep the browser open, there's no time travel, and you can't repeat the test cases individually. So, if you test and develop by doing TDD it's nearly impossible to actually see what's going on. You can slow down the test but if you running a server and you wait to browser to re-launch that's means waiting for infinity.

launch: {
 devtools: true,
 slowMo: 500,
},
Enter fullscreen mode Exit fullscreen mode

Even with Puppeteer reaching version 5 there's a gap in its ecosystem. Because it's not a testing framework.

Puppeteer is a Node library which provides a high-level API to control Chrome or Chromium over the DevTools Protocol.


Trying Cypress

The first issue with Cypress, that you need to start from scratch. A new assertion, a new testing framework, with a new structure.

install cypress

The installation includes examples that really help to know where you are going and what your test cases should look like. You use a chain of commands. You get something, trigger it, test it.

cy.get("#id-something").then((elm) => {
elmBox = elm[0].getBoundingClientRect();

const {x, y, width, height} = elmBox
});
Enter fullscreen mode Exit fullscreen mode

Cypress uses trigger to trigger an event

cy.get("#id-something")
  .trigger("mousedown", { button: 0 })
  .trigger("mousemove", { clientX: 100, clientY: 200 });
Enter fullscreen mode Exit fullscreen mode

It uses a whole different approach but once you read it you easily get it. Until you start to use assertion.

This is from Cypress documentation:

cy.get('.error').should('be.empty')
cy.contains('Login').should('be.visible')
cy.wrap({ foo: 'bar' }).its('foo').should('eq', 'bar') 
Enter fullscreen mode Exit fullscreen mode

You take a deep breath and ask yourself, should I really have to learn this? Even something like beforeAll in cypress is before. So, you get the sense that whatever transition you make it's not going to be smooth as you expect.

But your test runs with zero-config, with time travel, and yes you can repeat it forever. And it's super-fast.

Cypress is fast

However, my problem is not with speediness. I need, at a certain point to be able to repeat the same test command.

repeate the test

It turns out, Cypress automatically takes a screenshot for every command and you simply can highlight it forever which means a totally new debugging experience.


Conclusion

When it comes to increasing productivity, end-to-end test can be the real solution. Forget about all articles tell you about the benefits of testing and why you should use e2e. I personally experienced a huge difference in fixing bugs saving hours of chasing needles in a haystack.

Puppeteer can be a solution for expanding your test cases. But if you are using it with development, the answer is Cypress.

Cypress is rich with examples, and a supportive community. It's designed for the end-to-end tests; therefore, you won't struggle using it. If you are familiar with Mocha it won't take you a long time to get familiar with assertation. And it's amazing how you can use it even with no previous background about this type of testing. Most importantly, you immediately start experiencing the benefits of each test you write instead of figuring out how to configure it with your project.

Top comments (7)

Collapse
 
shalinibaskaran12 profile image
Shalini Baskaran

Thank you for sharing these article on Puppeteer vs. Cypress! I've been exploring different resources to enhance my test automation skills, I recently came across another article titled 'Playwright vs. Selenium vs. Cypress' that expands on some of the concepts you've covered here. It delves deeper into practical tips, techniques and how to select right framework for testing project . Keep up the great work!"

Collapse
 
jalal246 profile image
Jalal πŸš€

Thank you!

Collapse
 
vitmalina profile image
Vitali Malinouski

It felt like you were a bit biased towards puppeteer, I would guess because of server JavaScript background vs browser JavaScript. I come from browser JS and Cypress feels natural to me. Chaining is popular since jQuery days and in both server/client side JS it is now popularized with Promises. But it is much easier for me to read code that uses chaining then lots of awaits :)

But I would agree with you on a few points you mentioned

  • Assertions in Cypress could be much improved, I still have to look up documentation and cannot memorize them
  • Ability to pause at a command and then step through would be amazing. I tried .debug() and it stops in the middle of Cypress code :(. Also, adding .then(()=>{ debugger; }) has limited usefulness.
Collapse
 
albertodeago88 profile image
Alberto De Agostini

In my opinion Cypress is light years ahead of puppeteer
TestcafΓ© is also nice, especially if you need to test in different browsers

Collapse
 
jalal246 profile image
Jalal πŸš€

unfortunately, I haven't tried TestcafΓ© yet. And I totally agree with you. I think our view toward Puppeteer should change from using it in test to a tool to run Chromium.

Collapse
 
albertodeago88 profile image
Alberto De Agostini

Yep that's the point in my opinion. It's not a testing tool.
You can use it for that (and it's fine), but it's not meant to do that, cypress is

Collapse
 
loopmode profile image
Jovica Aleksic

Hi. You should also try TestcafΓ© - I'd love to hear your comparison!