Force download-window to open on file download - javascript

is there a way to force the browser through JavaScript/TypeScript to open the download-window. I'd like to open the download-window because most users are downloading directly to the download folder and I'd like to offer the user the possibility to rename the file and to choose the download folder.
I enable the download like this:
const json = JSON.stringify(data);
const blob = new Blob([json], {type: 'application/json'});
const url = URL.createObjectURL(blob);
const a = document.getElementById('export');
a.download = 'export.json';
a.href = url;

Full blogpost for the same : Download File in Angular Js2 Application
this two line missing in you code :
var url= window.URL.createObjectURL(b);//add this line
window.open(url);//add this line for download
I suggest try like this :
constructor(private http:Http)
{}
DownloadFile():void
{
this.getFile("http://localhost:1800/api/demo/GetTestFile")
.subscribe(fileData =>
{
let b:any = new Blob([fileData], { type: 'application/zip' });
var url= window.URL.createObjectURL(b);//add this line
window.open(url);//add this line for download
}
);
}
public getFile(path: string):Observable<any>{
let options = new RequestOptions({responseType: ResponseContentType.Blob});
return this.http.get(path, options)
.map((response: Response) => <Blob>response.blob()) ;
}
similar answer by me : Angular JS empty pdf in new window

Related

CSV file from server URL not downloading

I'm messing with a piece of code to download a CSV from server. this is what I'm trying:
downloadCSVTemp(){
let name = 'report.csv';
const response = api.getReportCSV()
.then((res)=>{
const blob = new Blob([res], { type: "data:text/csv;charset=utf-8," });
const blobURL = window.URL.createObjectURL(blob);
const anchor = document.createElement("a");
anchor.download = name;
anchor.href = blobURL;
anchor.dataset.downloadurl = ["text/csv", anchor.download, anchor.href].join(
":"
);
anchor.click();
});
}
getReportCSV(){
return axios.get("/export/assessments/");
}
I intend to download a csv file from server url by an axios call, But this code is downloading an csv file which can't be opend by the browser & full of garbage data. What's the problem here ?
The res argument contains Axios response object. When creating the blob, you should use res.data:
new Blob([res.data], { type: "data:text/csv;charset=utf-8," });

React - Downloading a Zip File from API Response Body in Bytes String?

