The MinnowBoard.org website is a Polymer web application hosted using Express in a NodeJS application.
The NodeJS application relies on a forwarding proxy for performing
secure https:// communication. A configuration for nginx
is documented
below.
The website uses NodeJS, npm, and bower:
npm install -g bower
git clone git@github.com:minnowboard-ord/website.git minnow
cd minnow
npm install
bower install
npm start &
xdg-open http://localhost:8080/
Bower projects can introduce a large number of dependent web projects, all of which need to be fetched when the website loads. The Polymer project has a utility to vulanize and optimize a website into a reduced set of resources.
To build the optimized version of the site, you need polymer-cli.
Unfortunately, polymer-cli has problems being installed behind a proxy due to a dependency on test-fixture, so if you use a proxy, you might not be able to install the polymer-cli project:
npm install -g polymer-cli
polymer build index.html
Running polymer build
will create a build
directory with a version
of the website with all HTML and CSS dependencies in a single file.
At this point, there are two manual changes that must be made:
The first is needed because if we provide <base href="https://github.com/MinnowBoard-org/website/blob/master/">
in the
index.html, polymer build will be unable to find the files it needs
to parse.
The second is needed due to polymer build's app-shell logic, which does not work well if you aren't using an app-shell. You can perform both of the above via:
touch build/bundled/shared-bundle.html
sed -i -e "s,<script>'base href=\"/\"';</script>,<base href=\"/\">,g" \
build/bundled/index.html
To host the website out of the build/bundled/
directory, provide the
BASE
environment variable to the npm start
command:
BASE=build/bundled/ npm start &
xdg-open http://localhost:8080
The sync
script performs a site upgrade by building the lastest
version and then renaming the build
directory to
${branch}-${shortSha}
, then setting a symlink from live
to that new
directory. BASE is therefore set to point to live/
on the staging
and production systems.
If you navigate to the /help page of the website, it provides a web form that allows users to submit a question directly to the MinnowBoard support team.
In the NodeJS application, the /help functionality is implemented in
routes/help.js
.
In addition to having an email sent whenever a user submits a help request via /help, the messages are written to the messages.log file.
The website runs on two servers, using Webhooks for continuous integration and deployment.
NOTE: To ensure only trusted updates are received from GitHub, Webhooks must
be configured with a Secret. The Secret is used to create a payload signature,
which is then sent in the X-Hub-Signature header from GitHub. routes/git-sync.js
takes the GITHUB_SECRET from the environment and uses that as the signature.
The staging server, stg.minnowboard.org is typically running the master
version of the GIT project hosted on https://github.com/minnowboard-org/website.
It is configured to automatically pull down the latest code any time there is an update to the GIT master branch via a Webhook configured on the GitHub project.
The Webhook invokes the sync
script which performs the polymer build
, performs
the two manual fixups described previously, as well as npm and bower updates.
Because polymer build
can take a long time to complete, the GitHub webhook
may timeout, which means the reporting console on the server will indicate
webhook failures. Check the update.log to see if the update completed.
The production server, minnowboard.org, is manually updated by merging from
master
into the production
branch.
When a version of the staging server is ready to be moved to production, it
can be moved to production
using the GitHub web front-end. The server will
then automatically upgrade via the same Webhook infrastructure that
stg.minnowboard.org uses.
For instructions for developing using Linux, see INSTALL-LINUX.
For instructions for developing using Windows, see INSTALL-WINDOWS.
There is a webhook configured for the minnowboard-org/website.git GitHub project that triggers a the site to automatically update from GitHub.
When deployed to the live server, edit links ("View content page on GitHub") are disabled by default. To simplify editing of the site content, you can enable edit mode and make those links visible by affixing the "edit=on" query parameter to the site URL. For example:
https://minnowboard.org/?edit=on
This will populate the page with the href links to the specific content pages managed on GitHub.
JSBeautify is used for the HTML, CSS, and Javascript files created for this project. For external projects pulled in as dependencies, no style linting is performed.
JSBeautify is configured to use 2-space tabs and to put a space between an anonymous function and the parenthesis. In general, the Google Javascript style guide[1] should be followed.
Creating a new top level page is pretty quick. Let's say you want a new page
called super-fancy
that can be accessed via https://minnowboard.org/super-fancy.
cd minnow # Or whatever directory you cloned the website into
mkdir pages/super-fancy
We will use the generic markdown page loader. It users two markdown files. One
for the left-navigation panel and one for the main panel. These files are loaded
from the pages/super-fancy
directory and are named super-fancy-intro.md
and
super-fancy.md
.
index.html
Add the following chunk of HTML (changing super-fancy
to your page name) in
the <iron-pages>
. You can look for the comment string <!-- pages are listed here -->
.
<template is="dom-if" id="super-fancy-template" if="[[showPage('super-fancy', tab)]]">
<generic-page id='super-fancy' edit="{{edit}}"
on-page-has-menu-changed='onPageHasMenuChanged'
layout="[[layoutClass]]"
route="{{subRoute}}"></generic-page>
</template>
NOTE: In the above, there are three instances of super-fancy
you need to change.
If you want open graph tags for the new page, edit meta.json
and add a section
describing the page (see the section Meta-Tag Injection for
information on those tags.)
And that's it. You can now load the page. Once you've tested it, you're ready to add your page to git, commit, and push to GitHub:
git branch add-super-fancy
git checkout add-super-fancy
git add pages/super-fancy/*
git commit -s -a -m "Added 'super-fancy' page"
git push origin add-super-fancy:add-super-fancy
Modify the file meta.json
to provide a list of patterns and corresponding
meta-tags to inject into the single-page-app returned with the URL.
The first pattern matched is the first set of tags returned. To test a pattern, use the Express Route Tester.
The markdown content is interpreted on the client through the markdown-it javascript parser. While it supports the commonmark markdown language, it includes some extensions as documented at https://markdown-it.github.io/
Embedded html tags are not enabled.
Polymer Build is used to create the "build" version of the site that is hosted on minnowboard.org. Prior to pushing to staging, you need to run the following:
polymer build index.html
git commit -s -a -m 'Polymer Build regeneration'
You can use the pm2 process manager to manage the website instance.
Install PM2 if you don't have it already:
sudo npm install -g pm2
Edit pm2.json
so that cwd
matches the directory you will run the server
from. For example, if you cloned it into /var/repos/minnowboard.org, change
cwd to "/var/repos/minnowboard.org"
:
"cwd": "/var/respo/minnowboard.org"
If you want to put log files somewhere other than /var/log/www, change the following entries as well:
"error_file": "/var/log/www/minnowboard.org.err",
"out_file": "/var/log/www/minnowboard.org.log",
NOTE: The user you run the application as needs to have write
permission to /var/log/www
:
sudo mkdir -p /var/log/www
sudo chown $(whoami): /var/log/www