2

I'm trying to get AngularJS to trigger a file download when a user clicks on a button.

The file that should download has to contain data that is generated during the script execution, so the text file's content should be built from a basic string in AngularJS.

How do I implement this?

Here is some mockup code on how I imagine this would work:

var fileContent = 'foobar';
$scope.download = function() {
  filedownload.run(fileContent, 'filename.txt');
}
Graham
  • 7,431
  • 18
  • 59
  • 84
Nicolai Schmid
  • 1,022
  • 1
  • 14
  • 29
  • 1
    Possible duplicate of [How do you serve a file for download with AngularJS or Javascript?](http://stackoverflow.com/questions/16514509/how-do-you-serve-a-file-for-download-with-angularjs-or-javascript) – georgeawg Mar 12 '17 at 23:02
  • [Angular File Saver](https://github.com/alferov/angular-file-saver) is a good polyfill for less modern browsers. – georgeawg Mar 12 '17 at 23:17

2 Answers2

4

In order to achieve this you have to create an a tag in your HTML:

<a download="content.txt" ng-href="{{ url }}">download</a>

Controller:

var content = 'file content for example';
var blob = new Blob([ content ], { type : 'text/plain' });
$scope.url = (window.URL || window.webkitURL).createObjectURL( blob );

And to enable the URL:

app = angular.module(...);
app.config(['$compileProvider',
    function ($compileProvider) {
        $compileProvider.aHrefSanitizationWhitelist(/^\s*(https?|ftp|mailto|tel|file|blob):/);
}]);

Source: How do you serve a file for download with AngularJS or Javascript?

Nicolai Schmid
  • 1,022
  • 1
  • 14
  • 29
  • Use `aHrefSanitizationWhitelist = /^\s*(https?|ftp|mailto|tel|file|blob):/`. For more information see [AngularJS sanitizeUri.js source code line #9](https://github.com/angular/angular.js/blob/master/src/ng/sanitizeUri.js#L9). – georgeawg Mar 12 '17 at 23:00
2

In simple cases, you can create a link with a Data URI:

var fileContent = 'foobar';
$scope.download = 'data:text/plain;base64,' + btoa(fileContent);

And then use it in your HTML template:

<a href="{{download}}">click here to download</a>

You may need to adapt the MIME type, depending on your string.

stholzm
  • 3,395
  • 19
  • 31
  • Thanks. This is an interesting approach. While this does generate a valid link, the download gets rejected in chrome due to an unsafe link error. For explanation: I want to create a vCard file in Angular to download and this is not the right solution. Do you have a follow up idea? Thanks! – Nicolai Schmid Mar 12 '17 at 21:51
  • Maybe Chrome rejects it only when the site is localhost? Other than that, I am out of ideas, sorry. – stholzm Mar 12 '17 at 21:53
  • I actually found a solution myself now. It's basically the same idea as yours – Nicolai Schmid Mar 12 '17 at 22:02
  • See [AngularJS $compileProvider API Reference - aHrefSanitizationWhitelist](https://docs.angularjs.org/api/ng/provider/$compileProvider#aHrefSanitizationWhitelist) – georgeawg Mar 12 '17 at 23:07