Downloading files with Ember app - ember.js

I have Ember App (built with Ember-CLI). On the backend I have Rails application which handles requests. Lets say that my API has following routes:
/model — returns list of models
/model/1 — returns model
/model/1/download — returns file
How can I force Ember app to start file download (using /download path) and how can I construct link for file download from within Ember app?

Why don't you just return the URL path for the download in your model for "/model/1". Then you can easily create links in your handlebars templates like so:
Download File

If you're going to hit the endpoint and return the file contents, I believe you'll need to set the Content Disposition header. More details here: Force download through js or query
Content-disposition=attachment; filename=some.file.name
If you are linking to the file directly, you could use the HTML5 download attribute;
<a href="{{model.download}}" download>Download File</a>

Don't do any of these manually, keep it simple and use ember-cli-file-saver!
// models/invoice.js
export default Model.extend({
invoiceNumber: attr('number'),
download: memberAction({ path: 'download', type: 'GET', ajaxOptions: { arraybuffer: true } })
});
// in a component
invoiceModel
.download()
.then((pdfContent) => this.saveFileAs('invoice.pdf', pdfContent, 'application/pdf'));

Related

vuejs app with vue router hosted on amplify direct url to file doesn't work

I have an issue on which I struggled all day long, I have a VueJS app with vue router that I host on amplify?
everything working great Except that
I need to give a direct access to a file (I want to register an Apple merchant ID with stripe)
I tried to create a route in my route/index.js with my file name that redirect to a component that open the merchantid file with an windows.open('myfile').
it works great on local serve and build but not once deployed through amplify built with webpack
//router/index.js
import WellKnown from '#/components/AppleVerification.vue'
Vue.use(VueRouter)
const routes = [
{
path: '/.well-known/apple-app-site-association',
component: WellKnown,
}
]
const router = new VueRouter({
mode: 'history',
routes
})
export default router
// AppleVerification.vue
<template>
<div></div>
</template>
<script>
export default {
name: 'WellKnown',
props: {
file: String
},
mounted () {
window.open('file:///.well-known/apple-developer-merchantid-domain-association')
}
}
</script>
so I went to amplify console and make a redirection with first priority to the URL and target address to the file. but it didn't work also.
I went out of ideas on how to give access to a file in my sources with a direct URL.
would appreciate a little help
thanks
You issue comes from the acces to the file througth Amplify for several reasons.
Try following:
rename your endfile "apple-developer-merchantid-domain-association"
with an extension like
apple-developer-merchantid-domain-association.txt
remove the dot in your path public/.well-known/apple-developer-merchantid-domain-association to public/well-known/apple-developer-merchantid-domain-association.txt
in your amplify console create a priority 1 rule that redirects your
https://mydomain/.well-known/apple-developer-merchantid-domain-association to
/well-known/apple-developer-merchantid-domain-association.txt with a 202 rexrite method.
It should work
You even didn't need the component anymore

Ember CLI Download Excel [Save As] - blob/binary format Error

I'm making an AJAX POST request from ember-cli to django rest framework in order to enable user to download excel/xls file. However, I'm stuck into formating problem, the file pops up but the content of the xls is not in correct format.
Here's the code I use in the controller:
Ember.$.ajax({
type: "POST",
url: "http://api.dev.maspa.biz/api/v1/panel/catalog/export",
data: 'ids=' + ids,
success: function(data) {
var hiddenElement = document.createElement('a');
hiddenElement.href = 'data:application/vnd.ms-excel' + encodeURI(data);
hiddenElement.target = '_blank';
hiddenElement.download = 'export.xls';
hiddenElement.click();
},
})
Looking for your helpful reply.
Thanks
Have you thought about using an ember addon to handle this export for you? It could be more reliable than coding it yourself.
Check out this add-on - https://github.com/roofstock/ember-cli-data-export.

ember cli multiple index files

I have an ember-cli based app which needs to be integrated into an existing java/JSP app. For this to happen I need to generate a JSP file with js/css fingerprinted URLs which are generated by ember-cli/broccoli-asset-rev.
This is working fine for a html file and I can set it use a JSP file by changing my Brocfile.js to include:
var app = new EmberApp({
outputPaths: {
app : {
html: 'index.jsp'
}
}
});
but this prevents ember serve working as it uses the index.jsp as the html file. Is it possible to have both generated?
After trying many things I have come up with two solutions, both have drawbacks. The first is to use make a new broccoli tree and merge it with he app tree then explicity run broccoli-asset-rev on the resulting tree. The downside of this is that the mustache does not get hydrated, this is useful for outputting config. This would look something like:
//Brocfile.js
var mergeTrees = require('broccoli-merge-trees');
var funnel = require('broccoli-funnel');
var assetRev = require('broccoli-asset-rev');
var EmberApp = require('ember-cli/lib/broccoli/ember-app');
var jspTree;
var app = new EmberApp({
fingerprint: {
enabled: false
},
storeConfigInMeta: false
});
jspTree = funnel('app', {
files: ['index.jsp']
});
module.exports = assetRev(mergeTrees([appTree = app.toTree(), jspTree]), {
extensions: ['js', 'css'],
replaceExtensions: ['jsp', 'html']
});
The other solution is the override a private api method in ember-cli which builds the tree for the index. This solution does let the mustache get hydrated but relies on a private method. You can find details here and here
How about adding symbolic link?
ln -s index.jsp index.html
Depending on what build tool you're using in your project, I'd probably recommend something like the following:
Put some placeholder sections in your index.html.
Copy index.jsp to index.jsp.tmp.
Copy in code from index.jsp into your placeholder sections.
Move index.jsp.tmp back to index.jsp and clean up.
You might consider something like gulp-replace to do the work.

Setting up Client Credentials OAuth2 with ember-cli and ember-simple-auth

I have been trying to setup OAuth2 client credentials flow with ember-cli and Rails API back-end and have hit a dead-end. Maybe because I'm new to ember. What I'm trying to do currently is this:
bower.json
{
"ember-simple-auth": "*"
}
Brocfile.js
app.import('vendor/ember-simple-auth/simple-auth.amd.js')
app.import('vendor/ember-simple-auth/simple-auth-oauth2.amd.js')
initializers/login.js
App.initializer({
name: 'Register Components',
initialize: function(container, application) {
registerComponents(container);
Ember.SimpleAuth.setup(application);
}
});
controllers/login.js
import LoginControllerMixin from 'simple-auth/mixins/login-controller-mixin';
export default Ember.Controller.extend(SimpleAuth.LoginControllerMixin, {
authenticatorFactory: 'simple-auth-authenticator:oauth2-password-grant'
});
templates/login.hbs
<form {{action authenticate on='submit'}}>
<label for="identification">Login</label>
{{view Ember.TextField id='identification' valueBinding='identification' placeholder='Enter Login'}}
<label for="password">Password</label>
{{view Ember.TextField id='password' type='password' valueBinding='password' placeholder='Enter Password'}}
<button type="submit">Login</button>
</form>
Any guides, tutorials or corrections in this regard is appreciated.
The latest release of Ember Simple Auth dropped the need for defining an initializer and added Ember CLI Addons for the library which make setting up everything a lot easier. Also the README and API docs now focus on using the library with Ember CLI which should help you a lot.
Checkout the README: https://github.com/simplabs/ember-simple-auth#readme
I recently discussed this on GitHub. This is what I ended up doing to authenticate the client using HTTP Basic Authentication (in app/app.js):
import OAuth2Authenticator from 'simple-auth-oauth2/authenticators/oauth2';
OAuth2Authenticator.reopen({
makeRequest: function(data) {
var clientId = MyProjectENV.APP.apiClientId;
var clientSecret = MyProjectENV.APP.apiClientSecret;
return Ember.$.ajax({
url: this.serverTokenEndpoint,
type: 'POST',
data: data,
dataType: 'json',
contentType: 'application/x-www-form-urlencoded',
headers: { "Authorization": "Basic " + btoa(clientId + ":" + clientSecret) }
});
}
});
and in config/environment.js:
var ENV = {
// ...
APP: {
apiClientId: "12345",
apiClientSecret: "abcdefg987654"
}
You can include the client id by setting the OAuth 2.0 authenticator's clientId property (see API docs: http://ember-simple-auth.com/api/classes/OAuth2PasswordGrantAuthenticator.html#property_clientId). Contrary to what other answer suggest here you should never ever include a client secret. As soon as you use a secret anywhere in your Ember app it's not a secret anymore as it is included in the source and visible for everyone who has access to the source (which usually is everybody on the whole internet).
Web clients are public clients in terms of OAuth that cannot be trusted, thus cannot use a client secret. You can use the client id for analytics etc. but you shouldn't even trust that on the server side as it could easily be manipulated and of course also used by other clients as it can simply be looked up from the app source.
So please everybody remember:
Never ever use a client secret in an Ember app!!!1!1!
Thanks to the huge effort of marcoow Ember-Simple-Auth supports an easy way of adding a client_it by now!
The value of clientId is set to null in the default authenticator by ESA (see file node_modules/e-s-a/addon/authenticator/oauth2-password-grant.js)
You can override the value in your custom authenticator in the same way you would override your custom server token endpoint.
// app/authenticators/oauth2.js
import OAuth2PasswordGrant from 'ember-simple-auth/authenticators/oauth2-password-grant';
import ENV from '../config/environment';
export default OAuth2PasswordGrant.extend({
serverTokenEndpoint: `${ENV.api.host}/oauth/token`,
clientId: `${ENV.APP.apiClientId}`,
});
You might consider the authors opinion on setting the client_id in this github discussion on esa.
UPDATE:
I updated the source code and deleted the client secret since you should not include it an ember app.

How to use Hogan.js in a separate js file

This question is from this thread:
Twitter Typeahead.js with Flask Jinja2 Templating
As suggested, I am trying to separate my js file. Here is the code
$('#search').typeahead({
name: 'Search',
local: {
value: 'String',
tokens: ['Test1','Test2']
language: 'English'
},
template: {{language}},
engine: Hogan
});
I understand what the problem is, but how do I "include" hogan.js? I have installed node.js and I can make it work through that, however, I don't understand how to apply it through flask.
If you are including a static file you can use Flask's url_for.
http://flask.pocoo.org/docs/quickstart/#static-files