Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for changing path to the downloads folder in cypress configuration #4675

Closed
joszo opened this issue Jul 9, 2019 · 27 comments
Closed
Labels
type: duplicate This issue or pull request already exists

Comments

@joszo
Copy link

joszo commented Jul 9, 2019

Hello,

could you add to the configuration something like:

downloadFolder: cypress/download

Normally it's downloaded to the /Users/username/Downloads/fileName.example but I want to make it more elastic for other people which after running the tests, doesn't have to change path to the downloads.

@joszo joszo changed the title Add support for changing path downloads in cypress configuration Add support for changing path to the downloads folder in cypress configuration Jul 9, 2019
@jennifer-shehane jennifer-shehane added the stage: needs information Not enough info to reproduce the issue label Jul 9, 2019
@jennifer-shehane
Copy link
Member

Normally it's downloaded to the /Users/username/Downloads/fileName.example

Could you be more specific about what 'it' is here? What is downloading to this path? Are you talking about downloading Cypress?

@joszo
Copy link
Author

joszo commented Jul 9, 2019

I'm running test in cypress which downloads the file.
Now it's downloaded to the /Users/${username}/Downloads/ folder.
After that, I would like to verify if the file exists in the system, and then I want to delete the file.

I think a nice feature would be that users could specify where the file should be downloaded. For example .../cypress/download. Do you get an idea?

@dannynicolas
Copy link

dannynicolas commented Jul 11, 2019

I think joszo may mean Setting the default download folder to a specific path. There's quite a bit of past-history when doing this using chrome headless and selenium, so there might be some additional research to do.

@joszo
Copy link
Author

joszo commented Jul 11, 2019

This is exactly what I meant :)

In Protractor there was something like that:

var path = require('path');
var downloadsPath = path.resolve(__dirname, './downloads');
................
'chromeOptions': {
           prefs: {
            download: {
              'prompt_for_download': false,
              'default_directory': downloadsPath
            }
          }
        }

And then we could specify the default folder to the cypress folder, so we could easier verify files, delete them or whatever we want to do with them.

So far I created some workaround for my purpose:

module.exports = (on, config) => {
	on('task', {
		deleteFile(fileName) {
			const fs = require('fs');
			const userName = require('os').userInfo().username;
			const downloadPath = `/Users/${userName}/Downloads/`;
			const absolutePath = downloadPath + fileName;
			const fileStats = fs.statSync(absolutePath);
			const fileSize = fileStats.size;

			if (fs.existsSync(absolutePath) && fileSize > 0) {
				try {
					fs.unlinkSync(absolutePath);
					console.log('File deleted');
					return null;
				} catch (err) {
					console.log(err);
				}
			}
			console.log('File is not exists');
			return null;
		}
	});
};

And usage looks like that:

cy.task('deleteFile', `${fileName}.pdf`)

I know that is not beautiful... but I'm not sure how it would behave on CI etc... 😢

@jennifer-shehane
Copy link
Member

Thanks for clarifying! This feature is duplicate of a requirement of this issue: #949 You may find some better workarounds in that thread too.

@jennifer-shehane jennifer-shehane added type: duplicate This issue or pull request already exists and removed stage: needs information Not enough info to reproduce the issue labels Jul 15, 2019
@natejcho
Copy link

natejcho commented Aug 7, 2019

This issue is not a duplicate, the referenced ticket above focusses on the download dialogue, and only mentions changing the download location.

Still having issue in changing the default location

@joszo
Copy link
Author

joszo commented Aug 7, 2019

@natejcho this is exactly what I had in mind :)

@pwagh88
Copy link

pwagh88 commented Aug 16, 2019

I am also facing the same issue as specified by @joszo
Once the file is downloaded, need to verify if the file exists in the system

@natejcho
Copy link

#949 (comment)

I replied in this thread my working solution.

@CuriousSoul230
Copy link

@joszo #4675 (comment)
Your comment mentioned in the above link was useful to me. Trying to implement it but were you successful in implementing this in CI?

