这是一个非常广泛的问题,但最近经历了所有这些,我相信我可以提供一个详细的回答,我是如何实现它的.这很关键,因为有很多选项,如果你查看大部分教程,他们主要关注的是使用rails后端而不是node或express.js.我会根据你的使用回答这个问题express.js.
我将在前面记住这ember-data是一个完全不同的ember分支,如果你觉得你的项目不需要它的功能而只是使用AJAX请求,你可以绕过它并完全不使用.ember-data为项目的初始启动增加了很多复杂性和开销.此外,TLS/SSL是您可以拥有的最重要的安全性,如果没有它,除此之外任何数量的尝试安全性都是无效的.现在已经开始了,让我们进入设置它的坚韧部分.
默认情况下ember-data使用JSONAPIAdapter基于JSON API规范的.Express.js如果使用默认值Adapter而没有Serializer更改,则您的API服务器必须能够运行此规范
将项目分解为核心组件以及他们需要做什么,以及可用的选项如下(我用粗体做的):
express.jsember-simple-auth 效果很好ember-simple-auth-token 为您提供使用基于令牌的身份验证的预建授权器基本流程如下:
这是我如何设置它
**设置Ember.js使用Express.jsAPI服务器**
为ember-cli安装以下项目:
ember install ember-simple-auth- 用于身份验证
ember install ember-simple-auth-token- 用于基于令牌的身份验证
在app/adapters/application.js:
import DS from 'ember-data';
import DataAdapterMixin from 'ember-simple-auth/mixins/data-adapter-mixin'; // Authenticating data from the API server
import Ember from 'ember';
import ENV from '../config/environment';
export default DS.JSONAPIAdapter.extend(DataAdapterMixin,{
authManager: Ember.inject.service('session'),
host: ENV.apihost, // location of the API server
namespace: ENV.apinamespace, // Namespace of API server ie: 'api/v1'
authorizer: 'authorizer:token', // Authorizer to use for authentication
ajax: function(url, method, hash) {
hash = hash || {}; // hash may be undefined
hash.crossDomain = true; // Needed for CORS
return this._super(url, method, hash);
}
});
Run Code Online (Sandbox Code Playgroud)
在config/environment.js:
ENV.host = 'http://localhost:4000'; /* this assumes the express.js server
is running on port 4000 locally, in a production environment it would point
to https://domainname.com/ */
ENV['ember-simple-auth'] = {
authorizer: 'authorizer:token', //uses ember-simple-auth-token authorizer
crossOriginWhitelist: ['http://localhost:4000'], // for CORS
baseURL: '/',
authenticationRoute: 'login', // Ember.js route that does authentication
routeAfterAuthentication: 'profile', // Ember.js route to transition to after authentication
routeIfAlreadyAuthenticated: 'profile' // Ember.js route to transition to if already authenticated
};
ENV['ember-simple-auth-token'] = {
serverTokenEndpoint: 'http://localhost:4000/auth/token', // Where to get JWT from
identificationField: 'email', // identification field that is sent to Express.js server
passwordField: 'password', // password field sent to Express.js server
tokenPropertyName: 'token', // expected response key from Express.js server
authorizationPrefix: 'Bearer ', // header value prefix
authorizationHeaderName: 'Authorization', // header key
headers: {},
};
ENV['apihost'] = "http://localhost:4000" // Host of the API server passed to `app/adapters/application.js`
ENV['apinamespace'] = ""; // Namespace of API server passed to `app/adapters/application.js`
Run Code Online (Sandbox Code Playgroud)
**设置Express.js服务器**
所需包裹:
express:自解释
body-parser:用于从ember.js站点解析JSON
cors:用于CORS支持
ejwt:在大多数路由上要求JWT到API服务器
passport:用于验证用户
passport-json:用于验证用户
bcrypt:用于散列/腌制用户密码
sequelize:用于数据建模
**设置server.js**
var express = require('express'); // App is built on express framework
var bodyParser = require('body-parser'); // For parsing JSON passed to use through the front end app
var cors = require('cors'); // For CORS support
var ejwt = require('express-jwt');
var passport = require('passport');
// Load Configuration files
var Config = require('./config/environment'),
config = new Config // Load our Environment configuration based on NODE_ENV environmental variable. Default is test.
var corsOptions = {
origin: config.cors
};
var app = express(); // Define our app object using express
app.use(bodyParser.urlencoded({extended: true})); // use x-www-form-urlencoded used for processing submitted forms from the front end app
app.use(bodyParser.json()); // parse json bodies that come in from the front end app
app.use(bodyParser.json({ type: 'application/vnd.api+json' })); // THIS ALLOWS ACCEPTING EMBER DATA BECAUSE JSON API FORMAT
app.use(cors(corsOptions)); // Cross-Origin Resource Sharing support
app.use(passport.initialize()); // initialize passport
app.use(ejwt({ secret: config.secret}).unless({path: ['/auth/token', { url : '/users', methods: ['POST']}]}));
require('./app/routes')(app); // Load our routes file that handles all the API call routing
app.listen(config.port); // Start our server on the configured port. Default is 4000
console.log('listening on port : ' + config.port);
Run Code Online (Sandbox Code Playgroud)
在 config/passport.js
// config/passport.js
// Configure Passport for local logins
// Required Modules
var JsonStrategy = require('passport-json').Strategy;
//
var User = require('../app/models/users'); // load user model
// Function
module.exports = function (passport) {
// serialize the user for the session
passport.serializeUser(function (user, done) {
done(null, user.id);
});
// deserialize the user
passport.deserializeUser(function (id, done) {
User.findById(id).then(function (user) {
done(null, user);
});
});
// LOCAL LOGIN ==========================================================
passport.use('json', new JsonStrategy({
usernameProp : 'email',
passwordProp : 'password',
passReqToCallback : true
},
function (req, email, password, done) {
User.findOne({where : {'email' : email }}).then(function (user) { // check against email
if (!user) {
User.findOne({where : {'displayName' : email}}).then(function(user){ //check against displayName
if (!user) return done(null, false);
else if (User.validatePassword(password,user.password)) return done(null, user);
else return done(null, false);
});
}
else if (User.validatePassword(password,user.password)) return done(null, user);
else return done(null, false);
});
}));
};
Run Code Online (Sandbox Code Playgroud)
示例app/models/users.js用户sequelize模型
// Load required Packages
var Sequelize = require('sequelize');
var bcrypt = require('bcrypt-node')
// Load required helpers
var sequelize = require('../helpers/sequelizeconnect');
var config = new require('../../config/environment'); // Load our Environment configuration based on NODE_ENV environmental variable. Default is test.
// Load other models
// Define model
var Users = sequelize.define('users', {
"email": { type: Sequelize.STRING}, // user email
"password": { type: Sequelize.STRING} // user password
});
// Methods =======================================================
// Hash a password before storing
Users.generateHash = function(password) {
return bcrypt.hashSync(password, bcrypt.genSaltSync(8), null);
};
// Compare a password from the DB
Users.validatePassword = function(password, dbpassword) {
return bcrypt.compareSync(password, dbpassword);
}
module.exports = Users
Run Code Online (Sandbox Code Playgroud)
此时,您的express.js服务器只需要routes.js为您的API服务器所需的路由设置,至少/auth/token为了执行身份验证.Ember.jsJSON API适配器期望成功响应的示例是:
var jsonObject = { // create json response object
"data": {
"type": "users", // ember.js model
"id": 1, // id of the model
"attributes": {
"email" : "example@example.com",
}
}
}
res.status(201).json(jsonObject); // send new data object with 201/OK as a response
Run Code Online (Sandbox Code Playgroud)
设置JSON API服务器以响应删除请求,验证错误等有很多复杂性.
| 归档时间: |
|
| 查看次数: |
720 次 |
| 最近记录: |