Skip to content

paperlesspaper/integrations

Repository files navigation

paperlesspaper Integrations

This repository contains a Docker-ready collection of paperlesspaper Open Integrations. Each integration is a small HTML/CSS/JS provider that exposes a manifest, a render page, and optionally a settings page or server-side data route.

The structure is based on the official paperlesspaper Open Integration overview. That documentation defines the core contract this repo follows: a public config.json, a deterministic render.html surface for screenshot generation, optional settings.html, and loading markers that let paperlesspaper wait until async content is ready.

Quick Start

Install dependencies and start the local provider:

npm install
npm start

The server listens on http://localhost:3000 by default. Check the health endpoint with:

curl http://localhost:3000/health

How It Works

Integrations live in applications/<slug>/.

File Purpose
config.json Install manifest consumed by paperlesspaper.
render.html Full-screen display surface captured for the ePaper image.
settings.html Optional custom settings UI embedded by paperlesspaper.
api/*.js Optional server-side routes exposed at /<slug>/api/<name>.
languages/*.json Localized labels and descriptions.
assets/* Integration-specific PNG icons and static assets.

The Express server maps every application folder to predictable URLs:

/:slug/             -> applications/:slug/render.html
/:slug/render.html  -> applications/:slug/render.html
/:slug/config.json  -> applications/:slug/config.json
/:slug/api/:name    -> applications/:slug/api/:name.js
/assets/*           -> shared helper assets

Render pages use shared assets from @paperlesspaper/openintegration, copied into public/ during npm install and Docker builds.

API routes accept both GET requests and same-origin JSON POST requests. Use POST for passwords, client secrets, access tokens, and private capability URLs so those values do not appear in query strings or routine URL access logs.

Shared Calendar Integrations

Google Calendar, Churchdesk, Outlook Calendar, Nextcloud Calendar, Apple Calendar, Proton Calendar, Webcal & iCalendar, and CalDAV Calendar use the same reusable calendar renderer from @paperlesspaper/openintegration. Provider adapters only fetch and normalize events; agenda, day, three-day, week, and year layouts, civil date ranges, recurrence handling, timezone display, fitting, and eInk styling remain shared. Individual providers may offer fewer views when their upstream range is limited.

Common settings include view, locale, timeZone, dayRange, maxEvents, highlightToday, highlightScale, and showLocation. Each integration adds only the connection and presentation options required by its datasource.

Integration Datasource and access model
Google Calendar Uses calendar events supplied by the paperlesspaper host and does not collect Google credentials.
Churchdesk Reads a public ChurchDesk rota by URL or UUID; private organization calendars are not supported.
Outlook Calendar Reads one Microsoft 365 work or school mailbox through Microsoft Graph calendarView, using an Entra application's client-credentials flow and admin-consented Calendars.ReadBasic.All.
Nextcloud Calendar Reads one private calendar through CalDAV using the instance URL, username, and a dedicated app password, with optional calendar-name or same-origin DAV-path selection.
Apple Calendar Reads an iCloud calendar's public, read-only webcal:// or HTTPS subscription feed; Apple Account credentials and private CalDAV are not used.
Proton Calendar Reads a public Share with anyone link, which requires a paid Proton plan; Proton credentials and CalDAV are not used.
Webcal & iCalendar Reads a public, capability-link, or HTTP Basic-authenticated webcal:///HTTP(S) iCalendar feed.
CalDAV Calendar Reads one exact calendar collection URL with a date-bounded, read-only CalDAV REPORT using HTTP Basic authentication.

JSON POST keeps connection values out of request URLs, but it is not a secret vault: the trusted renderer and server adapter still receive those values, and explicit request-body logging or browser inspection can expose them. Use a trusted HTTPS deployment, disable request-body logging for these routes, grant read-only access where possible, and revoke or rotate exposed credentials and sharing links.

Available Integrations

The production base URL is:

https://integrations.paperlesspaper.de

For example, the Quote manifest is available at https://integrations.paperlesspaper.de/quote/config.json, and its interactive demo is available at https://integrations.paperlesspaper.de/quote/run.

For local development, use http://localhost:3000/<slug>/config.json.

Icon Integration Demo Manifest URL Description
Airtable run config Shows one or more Airtable tables as compact eInk-friendly data views.
Apple Calendar run config Shows events from a public, read-only iCloud Calendar subscription.
Apple Photos Gallery run config Shows a random or numbered image from a public iCloud shared album.
Astronauts run config Shows the current people in space, grouped by spacecraft or station.
Bible Verses run config Shows a random Bible verse or a curated verse of the day.
Bike Commute Card run config Shows rain window, wind, route status, and air quality for a bike commute.
Bird of the Day run config Shows one deterministic daily bird with clean side-profile artwork and compact Wikipedia-sourced facts.
CalDAV Calendar run config Shows one calendar collection through authenticated, read-only CalDAV requests.
Chore Wheel run config Shows a rotating household chore wheel that assigns chores to members deterministically by day or week.
Churchdesk run config Shows services and rota assignments from a public ChurchDesk rota.
Constellations in the Sky run config Shows a seasonal constellation sky map with highlighted star patterns and labels.
Countdown Card run config Shows a configurable countdown or count-up with days, time, and optional progress.
Country of the Day run config Shows one deterministic daily country with a flag, capital, region, area, languages, currency, and compact map-friendly facts.
Daily Buddhism Wisdom run config Shows a daily Buddhist wisdom quote from Buddha API.
Day Calendar run config Shows the current day with optional demotivational quotes or funny facts from the paperlesspaper DayCalendar app.
Deutsche Bahn Abfahrten run config Shows a compact station-board view of upcoming realtime departures for a Deutsche Bahn station.
Dinosaur of the Day run config Shows one deterministic daily dinosaur with display-friendly silhouette artwork and compact Wikipedia-sourced facts.
Duden Wort des Tages run config Shows Duden's German word of the day with meaning, usage, origin, type, and frequency.
DWD Pollenflug run config Shows current DWD pollen forecasts for a German forecast region.
Finance Snapshot run config Shows a compact market dashboard with commodities, crypto, currencies, energy, indices, ETFs, stocks, and trend markers.
Fish of the Day run config Shows one deterministic daily prehistoric fish with generated CAD-like side-profile artwork and compact Wikipedia-sourced fossil facts.
Formula 1 Races run config Shows the upcoming Formula 1 Grand Prix with circuit details, date, session times, and a track image.
Google Calendar run config Displays Google Calendar events supplied by the paperlesspaper host.
Google Sheet Table run config Shows matching rows from a public Google Sheet as a compact Date, Name, and Group table.
Guest Mode Card run config Shows a guest-ready welcome card with scannable Wi-Fi QR, checkout time, house rules, nearby picks, smart-home hints, and emergency contact.
Human Rights — Article of the Day run config Shows one deterministic daily article from the Universal Declaration of Human Rights in English or German, with optional article pinning.
Immich Photos run config Shows a random, newest, or oldest photo from an Immich server.
Islamic Prayer Times run config Shows location-based Islamic prayer times with calculation methods, next-prayer countdown, optional iqamah timing, and Hijri date.
Jewish Date run config Shows the current Jewish/Hebrew calendar date with Hebrew typography, transliteration, and compact daily details.
Kids Fact Card run config Displays a kid-friendly dinosaur, space, or animal fact with a deterministic daily thinking prompt.
Language Learning run config Shows a deterministic foreign-language word of the day with pronunciation, translation, example, and a small practice prompt.
Losung run config Shows the daily Losung and Lehrtext Bible readings from losungen.de.
Mastodon run config Shows Mastodon timelines, hashtag streams, and profile feeds as compact eInk-friendly social cards.
Memo Medication Times run config Shows ANABOX smart medication intake times with medication colors, date header, last update, and a full-screen reminder during intake windows.
Moon Phase run config Shows the moon phase for a chosen date, with illumination, moon age, hemisphere, and an optional next major phase estimate.
Newsstand run config Shows a fresh newspaper front page from Riley Walz's Papers archive.
Nextcloud Calendar run config Shows events from a private Nextcloud calendar through read-only CalDAV requests.
Nextcloud Photos run config Shows a daily, random, dated, or numbered photo from a private Nextcloud Photos album.
NFL Scoreboard icon NFL Scoreboard run config Shows NFL scores, fixtures, live status, favorite-team highlights, and league leaders from ESPN.
Opening Hours run config Shows current opening status, today's hours, and the weekly schedule for a place.
Outlook Calendar run config Shows one Microsoft 365 work or school calendar through Microsoft Graph.
Proton Calendar run config Shows events from a read-only Proton Calendar sharing link.
Quote run config Shows a deterministic daily quote.
Simple Calendar run config Shows a configurable monthly calendar inspired by the TRMNL Simple Calendar recipe.
Simple Text run config Displays configurable plain text or markdown notes with typography, alignment, and framing controls.
Soccer Standings run config Shows European soccer league standings with favorite-team focus, crest-style markers, compact table rows, and an optional markdown note.
Spacecraft of the Day run config Shows one deterministic daily spacecraft with centered portrait artwork and compact mission facts.
The Onion - Editorial Cartoon run config Shows a recent editorial cartoon from The Onion's Cartoons section.
Todoist run config Shows Todoist tasks for today, the next seven days, a project, or a custom filter.
Tour de France run config Shows the current, next, or selected Tour de France 2026 stage with route details, profile imagery, and best-effort official ranking data.
Train of the Day run config Shows one deterministic daily train with first-car artwork and compact facts, focused mostly on European trains.
Travel Map run config Shows a personal visited map for countries, US states, or German Bundesländer with year-based coloring.
Tree of the Day run config Shows one deterministic daily tree with generated botanical artwork and compact Wikipedia-sourced facts.
Uptime Kuma Monitor run config Shows public Uptime Kuma status pages with monitor states, 24-hour uptime, heartbeat history, incidents, and maintenance windows.
Vocabulary run config Shows a new word each day with pronunciation, meaning, example usage, related words, and a reflection prompt.
Waste Collection Schedule run config Shows upcoming waste collection dates from an ICS/iCal feed or manual recurring schedules.
Weather run config Shows current weather and a three-day forecast from Open-Meteo.
Webcal & iCalendar run config Shows events from a Webcal subscription or an HTTP(S) iCalendar feed URL.
World Cup 2026 run config Shows World Cup 2026 fixtures, latest results, and the favorite-team group table in an eInk-friendly tournament dashboard.
Your Life in Weeks run config Shows a week-by-week lifetime grid from a configurable birth date, with age, progress, and current-week markers.
XKCD run config Shows the latest, random, or offset XKCD comic.

Development

Use the render URL while building an integration:

http://localhost:3000/<slug>/

Use the manifest URL when installing it in paperlesspaper:

http://localhost:3000/<slug>/config.json

Open Integrations should render within 100vw by 100vh, avoid browser-only chrome, and keep layout stable for predictable screenshots. If an integration fetches data, create the loading marker immediately and only mark the page loaded once content is ready:

<div id="website-has-loading-element"></div>
<div id="website-has-loaded">ready</div>

OpenIntegration CLI

This repo installs @paperlesspaper/openintegration from vendor/openintegration, so after npm install the CLI can be run with npx paperlesspaper-openintegration.

Create a starter integration:

npx paperlesspaper-openintegration scaffold ./applications/example --name "Example"

By default the scaffold includes api/data.js. Add --no-api for a static-only integration, or --force to overwrite existing scaffold files. The aliases init and create behave the same as scaffold.

Validate an integration:

npx paperlesspaper-openintegration check ./applications/example/config.json

Use --json when another script needs machine-readable validation output.

Run the local paperlesspaper host simulator:

npx paperlesspaper-openintegration dev ./applications/example/config.json

The preview opens at http://127.0.0.1:4300/__paperless/preview by default. It serves the integration folder, sends the INIT payload, renders manifest settings, supports live reload, and includes local render buttons. Useful options are --host, --port, --settings '{"title":"Demo"}', --language, --orientation, --frame-kind, --color, and --no-watch.

Render a PNG through local Chrome/Puppeteer and the production-like epdoptimize path:

npx paperlesspaper-openintegration render ./applications/example/config.json --viewport 800x480 --output /tmp/example-landscape.png
npx paperlesspaper-openintegration render ./applications/example/config.json --viewport 480x800 --output /tmp/example-portrait.png

render defaults to an 800x480 viewport and writes to render-output/<integration-name>-<viewport>.png when --output is omitted. Add --raw to write the unoptimized Puppeteer screenshot, or --epd-output device / --epd-output both to write device-palette output instead of, or alongside, the default dithered PNG. If Chrome is not in the default location, pass --chrome-bin <path> or set CHROME_BIN / PUPPETEER_EXECUTABLE_PATH.

Recommended loop for a new or changed integration:

npx paperlesspaper-openintegration check ./applications/example/config.json
npx paperlesspaper-openintegration render ./applications/example/config.json --viewport 800x480 --output /tmp/example-landscape.png
npx paperlesspaper-openintegration render ./applications/example/config.json --viewport 480x800 --output /tmp/example-portrait.png
npx paperlesspaper-openintegration dev ./applications/example/config.json

Screenshots

Regenerate local variant screenshots and update configVariants in application manifests:

npm run screenshots

Useful filters while iterating:

npm run screenshots -- --config-only
npm run screenshots -- --app weather --resolution 800x480

Generated screenshots are ignored by git under output/ and applications/*/screenshots/.

Docker

Build and run the container directly:

npm run docker:build
npm run docker:run

Or use Docker Compose:

docker compose up --build

Hosting

When hosting this provider for real devices, expose it over HTTPS and make sure paperlesspaper can fetch each integration manifest from the browser. The public install URL on the production deployment looks like:

https://integrations.paperlesspaper.de/<slug>/config.json

Some integrations call upstream APIs from api/data.js. Keep credentials in environment variables or user-provided settings, never in committed files or screenshot variants. Prefer same-origin JSON POST for user-provided secrets and capability links, use HTTPS, and avoid request-body logging. .env, node_modules, generated output, and local workspace files are intentionally ignored.

Adding An Integration

  1. Create applications/<slug>/.
  2. Add a config.json manifest with name, version, description, renderPage, icon, and any settings schema.
  3. Add a square transparent PNG icon at assets/icon.png and reference it as "./assets/icon.png".
  4. Add render.html and make it deterministic at the target viewport size.
  5. Add settings.html only when the built-in schema fields are not enough.
  6. Add api/data.js only when data should be fetched server-side.
  7. Run npm run screenshots -- --app <slug> to refresh variants.

Use the smallest provider that works: plain manifest settings first, a custom settings page when the user experience needs it, and server routes only when browser-side rendering cannot call the upstream service directly.

About

paperlesspaper base integrations (e.g. the ones we maintain)

Topics

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages