From 89351d7781fd1c460a7569fb68f6c4b11c107e88 Mon Sep 17 00:00:00 2001 From: John McLear Date: Tue, 2 Jun 2026 17:03:35 +0100 Subject: [PATCH 1/8] Add "More from Etherpad" ecosystem section to homepage MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit etherpad.org only linked to the core editor, the blog, the wiki and the plugin directory — there was nowhere pointing visitors at the other official projects the Foundation maintains (desktop/mobile app, CLI, proxy, load-tester, ueberDB, web components, Home Assistant add-on). Add a new "More from Etherpad" card grid between Download and Contribute, plus an "Apps & Tools" entry in the desktop nav and mobile drawer (scroll-point id "ecosystem"). Plugins are intentionally excluded — they keep their dedicated /plugins page, which the section links to. Cards are a responsive 1/2/3-column Tailwind grid that matches the existing section styling and supports light and dark themes. Co-Authored-By: Claude Opus 4.8 (1M context) --- app/page.tsx | 3 + src/Constants.ts | 5 ++ src/components/MobileDrawer.tsx | 6 +- src/pagesToDisplay/EtherpadEcosystem.tsx | 102 +++++++++++++++++++++++ src/pagesToDisplay/Header.tsx | 1 + 5 files changed, 116 insertions(+), 1 deletion(-) create mode 100644 src/pagesToDisplay/EtherpadEcosystem.tsx diff --git a/app/page.tsx b/app/page.tsx index 3b0a0b43..59ccd755 100644 --- a/app/page.tsx +++ b/app/page.tsx @@ -8,6 +8,7 @@ import {AIOnYourTerms} from "../src/pagesToDisplay/AIOnYourTerms.tsx"; import {AddFunctionalities} from "../src/pagesToDisplay/AddFunctionalities.tsx"; import {CustomizeAppearance} from "../src/pagesToDisplay/CustomizeAppearance.tsx"; import {DownloadLatestVersion} from "../src/pagesToDisplay/DownloadLatestVersion.tsx"; +import {EtherpadEcosystem} from "../src/pagesToDisplay/EtherpadEcosystem.tsx"; import {Contribute} from "../src/pagesToDisplay/Contribute.tsx"; import {FontAwesomeIcon} from "@fortawesome/react-fontawesome"; import {faExternalLink} from "@fortawesome/free-solid-svg-icons"; @@ -38,6 +39,8 @@ export default function Page() { + + diff --git a/src/Constants.ts b/src/Constants.ts index 8a54fc75..2a9b99fa 100644 --- a/src/Constants.ts +++ b/src/Constants.ts @@ -18,4 +18,9 @@ export const DOC_PAGE = `/doc/v${CURRENT_VERSION}/index.html` export const GITHUB_HELP = "https://docs.github.com" +// Official companion apps, clients and tools maintained by the Etherpad +// Foundation alongside the core editor. Plugins are intentionally excluded +// here — they live on the dedicated /plugins page. +export const ETHERPAD_ORG = "https://github.com/ether" + export const TRACKING_ID = 'UA-19303815-1' diff --git a/src/components/MobileDrawer.tsx b/src/components/MobileDrawer.tsx index d2a2c784..94d1ce39 100644 --- a/src/components/MobileDrawer.tsx +++ b/src/components/MobileDrawer.tsx @@ -1,6 +1,6 @@ 'use client' import {FontAwesomeIcon} from "@fortawesome/react-fontawesome"; -import {faInfoCircle, faDownload, faWrench, faExternalLink, faContactCard} from '@fortawesome/free-solid-svg-icons' +import {faInfoCircle, faDownload, faWrench, faExternalLink, faContactCard, faCubes} from '@fortawesome/free-solid-svg-icons' import {FC, useEffect} from "react"; import {ThemeToggler} from "./ThemeToggler.tsx"; import {useUIStore} from "../store/store.ts"; @@ -42,6 +42,10 @@ export const MobileDrawer:FC = ({isOpen, setOpen}) => { Download +
navigateToElement('ecosystem')}> + + Apps & Tools +
navigateToElement('contribute')}> Contribute diff --git a/src/pagesToDisplay/EtherpadEcosystem.tsx b/src/pagesToDisplay/EtherpadEcosystem.tsx new file mode 100644 index 00000000..2f6c9a6a --- /dev/null +++ b/src/pagesToDisplay/EtherpadEcosystem.tsx @@ -0,0 +1,102 @@ +import {FontAwesomeIcon} from "@fortawesome/react-fontawesome"; +import type {IconDefinition} from "@fortawesome/fontawesome-svg-core"; +import { + faCubes, + faDesktop, + faTerminal, + faNetworkWired, + faGaugeHigh, + faDatabase, + faCode, + faHouse, +} from "@fortawesome/free-solid-svg-icons"; +import {ETHERPAD_ORG} from "../Constants.ts"; + +type EcosystemProject = { + name: string, + url: string, + icon: IconDefinition, + description: string, +} + +// Curated, user-facing companion projects from the Etherpad Foundation. +// Plugins are deliberately left out — they have their own /plugins page. +const PROJECTS: EcosystemProject[] = [ + { + name: "Desktop & Mobile App", + url: `${ETHERPAD_ORG}/etherpad-desktop`, + icon: faDesktop, + description: "Run Etherpad as a native app on Windows, macOS, Linux, Android and iOS — collaborate without opening a browser.", + }, + { + name: "Command-line Client", + url: `${ETHERPAD_ORG}/etherpad-cli`, + icon: faTerminal, + description: "Create, read and edit pads straight from your terminal. Great for scripting and automating your Etherpad instance.", + }, + { + name: "Socket.IO Proxy", + url: `${ETHERPAD_ORG}/etherpad-proxy`, + icon: faNetworkWired, + description: "A reference proxy for Etherpad's real-time Socket.IO traffic — a starting point for inspecting or routing pad messages.", + }, + { + name: "Load Testing Tool", + url: `${ETHERPAD_ORG}/etherpad-load-test`, + icon: faGaugeHigh, + description: "Simulate many concurrent users hammering a pad so you can size and tune your instance before going live.", + }, + { + name: "ueberDB", + url: `${ETHERPAD_ORG}/ueberDB`, + icon: faDatabase, + description: "The database abstraction layer that powers Etherpad — one API over MySQL, PostgreSQL, Redis, MongoDB, SQLite and more.", + }, + { + name: "Web Components", + url: `${ETHERPAD_ORG}/webcomponents`, + icon: faCode, + description: "Embed a live Etherpad pad anywhere with a simple custom HTML element — drop it into your own site or app.", + }, + { + name: "Home Assistant Add-on", + url: `${ETHERPAD_ORG}/home-assistant-addon-etherpad`, + icon: faHouse, + description: "Self-host Etherpad on your Home Assistant box in a couple of clicks — collaborative notes for your smart home.", + }, +] + +export const EtherpadEcosystem = () => { + return
+

+ + More from Etherpad +

+

+ Etherpad is more than the editor. The Foundation maintains a family of official + apps, clients and tools to help you run, embed and scale Etherpad. Looking for + plugins instead? Browse the plugin directory. +

+
+ {PROJECTS.map((project) => ( + +
+ + + {project.name} + +
+ + {project.description} + +
+ ))} +
+
+} diff --git a/src/pagesToDisplay/Header.tsx b/src/pagesToDisplay/Header.tsx index 93910022..98b9f7b0 100644 --- a/src/pagesToDisplay/Header.tsx +++ b/src/pagesToDisplay/Header.tsx @@ -38,6 +38,7 @@ export const Header = () => {
  • About
  • navigateToElement('download')} title="download">Download
  • +
  • navigateToElement('ecosystem')} title="apps and tools">Apps & Tools
  • navigateToElement('contribute')} title="contribute">Contribute
  • navigateToElement("links")} title="links">Links
  • navigateToElement('contact')} title="contact">Contact
  • From 0c6438dfdd96fd97b1c5f7599a498ab0d0d60503 Mon Sep 17 00:00:00 2001 From: John McLear Date: Tue, 2 Jun 2026 17:46:36 +0100 Subject: [PATCH 2/8] Add Scale Calculator (scale.etherpad.org) to ecosystem section Co-Authored-By: Claude Opus 4.8 (1M context) --- src/pagesToDisplay/EtherpadEcosystem.tsx | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/src/pagesToDisplay/EtherpadEcosystem.tsx b/src/pagesToDisplay/EtherpadEcosystem.tsx index 2f6c9a6a..3a0dc1d7 100644 --- a/src/pagesToDisplay/EtherpadEcosystem.tsx +++ b/src/pagesToDisplay/EtherpadEcosystem.tsx @@ -9,6 +9,7 @@ import { faDatabase, faCode, faHouse, + faCalculator, } from "@fortawesome/free-solid-svg-icons"; import {ETHERPAD_ORG} from "../Constants.ts"; @@ -46,6 +47,12 @@ const PROJECTS: EcosystemProject[] = [ icon: faGaugeHigh, description: "Simulate many concurrent users hammering a pad so you can size and tune your instance before going live.", }, + { + name: "Scale Calculator", + url: "https://scale.etherpad.org", + icon: faCalculator, + description: "Estimate the CPU, memory and number of instances your deployment needs for a target number of concurrent users.", + }, { name: "ueberDB", url: `${ETHERPAD_ORG}/ueberDB`, From 2da0bea372bd690b5575883e216d69ee44735b0e Mon Sep 17 00:00:00 2001 From: John McLear Date: Tue, 2 Jun 2026 17:49:51 +0100 Subject: [PATCH 3/8] Add pad (terminal editor) and Printing Press to ecosystem section Co-Authored-By: Claude Opus 4.8 (1M context) --- src/pagesToDisplay/EtherpadEcosystem.tsx | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/src/pagesToDisplay/EtherpadEcosystem.tsx b/src/pagesToDisplay/EtherpadEcosystem.tsx index 3a0dc1d7..aa0bd378 100644 --- a/src/pagesToDisplay/EtherpadEcosystem.tsx +++ b/src/pagesToDisplay/EtherpadEcosystem.tsx @@ -10,6 +10,8 @@ import { faCode, faHouse, faCalculator, + faKeyboard, + faRobot, } from "@fortawesome/free-solid-svg-icons"; import {ETHERPAD_ORG} from "../Constants.ts"; @@ -35,6 +37,18 @@ const PROJECTS: EcosystemProject[] = [ icon: faTerminal, description: "Create, read and edit pads straight from your terminal. Great for scripting and automating your Etherpad instance.", }, + { + name: "pad — Terminal Editor", + url: `${ETHERPAD_ORG}/pad`, + icon: faKeyboard, + description: "A nano-class terminal text editor. Edit files locally, or join any pad over the network and watch collaborators' edits land live in your terminal.", + }, + { + name: "Printing Press", + url: "https://printingpress.dev", + icon: faRobot, + description: "Agent-native Etherpad tooling — a Go CLI, a Claude Code skill and an MCP server, generated from a spec so AI agents can drive Etherpad.", + }, { name: "Socket.IO Proxy", url: `${ETHERPAD_ORG}/etherpad-proxy`, From 2cb7fb7761452a921671520b92e01056d583fc90 Mon Sep 17 00:00:00 2001 From: John McLear Date: Tue, 2 Jun 2026 17:52:20 +0100 Subject: [PATCH 4/8] Drop Load Testing Tool from ecosystem section Niche post-deployment tool; discoverable from the Scale Calculator instead. Co-Authored-By: Claude Opus 4.8 (1M context) --- src/pagesToDisplay/EtherpadEcosystem.tsx | 7 ------- 1 file changed, 7 deletions(-) diff --git a/src/pagesToDisplay/EtherpadEcosystem.tsx b/src/pagesToDisplay/EtherpadEcosystem.tsx index aa0bd378..5442cfe0 100644 --- a/src/pagesToDisplay/EtherpadEcosystem.tsx +++ b/src/pagesToDisplay/EtherpadEcosystem.tsx @@ -5,7 +5,6 @@ import { faDesktop, faTerminal, faNetworkWired, - faGaugeHigh, faDatabase, faCode, faHouse, @@ -55,12 +54,6 @@ const PROJECTS: EcosystemProject[] = [ icon: faNetworkWired, description: "A reference proxy for Etherpad's real-time Socket.IO traffic — a starting point for inspecting or routing pad messages.", }, - { - name: "Load Testing Tool", - url: `${ETHERPAD_ORG}/etherpad-load-test`, - icon: faGaugeHigh, - description: "Simulate many concurrent users hammering a pad so you can size and tune your instance before going live.", - }, { name: "Scale Calculator", url: "https://scale.etherpad.org", From 932a6cf1c79343d6945eea4be2ea23c0243f8154 Mon Sep 17 00:00:00 2001 From: John McLear Date: Tue, 2 Jun 2026 18:00:32 +0100 Subject: [PATCH 5/8] Clarify pad card: collaboration is two-way, not just watching Co-Authored-By: Claude Opus 4.8 (1M context) --- src/pagesToDisplay/EtherpadEcosystem.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/pagesToDisplay/EtherpadEcosystem.tsx b/src/pagesToDisplay/EtherpadEcosystem.tsx index 5442cfe0..9672421b 100644 --- a/src/pagesToDisplay/EtherpadEcosystem.tsx +++ b/src/pagesToDisplay/EtherpadEcosystem.tsx @@ -40,7 +40,7 @@ const PROJECTS: EcosystemProject[] = [ name: "pad — Terminal Editor", url: `${ETHERPAD_ORG}/pad`, icon: faKeyboard, - description: "A nano-class terminal text editor. Edit files locally, or join any pad over the network and watch collaborators' edits land live in your terminal.", + description: "A nano-class terminal text editor. Edit files locally, or join any pad to collaborate in real time — your edits and everyone else's sync live, right in your terminal.", }, { name: "Printing Press", From c839880dc05cf13b9593577cf9167d811bd87fd4 Mon Sep 17 00:00:00 2001 From: John McLear Date: Tue, 2 Jun 2026 18:03:42 +0100 Subject: [PATCH 6/8] Address Qodo review: accessible nav link + next/link for /plugins - Give the new 'Apps & Tools' nav item (header + mobile drawer) a real href='/#ecosystem' and move navigation into the anchor's onClick so it is keyboard-focusable and activates on Enter (Qodo bug 1, correctness). - Use next/link for the internal /plugins link instead of a plain anchor to keep client-side routing (Qodo bug 2, performance). Co-Authored-By: Claude Opus 4.8 (1M context) --- src/components/MobileDrawer.tsx | 2 +- src/pagesToDisplay/EtherpadEcosystem.tsx | 3 ++- src/pagesToDisplay/Header.tsx | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/src/components/MobileDrawer.tsx b/src/components/MobileDrawer.tsx index 94d1ce39..c8735e08 100644 --- a/src/components/MobileDrawer.tsx +++ b/src/components/MobileDrawer.tsx @@ -44,7 +44,7 @@ export const MobileDrawer:FC = ({isOpen, setOpen}) => {
navigateToElement('contribute')}> diff --git a/src/pagesToDisplay/EtherpadEcosystem.tsx b/src/pagesToDisplay/EtherpadEcosystem.tsx index 9672421b..75efbdca 100644 --- a/src/pagesToDisplay/EtherpadEcosystem.tsx +++ b/src/pagesToDisplay/EtherpadEcosystem.tsx @@ -1,4 +1,5 @@ import {FontAwesomeIcon} from "@fortawesome/react-fontawesome"; +import Link from "next/link"; import type {IconDefinition} from "@fortawesome/fontawesome-svg-core"; import { faCubes, @@ -89,7 +90,7 @@ export const EtherpadEcosystem = () => {

Etherpad is more than the editor. The Foundation maintains a family of official apps, clients and tools to help you run, embed and scale Etherpad. Looking for - plugins instead? Browse the plugin directory. + plugins instead? Browse the plugin directory.

{PROJECTS.map((project) => ( diff --git a/src/pagesToDisplay/Header.tsx b/src/pagesToDisplay/Header.tsx index 98b9f7b0..ea32e9b5 100644 --- a/src/pagesToDisplay/Header.tsx +++ b/src/pagesToDisplay/Header.tsx @@ -38,7 +38,7 @@ export const Header = () => {
  • About
  • navigateToElement('download')} title="download">Download
  • -
  • navigateToElement('ecosystem')} title="apps and tools">Apps & Tools
  • +
  • {e.preventDefault(); navigateToElement('ecosystem')}} title="apps and tools">Apps & Tools
  • navigateToElement('contribute')} title="contribute">Contribute
  • navigateToElement("links")} title="links">Links
  • navigateToElement('contact')} title="contact">Contact
  • From 25bbecd8d5db7fc1a2e2d670206aa110e9d47a4f Mon Sep 17 00:00:00 2001 From: John McLear Date: Tue, 2 Jun 2026 19:36:40 +0100 Subject: [PATCH 7/8] Drop Web Components from ecosystem section Co-Authored-By: Claude Opus 4.8 (1M context) --- src/pagesToDisplay/EtherpadEcosystem.tsx | 7 ------- 1 file changed, 7 deletions(-) diff --git a/src/pagesToDisplay/EtherpadEcosystem.tsx b/src/pagesToDisplay/EtherpadEcosystem.tsx index 75efbdca..0c075857 100644 --- a/src/pagesToDisplay/EtherpadEcosystem.tsx +++ b/src/pagesToDisplay/EtherpadEcosystem.tsx @@ -7,7 +7,6 @@ import { faTerminal, faNetworkWired, faDatabase, - faCode, faHouse, faCalculator, faKeyboard, @@ -67,12 +66,6 @@ const PROJECTS: EcosystemProject[] = [ icon: faDatabase, description: "The database abstraction layer that powers Etherpad — one API over MySQL, PostgreSQL, Redis, MongoDB, SQLite and more.", }, - { - name: "Web Components", - url: `${ETHERPAD_ORG}/webcomponents`, - icon: faCode, - description: "Embed a live Etherpad pad anywhere with a simple custom HTML element — drop it into your own site or app.", - }, { name: "Home Assistant Add-on", url: `${ETHERPAD_ORG}/home-assistant-addon-etherpad`, From 457381a6e3dd80aec8d4aea5d987c8e4b4df714f Mon Sep 17 00:00:00 2001 From: John McLear Date: Tue, 2 Jun 2026 19:43:32 +0100 Subject: [PATCH 8/8] Add Plugins card to ecosystem section Surface the plugin directory as a first-class card (internal next/link to /plugins) rather than only an aside in the intro copy. Reword the intro to fold the plugin ecosystem into the main sentence. Co-Authored-By: Claude Opus 4.8 (1M context) --- src/pagesToDisplay/EtherpadEcosystem.tsx | 65 ++++++++++++++++-------- 1 file changed, 44 insertions(+), 21 deletions(-) diff --git a/src/pagesToDisplay/EtherpadEcosystem.tsx b/src/pagesToDisplay/EtherpadEcosystem.tsx index 0c075857..85687b47 100644 --- a/src/pagesToDisplay/EtherpadEcosystem.tsx +++ b/src/pagesToDisplay/EtherpadEcosystem.tsx @@ -3,6 +3,7 @@ import Link from "next/link"; import type {IconDefinition} from "@fortawesome/fontawesome-svg-core"; import { faCubes, + faPlug, faDesktop, faTerminal, faNetworkWired, @@ -19,11 +20,21 @@ type EcosystemProject = { url: string, icon: IconDefinition, description: string, + // Internal routes (e.g. /plugins) use next/link for client-side + // navigation; everything else opens the external project in a new tab. + internal?: boolean, } -// Curated, user-facing companion projects from the Etherpad Foundation. -// Plugins are deliberately left out — they have their own /plugins page. +// Curated, user-facing companion projects and resources from the Etherpad +// Foundation, surfaced alongside the core editor on the homepage. const PROJECTS: EcosystemProject[] = [ + { + name: "Plugins", + url: "/plugins", + icon: faPlug, + description: "Hundreds of community plugins add features, themes and integrations. Browse the directory and extend your Etherpad however you like.", + internal: true, + }, { name: "Desktop & Mobile App", url: `${ETHERPAD_ORG}/etherpad-desktop`, @@ -74,6 +85,20 @@ const PROJECTS: EcosystemProject[] = [ }, ] +const CARD_CLASS = "group flex flex-col h-full p-5 rounded-lg border border-gray-200 dark:border-gray-600 bg-white dark:bg-gray-700 transition-shadow hover:shadow-md focus:shadow-md no-underline" + +const CardBody = ({project}: {project: EcosystemProject}) => <> +
    + + + {project.name} + +
    + + {project.description} + + + export const EtherpadEcosystem = () => { return

    @@ -82,28 +107,26 @@ export const EtherpadEcosystem = () => {

    Etherpad is more than the editor. The Foundation maintains a family of official - apps, clients and tools to help you run, embed and scale Etherpad. Looking for - plugins instead? Browse the plugin directory. + apps, clients and tools — plus a large plugin ecosystem — to help you extend, run, + embed and scale Etherpad.

    {PROJECTS.map((project) => ( - -
    - - - {project.name} - -
    - - {project.description} - -
    + project.internal ? ( + + + + ) : ( + + + + ) ))}