cypress-io / cypress

Fast, easy and reliable testing for anything that runs in a browser.
https://cypress.io
MIT License
46.69k stars 3.16k forks source link

migrate from cy.route to cy.intercept for formdata #14439

Closed geyuqiu closed 1 year ago

geyuqiu commented 3 years ago

What would you like?

test works also after migration without refactoring everything

Why is this needed?

current prod code

const formData: FormData = new FormData();
formData.append('subject', topic);
formData.append('body', JSON.stringify(body));
// ...
formData.append(`attachment_${idx}`, img, attachment.fileName);

const request = new HttpRequest(
      'POST',
      url,
      formData,
      {reportProgress: true, responseType: 'text'},
);

currently test code (at version 5.6):

checkEmailRequestBody(): void {
    cy.server();
    cy.route({
      method: 'POST',
      url: this.getUrl(),
      onRequest: function onRequest(req) {
        const subject = req.request.body.get('subject');
        const body = req.request.body.get('body');
        const attachment0 = req.request.body.get('attachment_0');

// ...

this does not work anymore as req.body is of type any, and not of type object

// Assert request body
cy.intercept('POST', '/organization', (req) => {
  expect(req.body).to.include('Acme Company')
})
bahmutov commented 3 years ago

Is this a TypeScript problem or does not actually work (the req.body is invalid)?

yoavniran commented 3 years ago

think im facing the same issue. Im posting a form from my page being tested. When I do:

  cy.intercept({
            method: "POST",
            url: "http://test.upload/url",
        }, (req) => {
            console.log(req);
        });

req is an ArrayBuffer and I cant check whether it contains the params i except it to have.

This is the way I tested before (using server/route):


 cy.wait("@uploadReq")
     .then((xhr) => {
           expect(xhr.request.body.get("fieldA")).to.eq("abc");
           expect(xhr.request.body.get("fieldB")).to.eq("123");

         //more assertions
});

How can I do this with Intercept? (on Cypress 6.5.0)

samtsai commented 3 years ago

You can try decoding the buffer:

String.fromCharCode.apply(null, new Uint8Array(req.body))
OR
new TextDecoder().decode(req.body)

But I'm also facing this issue #14527 which prevents me from upgrading to 6.5.0.

Alternatively, you could upgrade/downgrade to 6.2.0 where req.body is a string.

yoavniran commented 3 years ago

I actually ended up writing a small command to handle multiple/form-data request body.

Just published to NPM - https://www.npmjs.com/package/cypress-intercept-formdata In case others find it useful as well.

Would have liked to see this simply handled by cypress but until then, this simple command works well for me

PhilippSpo commented 3 years ago

We've noticed an issue that may be related to this.

When intercepting a request with form-data in 6.6.0, the request body gets lost ā€“ it doesn't arrive at the server.

In 6.2.0 where the body is still a string, the request body doesn't get lost and the server receives it just fine.

To me this seems like a bug šŸ„ŗ. I can provide an example repo if needed.

jennifer-shehane commented 3 years ago

Is this issue still ocurring? We've had several fixes for intercept 7.0+, can anyone update and verify?

joaoghummel commented 3 years ago

This still ocurring.

yoavniran commented 3 years ago

@jennifer-shehane Im on 7.3.0 and still need cypress-intercept-formdata to be able to work with mutlipart requests

electrofLy commented 3 years ago

In our case stubbing a form data request with cy.intercept() malforms it - we are getting "Missing start boundary" when trying to serialize it on the backend. Using cypress 7.5.0. This works using cy.route() and it also works if we are not stubbing it.

cypress-app-bot commented 1 year ago

This issue has not had any activity in 180 days. Cypress evolves quickly and the reported behavior should be tested on the latest version of Cypress to verify the behavior is still occurring. It will be closed in 14 days if no updates are provided.