alpha-one
Version:
ideas about recurring tasks in Web- and Backend-Application building
551 lines (503 loc) • 16.9 kB
JavaScript
// Generated by CoffeeScript 1.7.1
(function() {
var A1, BITSNPIECES, OPTIONS, TEACUP, TRM, USERDB, alert, app_info, app_key, badge, debug, help, info, log, name_, rpr, user_db, warn, whisper;
USERDB = require('coffeenode-userdb');
OPTIONS = require('coffeenode-options');
TRM = require('coffeenode-trm');
rpr = TRM.rpr.bind(TRM);
badge = 'α1/templates';
log = TRM.get_logger('plain', badge);
info = TRM.get_logger('info', badge);
whisper = TRM.get_logger('whisper', badge);
alert = TRM.get_logger('alert', badge);
debug = TRM.get_logger('debug', badge);
warn = TRM.get_logger('warn', badge);
help = TRM.get_logger('help', badge);
BITSNPIECES = require('coffeenode-bitsnpieces');
TEACUP = require('coffeenode-teacup');
app_info = OPTIONS.get_app_info();
app_key = app_info['name'];
A1 = require('./main');
user_db = USERDB.new_db();
USERDB.validate_is_running(user_db);
for (name_ in TEACUP) {
eval("" + name_ + " = TEACUP[ " + (rpr(name_)) + " ]");
}
this.layout = function(request, response, content, done) {
var _ref, _ref1;
log(TRM.blue('layout'));
return this[(_ref = (_ref1 = request['A1']) != null ? _ref1['layout'] : void 0) != null ? _ref : 'plain'](request, response, content, done);
};
this.plain = function(request, response, content, done) {
var O, has_session, logged_in, page_style, session, title, user, _ref, _ref1;
log(TRM.blue('plain'));
O = request['A1'];
page_style = (_ref = O['page-style']) != null ? _ref : 'plain';
title = (_ref1 = O['title']) != null ? _ref1 : 'welcome';
session = request['session'];
has_session = session != null;
if (has_session) {
user = session['user'];
logged_in = user != null;
} else {
user = null;
logged_in = false;
}
return render((function(_this) {
return function() {
DOCTYPE(5);
return HTML(function() {
HEAD(function() {
COMMENT('#head-top');
META({
charset: 'utf-8'
});
TITLE(title);
RAW('<!--[if lt IE 9]>');
SCRIPT({
src: '/common/jquery.com/jquery-1.10.2.js'
});
RAW('<![endif]--><!--[if gte IE 9]><!-->');
SCRIPT({
src: '/common/jquery.com/jquery-2.0.3.js'
});
RAW('<!--<![endif]-->');
SCRIPT({
src: '/common/github.com_carhartl_jquery-cookie/jquery.cookie.js'
});
/* https://github.com/ehynds/jquery-notify */
/* http://www.erichynds.com/blog/a-jquery-ui-growl-ubuntu-notification-widget */
SCRIPT({
src: '/common/jquery.com/jquery-ui-1.10.3/ui/jquery.ui.widget.js'
});
SCRIPT({
src: '/common/erichynds.com/jquery-notify/src/jquery.notify.js'
});
LINK({
rel: 'stylesheet',
href: '/common/erichynds.com/jquery-notify/ui.notify.css'
});
RAW("<style>\n .ui-notify-message h1 {\n font-size: 120%;\n font-weight: normal;\n font-style: italic;\n }\n </style>");
COFFEESCRIPT(function() {
var after, notification_options, notify;
after = function(seconds, method) {
return setTimeout(method, seconds * 1000);
};
notification_options = {
sticky: false,
click: function(event, notification) {
return notification.close();
}
};
notify = function(title, text) {
var message;
message = {
title: title,
text: text
};
return ($('#notify-wrap')).notify('create', 'notify-default', message, notification_options);
};
return ($('document')).ready(function() {
var flash_messages, idx, text, _i, _ref2, _ref3;
($('#notify-wrap')).notify({
speed: 250,
expires: 5000
});
if ((flash_messages = $.cookie('flash-messages')) != null) {
flash_messages = JSON.parse(flash_messages);
for (idx = _i = _ref2 = flash_messages.length - 1; _i >= 0; idx = _i += -1) {
_ref3 = flash_messages[idx], title = _ref3[0], text = _ref3[1];
notify(title, text);
}
flash_messages.length = 0;
return $.cookie('flash-messages', '[]');
}
});
});
LINK({
rel: 'shortcut icon',
href: '/public/favicon.ico?v6'
});
return COMMENT('#head-bottom');
});
return BODY("." + page_style, function() {
COMMENT('#body-top');
DIV('#notify-wrap', {
style: 'display: none;'
}, function() {
return DIV('#notify-default', function() {
H1(function() {
return TEXT('\#{title}');
});
return P(function() {
return TEXT('\#{text}');
});
});
});
DIV({
id: 'login-reminder'
}, function() {
if (logged_in) {
return TEXT("you are logged in as " + request['session']['user']);
} else {
return null;
}
});
RAW(content);
if (logged_in) {
DIV(function() {
return A({
href: '/logout'
}, 'log out');
});
} else {
if (request['url'] !== '/login') {
DIV(function() {
return A({
href: '/login'
}, 'log in');
});
}
}
DIV(function() {
return A({
href: '/'
}, 'home');
});
DIV(function() {
return A({
href: '/restricted'
}, 'restricted');
});
DIV(function() {
return A({
href: '/welcome'
}, 'welcome');
});
DIV(function() {
return A({
href: '/goodbye'
}, 'goodbye');
});
DIV(function() {
return A({
href: '/notfound'
}, 'not found');
});
DIV(function() {
return A({
href: '/contact'
}, 'contact');
});
DIV(function() {
return A({
href: '/imprint'
}, 'imprint');
});
DIV(function() {
return A({
href: '/privacy'
}, 'privacy');
});
return COMMENT('#body-bottom');
});
});
};
})(this));
};
this.homepage = function(request, response, next) {
var O;
log(TRM.blue('homepage'));
O = request['A1'];
O['title'] = 'Homepage for Alpha-One';
return render((function(_this) {
return function() {
H1('Home');
return DIV("homepage for alpha-one");
};
})(this));
};
this.welcome = function(request, response, next) {
var O;
log(TRM.blue('welcome'));
O = request['A1'];
O['title'] = 'Welcome!';
return render((function(_this) {
return function() {
H1('Welcome');
return DIV("welcome to alpha-one");
};
})(this));
};
this.goodbye = function(request, response, next) {
var O;
log(TRM.blue('goodbye'));
O = request['A1'];
O['title'] = 'Good-Bye';
return render((function(_this) {
return function() {
H1('Good-Bye');
return DIV("good-bye from alpha-one");
};
})(this));
};
this.not_found = function(request, response) {
var O;
log(TRM.blue('not_found'));
O = request['A1'];
O['title'] = 'Not Found';
A1.HTTP.not_found(request, response);
return render((function(_this) {
return function() {
H1('404');
return DIV("nothing found for " + request['url']);
};
})(this));
};
this.contact = function(request, response) {
var O;
log(TRM.blue('contact'));
O = request['A1'];
O['title'] = 'contact';
return render((function(_this) {
return function() {
H1('Contact');
return DIV("Contact us at info@example.com");
};
})(this));
};
this.imprint = function(request, response) {
var O;
log(TRM.blue('imprint'));
O = request['A1'];
O['title'] = 'imprint';
request['A1']['flash']('Welcome...', '...to the mighty Alpha-One Imprint page!');
request['A1']['flash']('Info', 'We accept pull requests');
return render((function(_this) {
return function() {
H1('Imprint');
return DIV("The maintainers of this site are somewhat responsible for some content.");
};
})(this));
};
this.privacy = function(request, response) {
var O;
log(TRM.blue('privacy'));
O = request['A1'];
O['title'] = 'privacy';
return render((function(_this) {
return function() {
H1('Privacy');
return DIV("Yeah, privacy. Well, we take it seriously.");
};
})(this));
};
/* TAINT these things should probably go into their own module, no? */
this.login_get = function(request, response) {
var O, comes_from, has_session, login_count, session, _ref;
log(TRM.blue('login_get'));
O = request['A1'];
O['title'] = 'Log In or Sign Up';
comes_from = (_ref = request['cookies']) != null ? _ref['comes-from'] : void 0;
session = request['session'];
has_session = session != null;
if (has_session) {
login_count = session['login-count'] += 1;
} else {
login_count = 0;
}
return render((function(_this) {
return function() {
if (comes_from != null) {
request['A1']['flash']('For your information...', "You must log in to visit " + comes_from);
}
if (login_count > 1) {
DIV("attempt to log in: #" + login_count);
}
H1('Log In or Sign Up');
DIV(function() {
return FORM('#login-form', {
method: 'post',
action: '/login'
}, function() {
return FIELDSET(function() {
LEGEND("Log In");
DIV(function() {
return TEXT_INPUT({
label: "Your email or user name:",
name: 'uid-hint',
autofocus: true,
required: true
});
});
DIV(function() {
return PASSWORD({
label: "Your password:"
});
});
return DIV(function() {
return SUBMIT({
label: "submit"
});
});
});
});
});
return DIV(function() {
return FORM('#signup-form', {
method: 'post',
action: '/signup'
}, function() {
return FIELDSET(function() {
LEGEND("Sign Up");
DIV(function() {
return EMAIL({
label: "Your email:",
autocomplete: 'off'
});
});
DIV(function() {
return TEXT_INPUT({
label: "Your user name:",
autocomplete: 'off',
name: 'name',
autofocus: true,
required: true
});
});
DIV(function() {
return PASSWORD({
label: "Your password:",
autocomplete: 'off'
});
});
DIV(function() {
return CONFIRM_PASSWORD({
label: "Your password again:",
autocomplete: 'off'
});
});
return DIV(function() {
return SUBMIT({
label: "submit"
});
});
});
});
});
};
})(this));
};
this.login_post = function(request, response, done) {
var password, uid_hint;
log(TRM.blue('login_post'));
uid_hint = request['body']['uid-hint'];
password = request['body']['password'];
info('©11k', 'query arguments:', request['body']);
USERDB.authenticate_user(user_db, {
name: uid_hint
}, password, (function(_this) {
return function(error, user_known, password_matches) {
/* TAINT code duplication */
var message;
if (error != null) {
if (error['message'] === 'connect ECONNREFUSED') {
alert("\nthe CoffeeNode UserDB specified as \n" + (rpr(user_db)) + "\ncan not be accessed");
} else {
alert(error);
}
return done(new Error(error.stack));
}
log('©34e', TRM.gold(uid_hint), TRM.blue(password), TRM.truth(user_known), TRM.truth(password_matches));
if (user_known && password_matches) {
TRM.dir('©34e', (require('express')).session);
/* TAINT what to do if request.session does not exist? */
return request.session.regenerate(function() {
var message;
request.session.user = uid_hint;
A1.HTTP.back_to(request, response, '/welcome');
request.session['just-logged-in'] = true;
message = "You have been logged in as user " + (rpr(uid_hint));
request['A1']['flash']("Welcome", message);
return done(message);
});
} else {
log(TRM.lime('©15z', response.headerSent));
A1.HTTP.redirect(request, response, '/login');
message = "Your ID " + (rpr(uid_hint)) + " or password did not match; please try again.";
request['A1']['flash']("Login failed", message);
return done(message);
}
};
})(this));
return null;
};
this.signup_post = function(request, response, done) {
var email, entry, message, name, password, password_r;
log(TRM.blue('signup_post'));
email = request['body']['email'];
name = request['body']['name'];
password = request['body']['password'];
password_r = request['body']['password-r'];
if (password !== password_r) {
message = "your passwords do not match";
A1.HTTP.redirect(request, response, '/login');
done(message);
}
/* TAINT check for password strength (maybe only on client) */
/* TAINT check for email plausibility */
/* TAINT check for email uniqueness */
/* TAINT think up a UID generation method */
entry = {
'name': name,
'uid': "" + email + "-" + (1 * new Date()),
'password': password,
'email': email
};
USERDB.create_user(user_db, entry, function(error, result) {
/* TAINT code duplication */
if (error != null) {
if (error['message'] === 'connect ECONNREFUSED') {
alert("\nthe CoffeeNode UserDB specified as \n" + (rpr(user_db)) + "\ncan not be accessed");
} else {
alert(error);
}
return done(new Error(error.stack));
}
/* TAINT what to do if request.session does not exist? */
return request.session.regenerate((function(_this) {
return function() {
request.session.user = entry['uid'];
message = "you have been registered as " + entry['uid'];
request['A1']['flash']("Welcome", message);
A1.HTTP.back_to(request, response, '/welcome-new-user');
return done(message);
};
})(this));
});
return null;
};
this.logout = function(request, response, done) {
log(TRM.blue('restricted'));
request.session.destroy((function(_this) {
return function() {
A1.HTTP.back_to(request, response, '/goodbye');
return done("You have been logged out.");
};
})(this));
return null;
};
this.restricted = function(request, response) {
var O, uid;
log(TRM.blue('restricted'));
O = request['A1'];
O['title'] = 'Restricted Area';
uid = request.session.user;
return render((function(_this) {
return function() {
H1('Restricted Area');
return DIV("This is the Restricted Area");
};
})(this));
};
}).call(this);