Add CSRF protection.
This commit is contained in:
parent
8e47c74b68
commit
0910b16e1e
5 changed files with 68 additions and 7 deletions
|
@ -17,7 +17,7 @@ import debugname from 'debug';
|
|||
const debug = debugname('hostr-web');
|
||||
|
||||
const router = new Router();
|
||||
router.use(errors({template: path.join(__dirname, 'public', '404.html')}));
|
||||
router.use(errors({template: path.join(__dirname, 'public', 'error.html')}));
|
||||
|
||||
let statsdOpts = {prefix: 'hostr-web', host: process.env.STATSD_HOST || 'localhost'};
|
||||
router.use(stats(statsdOpts));
|
||||
|
@ -39,6 +39,8 @@ router.use(function* (next) {
|
|||
yield next;
|
||||
});
|
||||
|
||||
router.use(csrf());
|
||||
|
||||
router.use(views('views', {
|
||||
default: 'ejs'
|
||||
}));
|
||||
|
|
|
@ -21,7 +21,7 @@
|
|||
</div>
|
||||
<div class='row vertical-center'>
|
||||
<div class='col-md-12'>
|
||||
<h2><%=err.status%></h2>
|
||||
<h2>500</h2>
|
||||
<h1>Sorry, It looks like you've hit an unexpected error.</h1>
|
||||
<p class="lead">Refreshing might fix the problem. If not, sit tight! We're on it!</p>
|
||||
</div>
|
||||
|
|
47
web/public/error.html
Normal file
47
web/public/error.html
Normal file
|
@ -0,0 +1,47 @@
|
|||
<!DOCTYPE html>
|
||||
<html style='height:100%;'>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title ng-bind="Hostr">Hostr - File not found</title>
|
||||
<link rel="icon" type="image/png" href="/images/favicon.png">
|
||||
<link href='//fonts.googleapis.com/css?family=Lato:300,400' rel='stylesheet' type='text/css'>
|
||||
<link href='//fonts.googleapis.com/css?family=Open+Sans:400,300,600' rel='stylesheet' type='text/css'>
|
||||
<link href="/styles/app.css" rel="stylesheet" />
|
||||
</head>
|
||||
<body class='error'>
|
||||
<div class='container main'>
|
||||
<div class='row'>
|
||||
<div class='col-md-12'>
|
||||
<div class='error-logo'>
|
||||
<a href='/'><img src='/images/logo-dark-r.png' width='26' height='22' /></a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class='row vertical-center'>
|
||||
<div class='col-md-12'>
|
||||
<h2>{{ status }}</h2>
|
||||
{% if status >= 500 %}
|
||||
<h1>{{ error }}</h1>
|
||||
<p>Refreshing might fix the problem. If not, sit tight! We're on it!</p>
|
||||
{% elseif status === 404 %}
|
||||
<h1>Sorry, it looks like the file you asked for is gone.</h1>
|
||||
<a href='/'>Take Me Home</a>
|
||||
{% else %}
|
||||
<h1>{{ error }}</h1>
|
||||
<a href='/'>Take Me Home</a>
|
||||
{% endif %}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
var _gaq=[['_setAccount','UA-66209-2'],['_setDomainName', 'hostr.co'],['_trackPageview']];
|
||||
(function(d,t){var g=d.createElement(t),s=d.getElementsByTagName(t)[0];
|
||||
g.src='//www.google-analytics.com/ga.js';
|
||||
s.parentNode.insertBefore(g,s)}(document,'script'));
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
|
@ -65,6 +65,7 @@ export function* create() {
|
|||
}
|
||||
|
||||
export function* cancel() {
|
||||
this.assertCSRF();
|
||||
const Users = this.db.Users;
|
||||
const user = yield Users.findOne({_id: this.session.user.id});
|
||||
|
||||
|
|
|
@ -4,8 +4,9 @@ export function* signin() {
|
|||
if (!this.request.body.email) {
|
||||
return yield this.render('signin', {csrf: this.csrf});
|
||||
}
|
||||
this.statsd.incr('auth.attempt', 1);
|
||||
|
||||
this.statsd.incr('auth.attempt', 1);
|
||||
this.assertCSRF(this.request.body);
|
||||
const user = yield authenticate.call(this, this.request.body.email, this.request.body.password);
|
||||
if(!user) {
|
||||
this.statsd.incr('auth.failure', 1);
|
||||
|
@ -25,6 +26,7 @@ export function* signup() {
|
|||
return yield this.render('signup', {csrf: this.csrf});
|
||||
}
|
||||
|
||||
this.assertCSRF(this.request.body);
|
||||
if (this.request.body.email !== this.request.body.confirm_email) {
|
||||
return yield this.render('signup', {error: 'Emails do not match.', csrf: this.csrf});
|
||||
} else if (this.request.body.email && !this.request.body.terms) {
|
||||
|
@ -41,13 +43,19 @@ export function* signup() {
|
|||
return yield this.render('signup', {error: e.message, csrf: this.csrf});
|
||||
}
|
||||
this.statsd.incr('auth.signup', 1);
|
||||
return yield this.render('signup', {message: 'Thanks for signing up, we\'ve sent you an email to activate your account.'});
|
||||
return yield this.render('signup', {message: 'Thanks for signing up, we\'ve sent you an email to activate your account.', csrf: ''});
|
||||
}
|
||||
|
||||
|
||||
export function* forgot(token) {
|
||||
export function* forgot() {
|
||||
const Reset = this.db.Reset;
|
||||
const Users = this.db.Users;
|
||||
if (this.request.body) {
|
||||
return yield this.render('forgot', {token: null, csrf: this.csrf});
|
||||
}
|
||||
const token = this.params.token;
|
||||
|
||||
this.assertCSRF(this.request.body);
|
||||
if (this.request.body.email) {
|
||||
var email = this.request.body.email;
|
||||
yield sendResetToken.call(this, email);
|
||||
|
@ -87,9 +95,12 @@ export function* logout() {
|
|||
}
|
||||
|
||||
|
||||
export function* activate(code) {
|
||||
export function* activate() {
|
||||
const code = this.params.code;
|
||||
if (yield activateUser.call(this, code)) {
|
||||
this.statsd.incr('auth.activation', 1);
|
||||
this.redirect('/');
|
||||
} else {
|
||||
this.throw(400);
|
||||
}
|
||||
this.redirect('/');
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue