Static website that aggregates RSS publications from hackerspaces listed on the hackerspaces wiki.
The project fetches the source list from the Spaces with RSS feeds section on:
https://wiki.hackerspaces.org/User%3AJomat#Spaces_with_RSS_feeds
The repository also contains additional already-confirmed valid source rows in:
content/discovered_valid_source_urls.json
It validates candidate feed URLs, parses supported feeds, normalizes the data into local JSON snapshots, and renders a static multi-page site with:
- spaces index
- per-space detail pages
- per-day newspaper pages under
/news/
- Node.js
- npm
Install dependencies:
npm installFetch data and build the site:
npm run buildThis is the simplest local run and is enough to build the site from the main wiki RSS source list.
If you also want to include the checked-in additional valid sources from content/discovered_valid_source_urls.json, run:
npm run build -- --include-discovery-validStart the local HTTP server:
npm startThe local server serves the generated dist/ directory on port 8090 by default.
Open:
http://127.0.0.1:8090
The project is split into three commands:
npm run refreshupdates local data snapshots indata/npm run renderrebuildsdist/from existing local JSONnpm run buildrunsrefreshand thenrendernpm run refresh -- --include-discovery-validornpm run build -- --include-discovery-validalso merge in the checked-in additional valid sources fromcontent/discovered_valid_source_urls.json
Use npm run render when you changed only UI or rendering logic and do not need to refresh network data.
Discovery is a separate flow based on the broader hackerspace website directory.
Main commands:
npm run discover:feeds
npm run discover:valid-sourcesThe clean valid-source artifact written by this flow is:
content/discovered_valid_source_urls.json
It can be merged into refresh or build with:
npm run build -- --include-discovery-valid
npm run refresh -- --include-discovery-validDetailed discovery flow documentation:
This project is intended to be served as static files behind nginx.
The production flow was tested on Ubuntu 24.04.
Typical setup:
- Point your domain to the server with DNS records.
- Configure
nginxto serve a directory from/var/www/.... - Build or render the site so that
dist/contains the current static output. - Copy
dist/into the directory used bynginx. - Reload
nginx.
The repository includes:
This script supports three modes:
- default mode: copies the current
dist/toTARGET_DIRand reloadsnginx rendermode: runsnpm run render, then copiesdist/toTARGET_DIR, then reloadsnginxbuildmode: runsnpm run build, then copiesdist/toTARGET_DIR, then reloadsnginx
It does not run npm install.
Current target directory defaults to:
/var/www/hackerspace.newsYou can change it in the script or override it through the environment:
TARGET_DIR="/var/www/your-site" ./scripts/deploy-site.shTypical manual deployment with existing already-built dist/:
./scripts/deploy-site.shTypical manual deployment after re-rendering from existing local data snapshots:
./scripts/deploy-site.sh renderTypical manual deployment with fresh data refresh and full rebuild:
./scripts/deploy-site.sh buildThe repository also includes scripts for installing and removing a systemd timer that runs deployment every hour:
Install:
./scripts/install-deploy-site-timer.shRemove:
./scripts/uninstall-deploy-site-timer.shBy default, the timer runs once per hour. It executes ./scripts/deploy-site.sh build, refreshes data from the network, rebuilds the static site, copies dist/ to the target directory, and reloads nginx.
The installer creates a systemd service and timer for the current project path and configures the service to run ./scripts/deploy-site.sh build. That means each timer run refreshes data, rebuilds the site, copies dist/ to the target directory, and reloads nginx. The installer also starts the deploy service once immediately to verify that deployment works.
Source of truth:
https://wiki.hackerspaces.org/User%3AJomat#Spaces_with_RSS_feeds
Optional additional source rows:
content/discovered_valid_source_urls.json
Behavioral notes:
- normalized JSON in
data/is the local data layer - rendering reads only the data that actually exists
- missing fields are omitted from the UI
- feed parsing accounts for RSS, Atom, RDF, missing fields, empty feeds, and non-feed URLs
src/refreshDataset.jshandles ingestion and data snapshot generationsrc/renderSite.jsrenders static pages from local JSONsrc/cli/refresh.jsruns refresh onlysrc/cli/render.jsruns render onlysrc/cli/build.jsruns the full pipeline
Run the test suite:
npm test