@joszo
Copy link
Author

joszo commented Feb 10, 2020

@joszo #4675 (comment)
Your comment mentioned in the above link was useful to me. Trying to implement it but were you successful in implementing this in CI?

I will try tomorrow to run that solution in the CI, and I will inform you @CuriousSoul230

@natejcho
Copy link

@joszo #4675 (comment)
Your comment mentioned in the above link was useful to me. Trying to implement it but were you successful in implementing this in CI?

This runs fine in our pipeline.

Our stack uses Docker and gitlab. we export the downloads as an artifact

@CuriousSoul230
Copy link

CuriousSoul230 commented Feb 11, 2020

@joszo @natejcho

const downloadPath = `/Users/${userName}/Downloads/

Is the above statement working for you? I am getting the below error :(

cy.readFile("/Users/root/Downloads/Task1.json") failed because the file does not exist at the following path: /Users/root/Downloads/Task1.json

@CuriousSoul230
Copy link

@natejcho In your case do you set the path were the file is downloaded. I need to read the file and assert on some values before deleting them.

@joszo
Copy link
Author

joszo commented Feb 11, 2020

@joszo @natejcho
const downloadPath = `/Users/${userName}/Downloads/
Is the above statement working for you? I am getting the below error :(
cy.readFile("/Users/root/Downloads/Task1.json") failed because the file does not exist at the following path: /Users/root/Downloads/Task1.json

I think the problem will also occur if you will try to run tests in headless mode locally npx cypress run , because the browser tries to open pop up for confirmation of the save.

In free time I will try to figure out how to solve it, the solution which comes to mind is like @natejcho mentioned use docker (probably they use it with XVFB, so the tests are run in the CI in GUI mode).

Maybe I'm wrong... In the meantime, there is a nice article about using cypress with docker: https://www.cypress.io/blog/2019/05/02/run-cypress-with-a-single-docker-command/

@CuriousSoul230
Copy link

#4675 (comment)
Locally in headless mode I am not facing any issue, since the browser setting prevents pop up for confirmation of the save. I am not sure the behavior in the runners. We are also using Gitlab and Docker. Only if I can somehow find the actual downloadPath in Runners.

@joszo
Copy link
Author

joszo commented Feb 11, 2020

#4675 (comment)
Locally in headless mode I am not facing any issue, since the browser setting prevents pop up for confirmation of the save.

how did you avoid that pop up - #5651 in this issue we have example of pop up.

@CuriousSoul230
Copy link

@joszo
I am running in chrome headless mode which as u mentioned earlier is in XVFB and runs in GUI mode. In my local ,the browser settings>advanced>downloads has the setting 'Ask where to save each file before downloading' disabled. That is preventing the pop up. But I dont know how it is behaving in CI runners.

@natejcho
Copy link

@joszo @natejcho
const downloadPath = `/Users/${userName}/Downloads/
Is the above statement working for you? I am getting the below error :(
cy.readFile("/Users/root/Downloads/Task1.json") failed because the file does not exist at the following path: /Users/root/Downloads/Task1.json

in my solution above, the download will save relative to the project root directory so
My-Project/plzDownload.json

@natejcho
Copy link

natejcho commented Feb 11, 2020

#4675 (comment)
Locally in headless mode I am not facing any issue, since the browser setting prevents pop up for confirmation of the save.

how did you avoid that pop up - #5651 in this issue we have example of pop up.

in the solution I posted #949 (comment) you intercept the download. Attach the contents of the download to an a tag, read the raw html for the byte string (or whatever format you choose) and then write that to a file in your project directory.
Doing all this will never trigger the download confirm popup because as far as your browser is concerned, you never actually download anything

@ris314
Copy link

ris314 commented May 19, 2020

I faced this today and found the formal docs extremely helpful:
https://docs.cypress.io/api/plugins/browser-launch-api.html#Change-download-directory

@gowrishyadalam
Copy link

@ris314, I changed the download folder as u suggested in the previous comment, that code works fine with chrome browser, but I am getting an error while I am running test cases in electron browser
Below is error response

Cannot set property 'download' of undefined
TypeError: Cannot set property 'download' of `undefined`

@egretsRegrets
Copy link

egretsRegrets commented Jul 9, 2020

@ris314, I changed the download folder as u suggested in the previous comment, that code works fine with chrome browser, but I am getting an error while I am running test cases in electron browser
Below is error response

Cannot set property 'download' of undefined
TypeError: Cannot set property 'download' of `undefined`

Changing the download directory as suggested by the docs plugin example(https://docs.cypress.io/api/plugins/browser-launch-api.html#Change-download-directory) works for me when running with chrome. However, I'm seeing 'TypeError: Cannot set property 'download' of undefined' when running headless with electron (default).

@jennifer-shehane
Copy link
Member

jennifer-shehane commented Jul 10, 2020

Yeah, I think the options have to be different for Electron (sigh). I'll update the docs example. cypress-io/cypress-documentation#2971

I'm thinking this is not going to be configurable in Electron as is so you'll want to run cypress run --browser chrome.

@jennifer-shehane
Copy link
Member

File download is now supported in Cypress 6.3.0.

You can now test file downloads in Cypress without the download prompt displaying. Any files downloaded while testing file downloads will be stored in the downloadsFolder which is set to cypress/downloads by default. The downloadsFolder will be deleted before each run unless trashAssetsBeforeRuns is set to false.

This means that if you had any code written to prevent the download prompt or to configure the download location (like in a before:browser:launch event handler), you can remove all of these workarounds.

Our file download recipe has been updated, so you can see some ways to test different types of files after they've been downloaded there.

If you're encountering any bugs while testing file downloads, please open a new issue.

@shreeti91
Copy link

shreeti91 commented Jun 1, 2021

@jennifer-shehane
I have been trying to download a pdf file in firefox. For this, I referred to the below link:
https://github.com/cypress-io/cypress-example-recipes/blob/master/examples/testing-dom__download/cypress/integration/local-download-spec.js#L95

I want to download the pdf in "Cypress.config('downloadsFolder')" folder. I also used firefox browser preferences also to avoid pop-up and download directly inside my project. But even after multiple trials, I could not. Everytime, i can download only inside default download folder or on Desktop location based on values (0,1) of ['browser.download.folderList'] . Below is the before:browser:launch options that I used in plugins/index.js

module.exports = (on, config) => {
 
  on('before:browser:launch', (browser = {}, options) => {
    
         const downloadDirectory = process.cwd()+"\\cypress\\downloads"
        // prevents the browser download prompt
        if (browser.family === 'firefox') {
          options.preferences['browser.download.dir'] = downloadDirectory
          options.preferences['browser.download.folderList'] = 2
          options.preferences['browser.download.panel.shown'] = true
          options.preferences['browser.download.manager.focusWhenStarting'] = false
          options.preferences['browser.helperApps.neverAsk.saveToDisk'] = 'application/pdf','application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'
          options.preferences['browser.download.manager.useWindow'] = false
          options.preferences['pdfjs.disabled'] = true
          options.preferences['devtools.console.stdout.content'] = true
          options.preferences['intl.accept_languages'] = 'en-US'
        return options
             
        }  
  })

Is it possible to download the pdf inside cypress/downloads by using the firefox browser?
FYI: it works fine with Electron browser

Thanks in advance

@jennifer-shehane
Copy link
Member

@shreeti91 IF this is a question on using Cypress, you may want to try asking our community in our GitHub Discussions. As an open source project with a small maintainer team we have to focus our time on bugs and features in the product, which Issues are reserved for.

@cypress-io cypress-io locked as resolved and limited conversation to collaborators Jun 16, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
type: duplicate This issue or pull request already exists
Projects
None yet
Development

No branches or pull requests

10 participants