From f74e8dda1658e8f74cb0bf5d9f7e52732b481c1e Mon Sep 17 00:00:00 2001 From: Wyatt Johnson Date: Thu, 14 Sep 2017 14:27:45 -0600 Subject: [PATCH 1/5] added support for changing the static url --- app.js | 8 +++++++- config.js | 7 +++++++ docs/_docs/02-01-configuration.md | 6 ++++++ routes/admin/index.js | 10 +--------- routes/embed/index.js | 10 +--------- routes/index.js | 31 +++++++++++++++++++------------ routes/static.js | 13 +++++++++++++ url.js | 20 +++++++++++++++----- views/admin.ejs | 28 ++++++++++++++-------------- views/admin/docs.ejs | 2 +- views/article.ejs | 2 +- views/embed/stream.ejs | 2 +- 12 files changed, 86 insertions(+), 53 deletions(-) create mode 100644 routes/static.js diff --git a/app.js b/app.js index 741dac93f..4e74062d5 100644 --- a/app.js +++ b/app.js @@ -5,7 +5,12 @@ const path = require('path'); const helmet = require('helmet'); const compression = require('compression'); const cookieParser = require('cookie-parser'); -const {BASE_URL, BASE_PATH, MOUNT_PATH} = require('./url'); +const { + BASE_URL, + BASE_PATH, + MOUNT_PATH, + STATIC_URL, +} = require('./url'); const routes = require('./routes'); const debug = require('debug')('talk:app'); @@ -55,6 +60,7 @@ app.set('view engine', 'ejs'); app.locals.BASE_URL = BASE_URL; app.locals.BASE_PATH = BASE_PATH; app.locals.MOUNT_PATH = MOUNT_PATH; +app.locals.STATIC_URL = STATIC_URL; debug(`mounting routes on the ${MOUNT_PATH} path`); diff --git a/config.js b/config.js index d7e247ec3..1a54ece5a 100644 --- a/config.js +++ b/config.js @@ -117,6 +117,13 @@ const CONFIG = { // TALK_ROOT_URL and use it to mount the paths on. ROOT_URL_MOUNT_PATH: process.env.TALK_ROOT_URL_MOUNT_PATH === 'TRUE', + // DISABLE_STATIC_SERVER when TRUE will disable the routes used for static + // asset serving. + DISABLE_STATIC_SERVER: process.env.TALK_DISABLE_STATIC_SERVER === 'TRUE', + + // STATIC_URI is the base uri where static files are hosted. + STATIC_URI: process.env.TALK_STATIC_URI || process.env.TALK_ROOT_URL, + // The keepalive timeout (in ms) that should be used to send keep alive // messages through the websocket to keep the socket alive. KEEP_ALIVE: process.env.TALK_KEEP_ALIVE || '30s', diff --git a/docs/_docs/02-01-configuration.md b/docs/_docs/02-01-configuration.md index 6ffb9afc0..021735fb9 100644 --- a/docs/_docs/02-01-configuration.md +++ b/docs/_docs/02-01-configuration.md @@ -90,6 +90,12 @@ These are only used during the webpack build. managing the auth state manually, auth cannot be persisted, for further information refer to the [Persistence Documentation]({{ "/docs/running/persistence/" | absolute_url }})** (Default `${ssl ? 'ws' : 'wss'}://${location.host}${TALK_ROOT_URL_MOUNT_PATH}api/v1/live`) +- `TALK_STATIC_URI` (_optional_) - Used to set the uri where the static assets + should be served from. This is used when you want to upload the static assets + through your build process to a service like Google Cloud Storage or Amazon S3 + and you would then specify the CDN/Storage url. (Default `process.env.TALK_ROOT_URL`) +- `TALK_DISABLE_STATIC_SERVER` (_optional_) - When `TRUE`, it will not mount the + static asset serving routes on the router. (Default `FALSE`) ### Word Filter diff --git a/routes/admin/index.js b/routes/admin/index.js index ab6189e85..b3872d626 100644 --- a/routes/admin/index.js +++ b/routes/admin/index.js @@ -1,9 +1,6 @@ const express = require('express'); const router = express.Router(); -const { - RECAPTCHA_PUBLIC, - WEBSOCKET_LIVE_URI, -} = require('../../config'); +const {data} = require('../static'); // Get /email-confirmation expects a signed JWT in the hash router.get('/confirm-email', (req, res) => { @@ -20,11 +17,6 @@ router.get('/password-reset', (req, res) => { }); router.get('*', (req, res) => { - const data = { - TALK_RECAPTCHA_PUBLIC: RECAPTCHA_PUBLIC, - LIVE_URI: WEBSOCKET_LIVE_URI, - }; - res.render('admin', {data}); }); diff --git a/routes/embed/index.js b/routes/embed/index.js index 256d03b30..c360c1f76 100644 --- a/routes/embed/index.js +++ b/routes/embed/index.js @@ -1,20 +1,12 @@ const express = require('express'); const router = express.Router(); const SettingsService = require('../../services/settings'); -const { - RECAPTCHA_PUBLIC, - WEBSOCKET_LIVE_URI, -} = require('../../config'); +const {data} = require('../static'); router.use('/:embed', async (req, res, next) => { switch (req.params.embed) { case 'stream': { const {customCssUrl} = await SettingsService.retrieve(); - const data = { - TALK_RECAPTCHA_PUBLIC: RECAPTCHA_PUBLIC, - LIVE_URI: WEBSOCKET_LIVE_URI, - }; - return res.render('embed/stream', {customCssUrl, data}); } } diff --git a/routes/index.js b/routes/index.js index 6a8920dc3..23e8d8a47 100644 --- a/routes/index.js +++ b/routes/index.js @@ -11,6 +11,7 @@ const errors = require('../errors'); const {createGraphOptions} = require('../graph'); const accepts = require('accepts'); const apollo = require('graphql-server-express'); +const {DISABLE_STATIC_SERVER} = require('../config'); const router = express.Router(); @@ -39,20 +40,26 @@ if (process.env.NODE_ENV === 'production') { }); } -router.use('/client', express.static(path.join(__dirname, '../dist'))); -router.use('/public', express.static(path.join(__dirname, '../public'))); +if (!DISABLE_STATIC_SERVER) { -/** - * Serves a file based on a relative path. - */ -const serveFile = (filename) => (req, res) => res.sendFile(path.join(__dirname, filename)); + /** + * Serve the directories under public/dist from this router. + */ + router.use('/client', express.static(path.join(__dirname, '../dist'))); + router.use('/public', express.static(path.join(__dirname, '../public'))); -/** - * Serves the embed javascript files. - */ -router.get('/embed.js', serveFile('../dist/embed.js')); -router.get('/embed.js.gz', serveFile('../dist/embed.js.gz')); -router.get('/embed.js.map', serveFile('../dist/embed.js.map')); + /** + * Serves a file based on a relative path. + */ + const serveFile = (filename) => (req, res) => res.sendFile(path.join(__dirname, filename)); + + /** + * Serves the embed javascript files. + */ + router.get('/embed.js', serveFile('../dist/embed.js')); + router.get('/embed.js.gz', serveFile('../dist/embed.js.gz')); + router.get('/embed.js.map', serveFile('../dist/embed.js.map')); +} //============================================================================== // PASSPORT MIDDLEWARE diff --git a/routes/static.js b/routes/static.js new file mode 100644 index 000000000..12bf01282 --- /dev/null +++ b/routes/static.js @@ -0,0 +1,13 @@ +const { + RECAPTCHA_PUBLIC, + WEBSOCKET_LIVE_URI, +} = require('../config'); +const { + STATIC_URL, +} = require('../url'); + +module.exports.data = { + TALK_RECAPTCHA_PUBLIC: RECAPTCHA_PUBLIC, + LIVE_URI: WEBSOCKET_LIVE_URI, + STATIC_URL, +}; diff --git a/url.js b/url.js index 1def7a707..10013ce35 100644 --- a/url.js +++ b/url.js @@ -1,9 +1,15 @@ -const {ROOT_URL, ROOT_URL_MOUNT_PATH} = require('./config'); +const { + ROOT_URL, + ROOT_URL_MOUNT_PATH, + STATIC_URI, +} = require('./config'); const {URL} = require('url'); +const trailingSlash = (url) => url && url.length > 0 && url[url.length - 1] === '/' ? url : `${url}/`; + // Set the BASE_URL as the ROOT_URL, here we derive the root url by ensuring // that it ends in a `/`. -const BASE_URL = ROOT_URL && ROOT_URL.length > 0 && ROOT_URL[ROOT_URL.length - 1] === '/' ? ROOT_URL : `${ROOT_URL}/`; +const BASE_URL = trailingSlash(ROOT_URL); // The BASE_PATH is simply the path component of the BASE_URL. const BASE_PATH = new URL(BASE_URL).pathname; @@ -12,8 +18,12 @@ const BASE_PATH = new URL(BASE_URL).pathname; // This will mount all the application routes onto it. const MOUNT_PATH = ROOT_URL_MOUNT_PATH ? BASE_PATH : '/'; +// The STATIC_URL is the url where static assets should be loaded from. +const STATIC_URL = trailingSlash(STATIC_URI); + module.exports = { - BASE_URL: BASE_URL, - BASE_PATH: BASE_PATH, - MOUNT_PATH: MOUNT_PATH, + BASE_URL, + BASE_PATH, + MOUNT_PATH, + STATIC_URL, }; diff --git a/views/admin.ejs b/views/admin.ejs index 2aa23aa58..70fed054e 100644 --- a/views/admin.ejs +++ b/views/admin.ejs @@ -4,19 +4,19 @@ Talk - Coral Admin - - - - - - - - - - - - - + + + + + + + + + + + + + @@ -42,6 +42,6 @@
- + diff --git a/views/admin/docs.ejs b/views/admin/docs.ejs index d13dff064..ae2fe2dcf 100644 --- a/views/admin/docs.ejs +++ b/views/admin/docs.ejs @@ -28,6 +28,6 @@
- + diff --git a/views/article.ejs b/views/article.ejs index 0f8c75594..0bda3a6e0 100644 --- a/views/article.ejs +++ b/views/article.ejs @@ -24,7 +24,7 @@

<%= body %>

Admin - All Assets

- + From f19b3335373b8994ccef3a2dffdcf3f8415b1609 Mon Sep 17 00:00:00 2001 From: Chi Vinh Le Date: Mon, 18 Sep 2017 18:56:52 +0700 Subject: [PATCH 2/5] Fix some linter warnings --- .eslintrc.json | 11 +++--- .../coral-admin/src/components/CommentBox.css | 4 --- .../coral-admin/src/components/CommentBox.js | 35 ------------------- .../coral-admin/src/components/UserDetail.js | 1 - .../coral-admin/src/components/ui/Header.js | 4 +-- .../src/routes/Community/components/Table.js | 6 ++-- client/talk-plugin-commentbox/CommentBox.js | 1 - 7 files changed, 12 insertions(+), 50 deletions(-) delete mode 100644 client/coral-admin/src/components/CommentBox.css delete mode 100644 client/coral-admin/src/components/CommentBox.js diff --git a/.eslintrc.json b/.eslintrc.json index d7ed3908e..c92a2d7a8 100644 --- a/.eslintrc.json +++ b/.eslintrc.json @@ -24,12 +24,13 @@ "promise/no-promise-in-callback": "warn", "promise/no-callback-in-promise": "warn", - // TODO: Change all these to "error", or remove and use defaults. "react/display-name": "off", - "react/jsx-no-duplicate-props": "warn", - "react/jsx-no-target-blank": "warn", - "react/no-find-dom-node": "warn", - "react/no-unknown-property": "warn", + + // We'll keeping using this, as we'll switch over to Preact and we don't + // need to worry about deprecation. + "react/no-find-dom-node": "off", + + // TODO: Use default after fixing the errors. "react/prop-types": "off", "array-callback-return": "warn", diff --git a/client/coral-admin/src/components/CommentBox.css b/client/coral-admin/src/components/CommentBox.css deleted file mode 100644 index 34c7ca6ef..000000000 --- a/client/coral-admin/src/components/CommentBox.css +++ /dev/null @@ -1,4 +0,0 @@ - -.textareaContainer { - width: 100%; -} diff --git a/client/coral-admin/src/components/CommentBox.js b/client/coral-admin/src/components/CommentBox.js deleted file mode 100644 index ce3438960..000000000 --- a/client/coral-admin/src/components/CommentBox.js +++ /dev/null @@ -1,35 +0,0 @@ - -import React from 'react'; -import styles from './CommentBox.css'; -import {Button} from 'react-mdl'; - -// Renders a comment box for creating a new comment -export default class CommentBox extends React.Component { - constructor (props) { - super(props); - this.state = {name: '', body: ''}; - this.onSubmit = this.onSubmit.bind(this); - } - - onSubmit () { - const {name, body} = this.state; - this.props.onSubmit({name, body}); - this.setState({body: '', name: ''}); - } - - render (props, {name, body}) { - return ( -
-
- - -
-
-