You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
FloCafe is installed by café and retail owners who don't have GitHub
accounts. The Help menu links to GitHub Issues, which they won't open.
Real users hit real bugs, decide a GitHub account isn't worth creating
for a one-off report, and the report is lost. The fix is an in-app
feedback flow that works for every FloCafe user without any external
account.
Inspiration: bugdrop and Fider
The clearest end-user feedback widget in the open source space is mean-weasel/bugdrop, at
v1.53.0 with the most recent release 3 days ago. MIT, ~36 stars, ranked #6 on Product Hunt on 2026-05-09. One launcher, one modal, one sink.
Submit creates a GitHub issue via a server-side credential. The model
works because it does one thing.
For the second sink, the clearest end-user feedback board is getfider/fider, at v0.36.1 with
the most recent release 3 days ago. MIT, 4.4k stars. Fider gives you
posts, votes, comments, statuses, and a public board out of the box.
It exposes a public REST API at POST /api/v1/posts that takes a title and description, authenticated with a per-user API key
(Authorization: Bearer <key>).
Fider Cloud at *.fider.io is free for the first 250 feedback items
under a fair-use cap. If the board grows past that, we can revisit
self-hosting or another plan.
What the rest of the community does
Project
Last commit
Stars
Lesson
mean-weasel/bugdrop
3 days ago
36
The model. One modal, one sink, GitHub.
getfider/fider
3 days ago
4,400
The board. Posts, votes, comments, public API.
reikjarloekl/SitePing
2 months ago
0
DOM-anchored annotations, hidden below 768px. Wrong for POS tablets.
feedbackmonk
2 months ago
new
30 KB widget with a strict size cap. Inspiring rigor, AGPL-3.0 license rules it out.
usero-feedback/usero
2 months ago
3
Headless SDK with AI clustering. Heavy for our case.
contember/ucho
4 months ago
3
Solid.js widget with screenshot + annotations. Nice shape, but adds annotation tooling.
WarriorSushi/feedbacks.dev-2026
16 days ago
0
Next.js + Supabase + AI. FSL license, not MIT. Avoid.
rayketcham-lab/issue-reporter
4 months ago
0
Browser-only, token in page source. The lesson, not the model.
NoteLace desktop client
active
n/a
"Help us improve" opens mailto: with a Preview diagnostics button. The Preview pattern is good, but mailto: assumes a mail client.
Unmaintained or stale projects are excluded: electron-elements/send-feedback
(no release since 2022), BPS-Consulting/wafir (last push 4 months ago).
The community lands on a server-mediated design every time. The projects
that put a token in the renderer consistently draw spam warnings. The
projects that keep the credential behind a server endpoint with
validation and rate-limiting are the ones people keep using.
Proposed approach
Two sinks, both opt-in for the operator. The operator picks one, or
both, in the existing Settings UI. The flow is online-only in v1: if
the user is offline, the dialog tells them so and refuses to send.
Sink A: GitHub Issues (bugdrop-style)
The Express backend on :3001 creates an issue via a fine-grained PAT
held in GITHUB_FEEDBACK_TOKEN + GITHUB_FEEDBACK_REPO env vars.
Issues go to a dedicated FloCafe Feedback repo and are labeled user-idea / user-praise / user-issue so the maintainer can
filter.
Sink B: Fider (new)
The Express backend on :3001 posts to <fider-base>/api/v1/posts
with Authorization: Bearer <fider-api-key>. The Fider API key is
held in FIDER_FEEDBACK_URL and FIDER_FEEDBACK_API_KEY env vars.
The body shape is:
{
"title": "[FloCafe] <kind>: <first line of message>",
"description": "<message>\n\n---\n\n**App:** FloCafe <version>\n**OS:** <os>\n**Locale:** <locale>\n**Store hash:** <sha256(cut at 12)>\n**Last route:** <route>\n**Sent at:** <iso timestamp>"
}
Cloud Fider at feedback.fider.io works out of the box. Self-hosted
Fider works the same way once the operator points the env var at
their instance. Fider calls each submission a "post"; the title
follows the platform's own convention (a short idea, suggestion, or
bug), so we don't need to translate the category names.
UI surface
Two entry points. Both open the same FeedbackDialog, a Radix Dialog so we get a focus trap, ESC, and role="dialog" for free.
Help → Send feedback (one new menu item in HelpMenu).
Settings → Support → Send feedback (one new card next to the
existing "More Apps" and "About" cards).
The dialog has three category chips (Praise, Issue, Idea), a
single textarea, an optional email field, and a Send button. No
preview disclosure, no screenshot button in v1. The labels are
deliberately short so a cashier can pick one without reading.
Connectivity (online-only in v1)
The dialog checks navigator.onLine on open. If the user is
offline, the Send button is disabled and a one-line message says
"Please connect to the internet to send your feedback." When the
user comes back online, the message disappears and the button
re-enables.
On click, the renderer POSTs to /api/feedback directly through the
existing api client. There is no local queue, no SQLite table, no
drain loop. Offline users get a clear message; online users get a
direct round trip.
If the request fails:
Network error (offline mid-send, DNS failure, timeout) → the
dialog shows "Please connect to the internet to send your
feedback." with a Retry button.
Server error (5xx, no sink configured, sink auth failed) → the
dialog shows "Couldn't send right now. Please try again." with a
Retry button.
Validation error (4xx, missing fields) → the dialog shows the
field-specific error inline.
Server payload
The renderer builds and sends the payload; the backend forwards it
to the configured sink and never enriches client-side fields the
client already knows. The payload shape:
{
kind: 'praise'|'issue'|'idea'
message: string// required, max 2000 chars
email?: string// optional, validated
app_version: string// from app.getVersion()
os: 'win'|'mac'|'linux'
locale: string
store_id_hash: string// SHA-256 of store id, truncated to 12 hex
last_route: string// e.g. "/(dashboard)/settings"}
The server adds the ISO timestamp before forwarding. No order
contents, no customer names, no payment data, no unredacted logs.
Consent
No consent gate. The existing anonymous_data_consent setting stays
for telemetry and is unrelated here. If the user clicked Send, that
is the consent. The dialog shows one line under the email field:
"Your message and basic app info are sent to the configured
destination. We do not include order data or customer names."
Why this shape
One local component, two sinks. The renderer code is the same
regardless of sink. The sink choice is operator config.
Server-mediated. The pattern the community keeps converging on.
No new schema. Feedback never touches the local DB in v1.
We can add an offline queue in v2 if real users complain.
Fider is the better default for end users. GitHub Issues is
where developers live. Fider is where the customer's idea of
"feedback" lives: posts, votes, status updates, public board.
Using "Idea" as the category name matches Fider's own UI, so
what the user sees in the dialog and what they see on the
public board are the same word.
Free to start. The free Fider Cloud tier covers 250 items.
How we handle the cap if we get close is a follow-up question,
not a v1 commitment.
No new service to run. The Express backend on :3001 is
already there. New route, two sink adapters.
What this is not
Not a replacement for GitHub issues for developers and power users.
Not a chat or support tool. No two-way conversation in v1.
Not a replacement for crash reporting. Sentry is a separate
proposal if we ever want it.
Not an offline queue. That is v2 if anyone asks.
Not screenshot tooling. Also v2.
Sketch of the diff
main/services/feedback.ts — validates payload, dispatches to
sinks. No persistence.
main/services/feedback-sink-github.ts — thin Octokit wrapper,
the only file that touches the GitHub PAT.
main/services/feedback-sink-fider.ts — thin fetch wrapper,
the only file that touches the Fider API key.
main/routes/feedback.ts — POST /api/feedback, returns 200 on
success, 502/503 on sink failure, 503 on no sink configured.
frontend/src/components/feedback/FeedbackDialog.tsx — Radix Dialog, three category chips, textarea, email, Send, offline
message, error states.
frontend/src/components/help/HelpMenu.tsx — add the entry.
frontend/src/components/settings/SupportSection.tsx — new card.
Before I touch any code on this, I want to ask which way you'd rather
go on the Fider side.
The plan above proposes Fider Cloud free (250-item cap, Fider team
runs the infra). The alternative is self-hosted Fider via Docker
Compose + Postgres, on your own infrastructure.
If self-host, two open-source tools make the deploy easy: Dokploy (35k stars) and Coolify (59k stars, 280+
one-click services). Either gives you a Heroku-style dashboard for
the Fider container and Postgres without hand-rolling docker-compose.
The trade is "free + someone else's infra" vs "free + you run the
thing". I'd rather hear from both of you before I pick. Do you want
this on your own infra (and if so, would you use Dokploy, Coolify,
or something else), or is the free cloud tier good enough? Is there
a reason I'm missing?
Open questions
One Fider board per FloCafe instance, or one shared feedback.fider.io
board for the whole community? Default plan: shared board, posts
filtered by store_id_hash.
Should the email field ever leave the dialog? Default plan: no,
v1 is one-way. The maintainer replies via the Fider post or the
GitHub issue.
Should we also add an offline queue in v2? Default plan: only if
real users complain, and only after we measure how many POS
installs run on truly offline networks.
Problem
FloCafe is installed by café and retail owners who don't have GitHub
accounts. The Help menu links to GitHub Issues, which they won't open.
Real users hit real bugs, decide a GitHub account isn't worth creating
for a one-off report, and the report is lost. The fix is an in-app
feedback flow that works for every FloCafe user without any external
account.
Inspiration: bugdrop and Fider
The clearest end-user feedback widget in the open source space is
mean-weasel/bugdrop, atv1.53.0 with the most recent release 3 days ago. MIT, ~36 stars, ranked
#6 on Product Hunt on 2026-05-09. One launcher, one modal, one sink.
Submit creates a GitHub issue via a server-side credential. The model
works because it does one thing.
For the second sink, the clearest end-user feedback board is
getfider/fider, at v0.36.1 withthe most recent release 3 days ago. MIT, 4.4k stars. Fider gives you
posts, votes, comments, statuses, and a public board out of the box.
It exposes a public REST API at
POST /api/v1/poststhat takes atitleanddescription, authenticated with a per-user API key(
Authorization: Bearer <key>).Fider Cloud at
*.fider.iois free for the first 250 feedback itemsunder a fair-use cap. If the board grows past that, we can revisit
self-hosting or another plan.
What the rest of the community does
mean-weasel/bugdropgetfider/fiderreikjarloekl/SitePingfeedbackmonkusero-feedback/userocontember/uchoWarriorSushi/feedbacks.dev-2026rayketcham-lab/issue-reporterNoteLacedesktop clientmailto:with a Preview diagnostics button. The Preview pattern is good, butmailto:assumes a mail client.Unmaintained or stale projects are excluded:
electron-elements/send-feedback(no release since 2022),
BPS-Consulting/wafir(last push 4 months ago).The community lands on a server-mediated design every time. The projects
that put a token in the renderer consistently draw spam warnings. The
projects that keep the credential behind a server endpoint with
validation and rate-limiting are the ones people keep using.
Proposed approach
Two sinks, both opt-in for the operator. The operator picks one, or
both, in the existing Settings UI. The flow is online-only in v1: if
the user is offline, the dialog tells them so and refuses to send.
Sink A: GitHub Issues (bugdrop-style)
The Express backend on
:3001creates an issue via a fine-grained PATheld in
GITHUB_FEEDBACK_TOKEN+GITHUB_FEEDBACK_REPOenv vars.Issues go to a dedicated
FloCafe Feedbackrepo and are labeleduser-idea/user-praise/user-issueso the maintainer canfilter.
Sink B: Fider (new)
The Express backend on
:3001posts to<fider-base>/api/v1/postswith
Authorization: Bearer <fider-api-key>. The Fider API key isheld in
FIDER_FEEDBACK_URLandFIDER_FEEDBACK_API_KEYenv vars.The body shape is:
{ "title": "[FloCafe] <kind>: <first line of message>", "description": "<message>\n\n---\n\n**App:** FloCafe <version>\n**OS:** <os>\n**Locale:** <locale>\n**Store hash:** <sha256(cut at 12)>\n**Last route:** <route>\n**Sent at:** <iso timestamp>" }Cloud Fider at
feedback.fider.ioworks out of the box. Self-hostedFider works the same way once the operator points the env var at
their instance. Fider calls each submission a "post"; the title
follows the platform's own convention (a short idea, suggestion, or
bug), so we don't need to translate the category names.
UI surface
Two entry points. Both open the same
FeedbackDialog, a RadixDialogso we get a focus trap, ESC, androle="dialog"for free.Help → Send feedback(one new menu item inHelpMenu).Settings → Support → Send feedback(one new card next to theexisting "More Apps" and "About" cards).
The dialog has three category chips (Praise, Issue, Idea), a
single textarea, an optional email field, and a Send button. No
preview disclosure, no screenshot button in v1. The labels are
deliberately short so a cashier can pick one without reading.
Connectivity (online-only in v1)
The dialog checks
navigator.onLineon open. If the user isoffline, the Send button is disabled and a one-line message says
"Please connect to the internet to send your feedback." When the
user comes back online, the message disappears and the button
re-enables.
On click, the renderer POSTs to
/api/feedbackdirectly through theexisting
apiclient. There is no local queue, no SQLite table, nodrain loop. Offline users get a clear message; online users get a
direct round trip.
If the request fails:
dialog shows "Please connect to the internet to send your
feedback." with a Retry button.
dialog shows "Couldn't send right now. Please try again." with a
Retry button.
field-specific error inline.
Server payload
The renderer builds and sends the payload; the backend forwards it
to the configured sink and never enriches client-side fields the
client already knows. The payload shape:
The server adds the ISO timestamp before forwarding. No order
contents, no customer names, no payment data, no unredacted logs.
Consent
No consent gate. The existing
anonymous_data_consentsetting staysfor telemetry and is unrelated here. If the user clicked Send, that
is the consent. The dialog shows one line under the email field:
"Your message and basic app info are sent to the configured
destination. We do not include order data or customer names."
Why this shape
regardless of sink. The sink choice is operator config.
We can add an offline queue in v2 if real users complain.
where developers live. Fider is where the customer's idea of
"feedback" lives: posts, votes, status updates, public board.
Using "Idea" as the category name matches Fider's own UI, so
what the user sees in the dialog and what they see on the
public board are the same word.
How we handle the cap if we get close is a follow-up question,
not a v1 commitment.
:3001isalready there. New route, two sink adapters.
What this is not
proposal if we ever want it.
Sketch of the diff
main/services/feedback.ts— validates payload, dispatches tosinks. No persistence.
main/services/feedback-sink-github.ts— thin Octokit wrapper,the only file that touches the GitHub PAT.
main/services/feedback-sink-fider.ts— thinfetchwrapper,the only file that touches the Fider API key.
main/routes/feedback.ts—POST /api/feedback, returns 200 onsuccess, 502/503 on sink failure, 503 on no sink configured.
frontend/src/components/feedback/FeedbackDialog.tsx— RadixDialog, three category chips, textarea, email, Send, offlinemessage, error states.
frontend/src/components/help/HelpMenu.tsx— add the entry.frontend/src/components/settings/SupportSection.tsx— new card.frontend/src/lib/api/feedback.ts— typed client.frontend/src/lib/i18n/locales/{en,es}/feedback.json— strings.tests/feedback.test.ts— validation, sink dispatch, offlinepayload, 5xx/4xx handling, no-sink → 503.
Acceptance criteria
Idea from inside the app, online.
the internet, and the Send button is disabled.
the operator wires at least one credential.
[FloCafe]andthe kind, so the maintainer can filter.
logs, store id is hashed.
role="dialog", visible focusring.
npm test,npm run lint,npm run build,npm run build:frontendall pass.Heads up for @khaira777 and @itsbkm
Before I touch any code on this, I want to ask which way you'd rather
go on the Fider side.
The plan above proposes Fider Cloud free (250-item cap, Fider team
runs the infra). The alternative is self-hosted Fider via Docker
Compose + Postgres, on your own infrastructure.
If self-host, two open-source tools make the deploy easy:
Dokploy (35k stars) and
Coolify (59k stars, 280+
one-click services). Either gives you a Heroku-style dashboard for
the Fider container and Postgres without hand-rolling docker-compose.
The trade is "free + someone else's infra" vs "free + you run the
thing". I'd rather hear from both of you before I pick. Do you want
this on your own infra (and if so, would you use Dokploy, Coolify,
or something else), or is the free cloud tier good enough? Is there
a reason I'm missing?
Open questions
feedback.fider.ioboard for the whole community? Default plan: shared board, posts
filtered by
store_id_hash.v1 is one-way. The maintainer replies via the Fider post or the
GitHub issue.
real users complain, and only after we measure how many POS
installs run on truly offline networks.