I have a working API call that returns in the response body a string prepared in Bytes format on the Python side that is a zip file. The String looks something like this, but longer:
PK��Q��F���������������/export_file.csv��uX\M�
This is a zip file containing one csv file. In tools such as postman, hitting the same POST endpoint with the same parameters in the body, I can successfully download a valid zip file, unzip the contents, and view the .csv file. In the browser debugger tools, I can see the API endpoint returning a successful response, with the same string above in the body.
Where I have failed at every attempt is on the react side, doing the work necessary to take this string and download the same zip file. Every suggestion I've read on SO and everywhere else has failed me. Here is what some of my failed attempts look like:
(Also note that a successful API call returns a 26kb payload from this example)
export function downloadZipFile(responseBody){
/* Blob Attempts */
// These download a 46kb file. Attempting to open gives "The compressed zip folder is invalid"
// var blob = new Blob([responseBody], {type: "content-type"});
// var blob = new Blob([responseBody], {type: "application/zip"});
// var blob = new Blob([responseBody], {type: "application/zip, application/octet-stream"});
// var blob = new Blob([responseBody], {type: "application/octet-stream"});
// var blob = new Blob([responseBody], {type: "octet/stream"});
var fileName = "export.zip";
saveAs(blob,fileName);
/* Data String Attempts */
// const dataStr = "data:application/zip;" + responseBody; // "Failed - Network Error"
// const dataStr = "data:application/zip, application/octet-stream;" + responseBody; // Downloads 1kb File "The compressed zip folder is invalid"
// const dataStr = "data:application/zip,application/octet-stream;" + responseBody; // Downloads 1kb File "The compressed zip folder is invalid"
// const dataStr = "data:application/octet-stream;" + responseBody; // "Failed - Network Error"
let downloadElement = document.createElement('a');
downloadElement.setAttribute("href", dataStr);
downloadElement.setAttribute("download", "export.zip");
document.body.appendChild(downloadElement);
downloadElement.click();
downloadElement.remove();
}
I've arrived late, but hope to help someone.
It is really important to set responseType as 'arraybuffer' in the api call, like this:
...
export const getZip = async (id) => {
const { data } = await axios.get(
"/sypa-applications/export",
{
id
},
{ responseType: "arraybuffer" }
);
return data;
}
...
Then you can download the ZIP from both ways:
1.- Using file-saver npm dependency:
let blob = new Blob([data], { type: "application/zip" });
saveAs(blob, "fileName.zip");
2.- Using DOM:
const url = window.URL.createObjectURL(new Blob([data], { type: "application/zip" });
const link = document.createElement("a");
link.href = url;
link.setAttribute("download", "fileName.zip");
document.body.appendChild(link);
link.click();
link.parentNode.removeChild(link);
I couldn't download the ZIP until I set the responseType param to "arraybuffer" in the GET request.
Best regard,
Alberto.
Did you check this tool? https://gildas-lormeau.github.io/zip.js/
There is an example for unzipping a file using js in the browser. http://gildas-lormeau.github.io/zip.js/demos/demo2.html
It seems that this is what you want. First unzip the file and the use the .csv as wanted

Typescript download PDF file have empty contant

I have a script to download different type files from server side. The code works for text/xml but when the downloaded pdf file is empty.
let response = this.http.get(this.Url , new Headers({responseType: 'blob'}))
.subscribe(doc => {
if (doc) {
let contentType = doc.headers.get("Content-Type");
let name = doc.headers.get("Content-Disposition").split("=")[1];
let blob = new Blob([doc.text()], {type: contentType});
let a = window.document.createElement("a");
a.href = window.URL.createObjectURL(blob);
a.download = name;
document.body.appendChild(a);
a.click();
document.body.removeChild(a);
}
},
error => this.msgService.showError(this.msgs, error));
My server
#GET
#Consumes(MediaType.APPLICATION_JSON)
#Path("-----")
public Response getDocument(#PathParam("documentId") Long documentId) throws Exception {
Document document = ---------------;
return ResponseHelper.createOkResponse(
output -> IOUtils.write(document.documentContent(), output),
document.documentName(),
document.documentType()
);
}
I can see the doc.text() is returning some byte[]. Also tried {responseType: 'arraybuffer'}. can anyone advise how can i display for pdf ?
Thanks

How to get a File() or Blob() from an URL in javascript?

I try to upload an image to the Firebase storage from an URL (with ref().put(file))(www.example.com/img.jpg).
To do so i need a File or Blob, but whenever I try new File(url) it says "not enough arguments“…
EDIT:
And I actually want to upload a whole directory of files, that’s why i can’t upload them via Console
Try using the fetch API. You can use it like so:
fetch('https://upload.wikimedia.org/wikipedia/commons/7/77/Delete_key1.jpg')
.then(res => res.blob()) // Gets the response and returns it as a blob
.then(blob => {
// Here's where you get access to the blob
// And you can use it for whatever you want
// Like calling ref().put(blob)
// Here, I use it to make an image appear on the page
let objectURL = URL.createObjectURL(blob);
let myImage = new Image();
myImage.src = objectURL;
document.getElementById('myImg').appendChild(myImage)
});
<div id="myImg"></div>
As of July 2022, the fetch API has about 97% browser support worldwide, with basically just IE missing it. You can get that to near 100% using a polyfill, which I recommend if you're still targeting IE.
#James answer is correct but it is not compatible with all browsers. You can try this jQuery solution :
$.get('blob:yourbloburl').then(function(data) {
var blob = new Blob([data], { type: 'audio/wav' });
});
It did not work until I added credentials
fetch(url, {
headers: {
"Content-Type": "application/octet-stream",
},
credentials: 'include'
})
async function url2blob(url) {
try {
const data = await fetch(url);
const blob = await data.blob();
await navigator.clipboard.write([
new ClipboardItem({
[blob.type]: blob
})
]);
console.log("Success.");
} catch (err) {
console.error(err.name, err.message);
}
}
If you are using homepage in package.json then ypu have to use:
CurrentUrl: http://localhost:3008/tempAppHomepageFromPackageJson/
const file: File = this.state.file;
const localUrlToFile = URL.createObjectURL(file);
const fileHash = localUrlToFile.split('/');
const objectUrl = location.href + fileHash[fileHash.length - 1];
objectUrl is the local url to file. For example to show in runtime you uploading file.
Second solution is (if you have no homepage in package.json):
const file: File = this.state.file;
const objectUrl = window.URL.createObjectURL(file);
Third solution (Not working in safari):
const file: File = this.state.file;
let reader = new FileReader();
reader.readAsDataURL(file);
const objectUrl = reader.result as string;
Enjoy ;)

How to download image from a url in chrome app using chrome filesystem api?

I have a url which has a image. I want to download that image using chrome api. I am developing a chrome app and not extension.
Can anyone please tell me where i am going wrong??
My code:
service('fileService', function($window){
this.saveUserInfo = function(theFilePath) {
// filepath is the url passed from controller{
// Get the directory entry stored (if any).
var fileUrl = "";
var config = {
type: 'saveFile',
suggestedName: 'TheBee.png',
accepts:[{extensions: ['png', 'jpg', 'jpeg']}]
};
chrome.fileSystem.chooseEntry(config, function(writableEntry) {
chrome.fileSystem.getWritableEntry(writableEntry, function(entry1) {
entry1.getFile(theFilePath, {create:true}, function(entry2) {
entry2.createWriter(function(writer) {
var blob = new Blob({type: 'image/png'});
writer.write(blob);
});
});
});
});
});
});
Change
var blob = new Blob({type: 'image/png'});
To
var blob = new Blob([entry1],{type: 'image/png'});
The Blob contructor acceptes blob parts: MSDN=> Blob(blobParts[, options])
You cannot use getFile on entry1 because it is a file itself. You will need to change config.type to "openDirectory"
You also need to add an empty array as the first input to the blob constructor.

Categories