Отправить загруженный файл на сервер в Cypress - PullRequest
0 голосов
/ 20 декабря 2018

Я использую Cypress, чтобы использовать свое приложение, и столкнулся с проблемой, отправив загруженный файл на сервер.Он отправляет пустой FormData.

Я использую код, найденный здесь https://github.com/cypress-io/cypress/issues/170, для обработки загрузки файла:

 return cy.get('input[type=file]').then(subject => {
    return cy
        .fixture('blueprint.xlsx', 'base64')
        .then(Cypress.Blob.base64StringToBlob)
        .then(blob => {
            const el = <HTMLInputElement>subject[0]
            if (el != null) {
                const testFile = new File([blob], 'blueprint.xlsx')
                const dataTransfer = new DataTransfer()
                dataTransfer.items.add(testFile)
                el.files = dataTransfer.files
            }
            return subject
        })
}) 

Когда я отлаживаю вызов API,файл установлен, он находится в папке fixtures, и все выглядит нормально, но вызов не имеет никаких формданных (что должно быть файлом) и заканчивается ошибкой 400 Bad request.

Почему именно формданныепусто?Это проблема кипариса?Есть ли способ отправить файл моего прибора на сервер?

Ответы [ 3 ]

0 голосов
/ 27 февраля 2019

после многих часов попыток, я нашел обходной путь, чтобы сделать ng-file-upload работоспособным.

По крайней мере, моя проблема была в файле, который не был передан как экземпляр Blob, я думаю.

Я использовал тот же фрагмент, что и Jonas, на стороне кипариса.

Обходной путь - добавить проверку в функцию загрузки, которая управляет изменениями в директивах select и drop.

function upload() {
    if (!Upload.isFile(file)) {
      file = new File([file], file.name, { type: file.type })
    }

    Upload.upload({
        url: "/api/upload",
        data: {
          file: file
        }
    })
    .then(/* ... */)
    /* ... */
}

Это просто обходной путь, и он мне не очень нравится.

Я не знаю, почему это происходит, это происходит для меня, только когда я тестирую его с помощью кипариса, поэтому я не люблю добавлять это в свой производственный код.

Может кто-нибудь помочь мне понять, почему это происходит?

Кто-нибудь знает, почему экземпляр файла, переданный в функцию загрузки, кажется экземпляром файла, но тогда это не так?

0 голосов
/ 04 июня 2019

Я использую "cypress": "3.3.1"

Следующие коды работают для меня,

const fixturePath = 'test.png';
const mimeType = 'application/png';
const filename = 'test.png';

cy.getTestElement('testUploadFrontID')
  .get('input[type=file')
  .eq(0)
  .then(subject => {
    cy.fixture(fixturePath, 'base64').then(front => {
      Cypress.Blob.base64StringToBlob(front, mimeType).then(function(blob) {
        var testfile = new File([blob], filename, { type: mimeType });
        var dataTransfer = new DataTransfer();
        var fileInput = subject[0];

        dataTransfer.items.add(testfile);
        fileInput.files = dataTransfer.files;

        cy.wrap(subject).trigger('change', { force: true });
      });
    });
  });

getTestElement - это команда, добавленная мной самостоятельно,

Cypress.Commands.add(`getTestElement`, selector =>
cy.get(`[data-testid="${selector}"]`)
);
0 голосов
/ 21 декабря 2018

Ваш код работает нормально на демонстрационной странице ng-file-upload .

Я также протестировал файл 'xlsx', проблем не обнаружено.

describe('Angular file upload Demo', () => {

  /*
    To run these tests, add a file 'logo.png' to /cypress/fixtures
  */

  it('uploads the fixture file', () => {
    cy.visit('https://angular-file-upload.appspot.com/')
    cy.get('[name=userName]').type('myLogo')

    cy.get('[name=file]').then(subject => {
      return cy.fixture('logo.png', 'base64')
        .then(Cypress.Blob.base64StringToBlob)
        .then(blob => {
          console.log('blob', blob)
          const el = subject[0]
          if (el != null) {
            const testFile = new File([blob], 'logo.png')
            const dataTransfer = new DataTransfer()
            dataTransfer.items.add(testFile)
            el.files = dataTransfer.files
          }
          return subject          
        })
    })

    cy.contains('button', 'Submit').click()

    cy.contains('.progress', '100%')
    cy.contains('body', 'Upload Successful')
  })

  Cypress.Commands.add('uploadFile', { prevSubject: 'element' }, (subject, fileName) => {
    console.log('subject', subject)
    return cy.fixture(fileName, 'base64')
      .then(Cypress.Blob.base64StringToBlob)
      .then(blob => {
        console.log('blob', blob)
        const el = subject[0]
        if (el != null) {
          const testFile = new File([blob], fileName)
          const dataTransfer = new DataTransfer()
          dataTransfer.items.add(testFile)
          el.files = dataTransfer.files
        }
        return subject          
      })
    }
  )

  it('uploads the file via custom command', () => {
    cy.visit('https://angular-file-upload.appspot.com/')
    cy.get('[name=userName]').type('myLogo')

    cy.get('[name=file]').uploadFile('logo.png')

    cy.contains('button', 'Submit').click()

    cy.contains('.progress', '100%')
    cy.contains('body', 'Upload Successful')
  })

})
...