diff options
Diffstat (limited to 'src/server')
| -rw-r--r-- | src/server/RouteStore.ts | 29 | ||||
| -rw-r--r-- | src/server/authentication/config/passport.ts | 7 | ||||
| -rw-r--r-- | src/server/authentication/controllers/WorkspacesMenu.css | 3 | ||||
| -rw-r--r-- | src/server/authentication/controllers/WorkspacesMenu.tsx | 96 | ||||
| -rw-r--r-- | src/server/authentication/controllers/user.ts | 107 | ||||
| -rw-r--r-- | src/server/authentication/controllers/user_controller.ts | 263 | ||||
| -rw-r--r-- | src/server/authentication/models/user_model.ts (renamed from src/server/authentication/models/User.ts) | 24 | ||||
| -rw-r--r-- | src/server/database.ts | 6 | ||||
| -rw-r--r-- | src/server/index.ts | 156 |
9 files changed, 537 insertions, 154 deletions
diff --git a/src/server/RouteStore.ts b/src/server/RouteStore.ts new file mode 100644 index 000000000..f12aed85e --- /dev/null +++ b/src/server/RouteStore.ts @@ -0,0 +1,29 @@ +// PREPEND ALL ROUTES WITH FORWARD SLASHES! + +export enum RouteStore { + // GENERAL + root = "/", + home = "/home", + corsProxy = "/corsProxy", + delete = "/delete", + + // UPLOAD AND STATIC FILE SERVING + public = "/public", + upload = "/upload", + images = "/images", + + // USER AND WORKSPACES + addWorkspace = "/addWorkspaceId", + getAllWorkspaces = "/getAllWorkspaceIds", + getActiveWorkspace = "/getActiveWorkspaceId", + setActiveWorkspace = "/setActiveWorkspaceId", + updateCursor = "/updateCursor", + + // AUTHENTICATION + signup = "/signup", + login = "/login", + logout = "/logout", + forgot = "/forgotpassword", + reset = "/reset/:token", + +}
\ No newline at end of file diff --git a/src/server/authentication/config/passport.ts b/src/server/authentication/config/passport.ts index 05f6c3133..b6fe15655 100644 --- a/src/server/authentication/config/passport.ts +++ b/src/server/authentication/config/passport.ts @@ -2,8 +2,9 @@ import * as passport from 'passport' import * as passportLocal from 'passport-local'; import * as mongodb from 'mongodb'; import * as _ from "lodash"; -import { default as User } from '../models/User'; +import { default as User } from '../models/user_model'; import { Request, Response, NextFunction } from "express"; +import { RouteStore } from '../../RouteStore'; const LocalStrategy = passportLocal.Strategy; @@ -18,7 +19,7 @@ passport.deserializeUser<any, any>((id, done) => { }); // AUTHENTICATE JUST WITH EMAIL AND PASSWORD -passport.use(new LocalStrategy({ usernameField: 'email' }, (email, password, done) => { +passport.use(new LocalStrategy({ usernameField: 'email', passReqToCallback: true }, (req, email, password, done) => { User.findOne({ email: email.toLowerCase() }, (error: any, user: any) => { if (error) return done(error); if (!user) return done(undefined, false, { message: "Invalid email or password" }) // invalid email @@ -35,7 +36,7 @@ export let isAuthenticated = (req: Request, res: Response, next: NextFunction) = if (req.isAuthenticated()) { return next(); } - return res.redirect("/login"); + return res.redirect(RouteStore.login); } export let isAuthorized = (req: Request, res: Response, next: NextFunction) => { diff --git a/src/server/authentication/controllers/WorkspacesMenu.css b/src/server/authentication/controllers/WorkspacesMenu.css new file mode 100644 index 000000000..b89039965 --- /dev/null +++ b/src/server/authentication/controllers/WorkspacesMenu.css @@ -0,0 +1,3 @@ +.ids:hover { + color: darkblue; +}
\ No newline at end of file diff --git a/src/server/authentication/controllers/WorkspacesMenu.tsx b/src/server/authentication/controllers/WorkspacesMenu.tsx new file mode 100644 index 000000000..1533b1e62 --- /dev/null +++ b/src/server/authentication/controllers/WorkspacesMenu.tsx @@ -0,0 +1,96 @@ +import * as React from 'react'; +import { observable, action, configure, reaction, computed, ObservableMap, runInAction } from 'mobx'; +import { observer } from "mobx-react"; +import './WorkspacesMenu.css' +import { Document } from '../../../fields/Document'; +import { EditableView } from '../../../client/views/EditableView'; +import { KeyStore } from '../../../fields/KeyStore'; + +export interface WorkspaceMenuProps { + active: Document | undefined; + open: (workspace: Document) => void; + new: (init: boolean) => void; + allWorkspaces: Document[]; +} + +@observer +export class WorkspacesMenu extends React.Component<WorkspaceMenuProps> { + static Instance: WorkspacesMenu; + @observable private workspacesExposed: boolean = false; + + constructor(props: WorkspaceMenuProps) { + super(props); + WorkspacesMenu.Instance = this; + this.addNewWorkspace = this.addNewWorkspace.bind(this); + } + + @action + addNewWorkspace() { + this.props.new(false); + this.toggle(); + } + + @action + toggle() { + this.workspacesExposed = !this.workspacesExposed; + } + + render() { + return ( + <div + style={{ + width: "auto", + maxHeight: '200px', + overflow: 'scroll', + borderRadius: 5, + position: "absolute", + top: 78, + left: this.workspacesExposed ? 11 : -500, + background: "white", + border: "black solid 2px", + transition: "all 1s ease", + zIndex: 15, + padding: 10, + paddingRight: 12, + }}> + <img + src="https://bit.ly/2IBBkxk" + style={{ + width: 20, + height: 20, + marginTop: 3, + marginLeft: 3, + marginBottom: 3, + cursor: "grab" + }} + onClick={this.addNewWorkspace} + /> + {this.props.allWorkspaces.map((s, i) => + <div + key={s.Id} + onContextMenu={(e) => { + e.preventDefault(); + this.props.open(s); + }} + style={{ + marginTop: 10, + color: s === this.props.active ? "red" : "black" + }} + > + <span>{i + 1} - </span> + <EditableView + display={"inline"} + GetValue={() => { return s.Title }} + SetValue={(title: string): boolean => { + s.SetText(KeyStore.Title, title); + return true; + }} + contents={s.Title} + height={20} + /> + </div> + )} + </div> + ); + } +}
\ No newline at end of file diff --git a/src/server/authentication/controllers/user.ts b/src/server/authentication/controllers/user.ts deleted file mode 100644 index f74ff9039..000000000 --- a/src/server/authentication/controllers/user.ts +++ /dev/null @@ -1,107 +0,0 @@ -import { default as User, UserModel, AuthToken } from "../models/User"; -import { Request, Response, NextFunction } from "express"; -import * as passport from "passport"; -import { IVerifyOptions } from "passport-local"; -import "../config/passport"; -import * as request from "express-validator"; -const flash = require("express-flash"); -import * as session from "express-session"; -import * as pug from 'pug'; - -/** - * GET /signup - * Signup page. - */ -export let getSignup = (req: Request, res: Response) => { - if (req.user) { - return res.redirect("/"); - } - res.render("signup.pug", { - title: "Sign Up" - }); -}; - -/** - * POST /signup - * Create a new local account. - */ -export let postSignup = (req: Request, res: Response, next: NextFunction) => { - req.assert("email", "Email is not valid").isEmail(); - req.assert("password", "Password must be at least 4 characters long").len({ min: 4 }); - req.assert("confirmPassword", "Passwords do not match").equals(req.body.password); - req.sanitize("email").normalizeEmail({ gmail_remove_dots: false }); - - const errors = req.validationErrors(); - - if (errors) { - req.flash("errors", "Unable to facilitate sign up. Please try again."); - return res.redirect("/signup"); - } - - const user = new User({ - email: req.body.email, - password: req.body.password - }); - - User.findOne({ email: req.body.email }, (err, existingUser) => { - if (err) { return next(err); } - if (existingUser) { - req.flash("errors", "Account with that email address already exists."); - return res.redirect("/signup"); - } - user.save((err) => { - if (err) { return next(err); } - req.logIn(user, (err) => { - if (err) { - return next(err); - } - res.redirect("/"); - }); - }); - }); -}; - - -/** - * GET /login - * Login page. - */ -export let getLogin = (req: Request, res: Response) => { - if (req.user) { - return res.redirect("/"); - } - res.send("<p>dear lord please render</p>"); - // res.render("account/login", { - // title: "Login" - // }); -}; - -/** - * POST /login - * Sign in using email and password. - */ -export let postLogin = (req: Request, res: Response, next: NextFunction) => { - req.assert("email", "Email is not valid").isEmail(); - req.assert("password", "Password cannot be blank").notEmpty(); - req.sanitize("email").normalizeEmail({ gmail_remove_dots: false }); - - const errors = req.validationErrors(); - - if (errors) { - req.flash("errors", "Unable to login at this time. Please try again."); - return res.redirect("/login"); - } - - passport.authenticate("local", (err: Error, user: UserModel, info: IVerifyOptions) => { - if (err) { return next(err); } - if (!user) { - req.flash("errors", info.message); - return res.redirect("/login"); - } - req.logIn(user, (err) => { - if (err) { return next(err); } - req.flash("success", "Success! You are logged in."); - res.redirect("/"); - }); - })(req, res, next); -};
\ No newline at end of file diff --git a/src/server/authentication/controllers/user_controller.ts b/src/server/authentication/controllers/user_controller.ts new file mode 100644 index 000000000..2cef958e8 --- /dev/null +++ b/src/server/authentication/controllers/user_controller.ts @@ -0,0 +1,263 @@ +import { default as User, DashUserModel, AuthToken } from "../models/user_model"; +import { Request, Response, NextFunction } from "express"; +import * as passport from "passport"; +import { IVerifyOptions } from "passport-local"; +import "../config/passport"; +import * as request from "express-validator"; +const flash = require("express-flash"); +import * as session from "express-session"; +import * as pug from 'pug'; +import * as async from 'async'; +import * as nodemailer from 'nodemailer'; +import c = require("crypto"); +import { RouteStore } from "../../RouteStore"; + +/** + * GET /signup + * Directs user to the signup page + * modeled by signup.pug in views + */ +export let getSignup = (req: Request, res: Response) => { + if (req.user) { + let user = req.user; + return res.redirect(RouteStore.home); + } + res.render("signup.pug", { + title: "Sign Up", + user: req.user, + }); +}; + +/** + * POST /signup + * Create a new local account. + */ +export let postSignup = (req: Request, res: Response, next: NextFunction) => { + req.assert("email", "Email is not valid").isEmail(); + req.assert("password", "Password must be at least 4 characters long").len({ min: 4 }); + req.assert("confirmPassword", "Passwords do not match").equals(req.body.password); + req.sanitize("email").normalizeEmail({ gmail_remove_dots: false }); + + const errors = req.validationErrors(); + + if (errors) { + res.render("signup.pug", { + title: "Sign Up", + user: req.user, + }); + return res.redirect(RouteStore.signup); + } + + const email = req.body.email; + const password = req.body.password; + + const user = new User({ + email, + password, + userDoc: "document here" + }); + + User.findOne({ email }, (err, existingUser) => { + if (err) { return next(err); } + if (existingUser) { + return res.redirect(RouteStore.login); + } + user.save((err) => { + if (err) { return next(err); } + req.logIn(user, (err) => { + if (err) { + return next(err); + } + res.redirect(RouteStore.home); + }); + }); + }); + +}; + + +/** + * GET /login + * Login page. + */ +export let getLogin = (req: Request, res: Response) => { + if (req.user) { + return res.redirect(RouteStore.home); + } + res.render("login.pug", { + title: "Log In", + user: req.user + }); +}; + +/** + * POST /login + * Sign in using email and password. + * On failure, redirect to signup page + */ +export let postLogin = (req: Request, res: Response, next: NextFunction) => { + req.assert("email", "Email is not valid").isEmail(); + req.assert("password", "Password cannot be blank").notEmpty(); + req.sanitize("email").normalizeEmail({ gmail_remove_dots: false }); + + const errors = req.validationErrors(); + + if (errors) { + req.flash("errors", "Unable to login at this time. Please try again."); + return res.redirect(RouteStore.signup); + } + + passport.authenticate("local", (err: Error, user: DashUserModel, info: IVerifyOptions) => { + if (err) { return next(err); } + if (!user) { + return res.redirect(RouteStore.signup); + } + req.logIn(user, (err) => { + if (err) { return next(err); } + res.redirect(RouteStore.home); + }); + })(req, res, next); +}; + +/** + * GET /logout + * Invokes the logout function on the request + * and destroys the user's current session. + */ +export let getLogout = (req: Request, res: Response) => { + req.logout(); + const sess = req.session; + if (sess) { + sess.destroy((err) => { if (err) { console.log(err); } }); + } + res.redirect(RouteStore.login); +} + +export let getForgot = function (req: Request, res: Response) { + res.render("forgot.pug", { + title: "Recover Password", + user: req.user, + }); +} + +export let postForgot = function (req: Request, res: Response, next: NextFunction) { + const email = req.body.email; + async.waterfall([ + function (done: any) { + let token: string; + c.randomBytes(20, function (err: any, buffer: Buffer) { + if (err) { + done(null); + return; + } + done(null, buffer.toString('hex')); + }) + }, + function (token: string, done: any) { + User.findOne({ email }, function (err, user: DashUserModel) { + if (!user) { + // NO ACCOUNT WITH SUBMITTED EMAIL + return res.redirect(RouteStore.forgot); + } + user.passwordResetToken = token; + user.passwordResetExpires = new Date(Date.now() + 3600000); // 1 HOUR + user.save(function (err: any) { + done(null, token, user); + }); + }); + }, + function (token: Uint16Array, user: DashUserModel, done: any) { + const smtpTransport = nodemailer.createTransport({ + service: 'Gmail', + auth: { + user: 'brownptcdash@gmail.com', + pass: 'browngfx1' + } + }); + const mailOptions = { + to: user.email, + from: 'brownptcdash@gmail.com', + subject: 'Dash Password Reset', + text: 'You are receiving this because you (or someone else) have requested the reset of the password for your account.\n\n' + + 'Please click on the following link, or paste this into your browser to complete the process:\n\n' + + 'http://' + req.headers.host + '/reset/' + token + '\n\n' + + 'If you did not request this, please ignore this email and your password will remain unchanged.\n' + }; + smtpTransport.sendMail(mailOptions, function (err) { + // req.flash('info', 'An e-mail has been sent to ' + user.email + ' with further instructions.'); + done(null, err, 'done'); + }); + } + ], function (err) { + if (err) return next(err); + res.redirect(RouteStore.forgot); + }) +} + +export let getReset = function (req: Request, res: Response) { + User.findOne({ passwordResetToken: req.params.token, passwordResetExpires: { $gt: Date.now() } }, function (err, user: DashUserModel) { + if (!user || err) { + return res.redirect(RouteStore.forgot); + } + res.render("reset.pug", { + title: "Reset Password", + user: req.user, + }); + }); +} + +export let postReset = function (req: Request, res: Response) { + async.waterfall([ + function (done: any) { + User.findOne({ passwordResetToken: req.params.token, passwordResetExpires: { $gt: Date.now() } }, function (err, user: DashUserModel) { + if (!user || err) { + return res.redirect('back'); + } + + req.assert("password", "Password must be at least 4 characters long").len({ min: 4 }); + req.assert("confirmPassword", "Passwords do not match").equals(req.body.password); + + if (req.validationErrors()) { + return res.redirect('back'); + } + + user.password = req.body.password; + user.passwordResetToken = undefined; + user.passwordResetExpires = undefined; + + user.save(function (err) { + if (err) { + return res.redirect(RouteStore.login); + } + req.logIn(user, function (err) { + if (err) { + return; + } + }); + done(null, user); + }); + }); + }, + function (user: DashUserModel, done: any) { + const smtpTransport = nodemailer.createTransport({ + service: 'Gmail', + auth: { + user: 'brownptcdash@gmail.com', + pass: 'browngfx1' + } + }); + const mailOptions = { + to: user.email, + from: 'brownptcdash@gmail.com', + subject: 'Your password has been changed', + text: 'Hello,\n\n' + + 'This is a confirmation that the password for your account ' + user.email + ' has just been changed.\n' + }; + smtpTransport.sendMail(mailOptions, function (err) { + done(null, err); + }); + } + ], function (err) { + res.redirect(RouteStore.login); + }); +}
\ No newline at end of file diff --git a/src/server/authentication/models/User.ts b/src/server/authentication/models/user_model.ts index 9752c4260..3d4ed6896 100644 --- a/src/server/authentication/models/User.ts +++ b/src/server/authentication/models/user_model.ts @@ -1,6 +1,5 @@ //@ts-ignore import * as bcrypt from "bcrypt-nodejs"; -import * as crypto from "crypto"; //@ts-ignore import * as mongoose from "mongoose"; var url = 'mongodb://localhost:27017/Dash' @@ -16,12 +15,15 @@ mongoose.connection.on('error', function (error) { mongoose.connection.on('disconnected', function () { console.log('connection closed'); }); -export type UserModel = mongoose.Document & { +export type DashUserModel = mongoose.Document & { email: string, password: string, - passwordResetToken: string, - passwordResetExpires: Date, - tokens: AuthToken[], + passwordResetToken: string | undefined, + passwordResetExpires: Date | undefined, + + allWorkspaceIds: Array<String>, + activeWorkspaceId: String, + activeUsersId: String, profile: { name: string, @@ -47,10 +49,16 @@ const userSchema = new mongoose.Schema({ passwordResetToken: String, passwordResetExpires: Date, + allWorkspaceIds: { + type: Array, + default: [] + }, + activeWorkspaceId: String, + activeUsersId: String, + facebook: String, twitter: String, google: String, - tokens: Array, profile: { name: String, @@ -65,7 +73,7 @@ const userSchema = new mongoose.Schema({ * Password hash middleware. */ userSchema.pre("save", function save(next) { - const user = this as UserModel; + const user = this as DashUserModel; if (!user.isModified("password")) { return next(); } bcrypt.genSalt(10, (err, salt) => { if (err) { return next(err); } @@ -77,7 +85,7 @@ userSchema.pre("save", function save(next) { }); }); -const comparePassword: comparePasswordFunction = function (this: UserModel, candidatePassword, cb) { +const comparePassword: comparePasswordFunction = function (this: DashUserModel, candidatePassword, cb) { bcrypt.compare(candidatePassword, this.password, (err: mongoose.Error, isMatch: boolean) => { cb(err, isMatch); }); diff --git a/src/server/database.ts b/src/server/database.ts index f3c1c9427..164bdd68a 100644 --- a/src/server/database.ts +++ b/src/server/database.ts @@ -19,7 +19,7 @@ export class Database { public update(id: string, value: any, callback: () => void) { if (this.db) { let collection = this.db.collection('documents'); - collection.update({ _id: id }, { $set: value }, { + collection.updateOne({ _id: id }, { $set: value }, { upsert: true }, callback); } @@ -70,6 +70,10 @@ export class Database { let collection = this.db.collection('documents'); let cursor = collection.find({ _id: { "$in": ids } }) cursor.toArray((err, docs) => { + if (err) { + console.log(err.message); + console.log(err.errmsg); + } fn(docs); }) }; diff --git a/src/server/index.ts b/src/server/index.ts index 7f1e95964..d0df95ca3 100644 --- a/src/server/index.ts +++ b/src/server/index.ts @@ -15,54 +15,61 @@ import { FieldId, Field } from '../fields/Field'; import { Database } from './database'; import { ServerUtils } from './ServerUtil'; import { ObjectID } from 'mongodb'; +import * as bcrypt from "bcrypt-nodejs"; import { Document } from '../fields/Document'; import * as io from 'socket.io' import * as passportConfig from './authentication/config/passport'; -import { getLogin, postLogin, getSignup, postSignup } from './authentication/controllers/user'; +import { getLogin, postLogin, getSignup, postSignup, getLogout, postReset, getForgot, postForgot, getReset } from './authentication/controllers/user_controller'; const config = require('../../webpack.config'); const compiler = webpack(config); const port = 1050; // default port to listen const serverPort = 1234; import * as expressValidator from 'express-validator'; import expressFlash = require('express-flash'); +import flash = require('connect-flash'); import * as bodyParser from 'body-parser'; import * as session from 'express-session'; +// import cookieSession = require('cookie-session'); +import * as cookieParser from 'cookie-parser'; import c = require("crypto"); const MongoStore = require('connect-mongo')(session); const mongoose = require('mongoose'); -const bluebird = require('bluebird'); import { performance } from 'perf_hooks' +import User, { DashUserModel } from './authentication/models/user_model'; import * as fs from 'fs'; import * as request from 'request' +import { RouteStore } from './RouteStore'; +import * as MobileDetect from 'mobile-detect'; const download = (url: string, dest: fs.PathLike) => { request.get(url).pipe(fs.createWriteStream(dest)); } const mongoUrl = 'mongodb://localhost:27017/Dash'; -// mongoose.Promise = bluebird; -mongoose.connect(mongoUrl)//.then( -// () => { /** ready to use. The `mongoose.connect()` promise resolves to undefined. */ }, -// ).catch((err: any) => { -// console.log("MongoDB connection error. Please make sure MongoDB is running. " + err); -// process.exit(); -// }); +mongoose.connect(mongoUrl) mongoose.connection.on('connected', function () { console.log("connected"); }) -app.use(bodyParser.json()); -app.use(bodyParser.urlencoded({ extended: true })); -app.use(expressValidator()); -app.use(expressFlash()); -app.use(require('express-session')({ +// SESSION MANAGEMENT AND AUTHENTICATION MIDDLEWARE +// ORDER OF IMPORTS MATTERS + +app.use(cookieParser(`${c.randomBytes(64)}`)); +app.use(session({ secret: `${c.randomBytes(64)}`, resave: true, + cookie: { maxAge: 7 * 24 * 60 * 60 }, saveUninitialized: true, store: new MongoStore({ url: 'mongodb://localhost:27017/Dash' }) })); + +app.use(flash()); +app.use(expressFlash()); +app.use(bodyParser.json()); +app.use(bodyParser.urlencoded({ extended: true })); +app.use(expressValidator()); app.use(passport.initialize()); app.use(passport.session()); app.use((req, res, next) => { @@ -70,13 +77,50 @@ app.use((req, res, next) => { next(); }); -app.get("/signup", getSignup); -app.post("/signup", postSignup); -app.get("/login", getLogin); -app.post("/login", postLogin); +enum Method { + GET, + POST +} + +/** + * Please invoke this function when adding a new route to Dash's server. + * It ensures that any requests leading to or containing user-sensitive information + * does not execute unless Passport authentication detects a user logged in. + * @param method whether or not the request is a GET or a POST + * @param route the forward slash prepended path name (reference and add to RouteStore.ts) + * @param handler the action to invoke, recieving a DashUserModel and the expected request and response + * @param onRejection an optional callback invoked on return if no user is found to be logged in + */ +function addSecureRoute(method: Method, + route: string, + handler: (user: DashUserModel, req: express.Request, res: express.Response) => void, + onRejection: (res: express.Response) => any = (res) => res.redirect(RouteStore.logout)) { + switch (method) { + case Method.GET: + app.get(route, (req, res) => { + const dashUser: DashUserModel = req.user; + if (!dashUser) return onRejection(res); + handler(dashUser, req, res); + }); + break; + case Method.POST: + app.post(route, (req, res) => { + const dashUser: DashUserModel = req.user; + if (!dashUser) return onRejection(res); + handler(dashUser, req, res); + }); + break; + } +} + +// STATIC FILE SERVING + +let FieldStore: ObservableMap<FieldId, Field> = new ObservableMap(); -// IMAGE UPLOADING HANDLER -app.post("/upload", (req, res, err) => { +app.use(express.static(__dirname + RouteStore.public)); +app.use(RouteStore.images, express.static(__dirname + RouteStore.public)) + +addSecureRoute(Method.POST, RouteStore.upload, (user, req, res) => { let form = new formidable.IncomingForm() form.uploadDir = __dirname + "/public/files/" form.keepExtensions = true @@ -91,18 +135,43 @@ app.post("/upload", (req, res, err) => { } res.send(names); }); -}) +}); -app.use(express.static(__dirname + '/public')); -app.use('/images', express.static(__dirname + '/public')) +// anyone attempting to navigate to localhost at this port will +// first have to login +addSecureRoute(Method.GET, RouteStore.root, (user, req, res) => { + res.redirect(RouteStore.home); +}); -let FieldStore: ObservableMap<FieldId, Field> = new ObservableMap(); +// YAY! SHOW THEM THEIR WORKSPACES NOW +addSecureRoute(Method.GET, RouteStore.home, (user, req, res) => { + res.sendFile(path.join(__dirname, '../../deploy/index.html')); +}); -// define a route handler for the default home page -app.get("/", (req, res) => { - res.redirect("/doc/mainDoc"); - // res.sendFile(path.join(__dirname, '../../deploy/index.html')); +addSecureRoute(Method.GET, RouteStore.getActiveWorkspace, (user, req, res) => { + res.send(user.activeWorkspaceId || ""); +}); + +addSecureRoute(Method.GET, RouteStore.getAllWorkspaces, (user, req, res) => { + res.send(JSON.stringify(user.allWorkspaceIds)); +}); + +addSecureRoute(Method.POST, RouteStore.setActiveWorkspace, (user, req, res) => { + user.update({ $set: { activeWorkspaceId: req.body.target } }, (err, raw) => { + res.sendStatus(err ? 500 : 200); + }); +}); + +addSecureRoute(Method.POST, RouteStore.addWorkspace, (user, req, res) => { + user.update({ $push: { allWorkspaceIds: req.body.target } }, (err, raw) => { + res.sendStatus(err ? 500 : 200); + }); }); +// define a route handler for the default home page +// app.get("/", (req, res) => { +// res.redirect("/doc/mainDoc"); +// // res.sendFile(path.join(__dirname, '../../deploy/index.html')); +// }); app.get("/doc/:docId", (req, res) => { res.sendFile(path.join(__dirname, '../../deploy/index.html')); @@ -112,13 +181,34 @@ app.get("/hello", (req, res) => { res.send("<p>Hello</p>"); }) -app.use("/corsProxy", (req, res) => { +// AUTHENTICATION + +// Sign Up +app.get(RouteStore.signup, getSignup); +app.post(RouteStore.signup, postSignup); + +// Log In +app.get(RouteStore.login, getLogin); +app.post(RouteStore.login, postLogin); + +// Log Out +app.get(RouteStore.logout, getLogout); + +// FORGOT PASSWORD EMAIL HANDLING +app.get(RouteStore.forgot, getForgot) +app.post(RouteStore.forgot, postForgot) + +// RESET PASSWORD EMAIL HANDLING +app.get(RouteStore.reset, getReset); +app.post(RouteStore.reset, postReset); + +app.use(RouteStore.corsProxy, (req, res) => { req.pipe(request(req.url.substring(1))).pipe(res); }); -app.get("/delete", (req, res) => { +app.get(RouteStore.delete, (req, res) => { deleteAll(); - res.redirect("/"); + res.redirect(RouteStore.home); }); app.use(wdm(compiler, { @@ -158,10 +248,6 @@ function barReceived(guid: String) { clients[guid.toString()] = new Client(guid.toString()); } -function addDocument(document: Document) { - -} - function getField([id, callback]: [string, (result: any) => void]) { Database.Instance.getDocument(id, (result: any) => { if (result) { |
