import React from 'react';
import { StaticRouter } from 'react-router-dom';
import express from 'express';
import { renderToString } from 'react-dom/server';
import serialize from 'serialize-javascript';
import pathToRegexp from 'path-to-regexp';
import bodyParser from 'body-parser';
import session from 'express-session';
import pgConnect from 'connect-pg-simple';
import App from './frontend/app';
import { pool } from './db';
import { authUser, createUser, getUserById } from './user';
import { queryBuildingAtPoint, getBuildingById, saveBuilding } from './building';
import tileserver from './tileserver';
// create server
const server = express();
// reference packed assets
const assets = require(process.env.RAZZLE_ASSETS_MANIFEST);
// disable header
server.disable('x-powered-by');
// serve static files
server.use(express.static(process.env.RAZZLE_PUBLIC_DIR));
// parse POSTed json body
server.use(bodyParser.json());
// handle user sessions
const pgSession = pgConnect(session);
const sess = {
name: 'cl.session',
store: new pgSession({
pool: pool,
tableName : 'user_sessions'
}),
secret: process.env.APP_COOKIE_SECRET,
saveUninitialized: false,
resave: false,
cookie: { maxAge: 30 * 24 * 60 * 60 * 1000 } // 30 days
};
if (server.get('env') === 'production') {
// trust first proxy
server.set('trust proxy', 1)
// serve secure cookies
sess.cookie.secure = true
}
server.use(session(sess));
// handle HTML routes (server-side rendered React)
server.get('/*.html', frontendRoute);
server.get('/', frontendRoute);
function frontendRoute(req, res) {
const data = {};
const building_id = parseBuildingURL(req.url);
Promise.all([
req.session.user_id? getUserById(req.session.user_id) : undefined,
building_id? getBuildingById(building_id) : undefined
]).then(function(values){
const user = values[0];
const building = values[1];
data.user = user;
data.building = building;
renderHTML(data, req, res)
})
}
function parseBuildingURL(url){
const re = pathToRegexp('/building/:building.html')
const matches = re.exec(url)
if (matches && matches.length === 2) {
return matches[1]
}
return undefined;
}
function renderHTML(data, req, res){
const context = {};
const markup = renderToString(