Skip to content

Meeting polls: vote for Best Table Topics Speaker, Best Speaker, and Best Evaluator (#80) - #143

Draft
claude[bot] wants to merge 1 commit into
devfrom
factory/80-meeting-polls
Draft

claude[bot] wants to merge 1 commit into
devfrom
factory/80-meeting-polls

Conversation

@claude

@claude claude Bot commented Nov 14, 2026

Copy link
Copy Markdown

Closes #80

Plan: .factory/plans/80-meeting-polls.md

Answer the open questions inline on the plan file, then add plan:approved.

🤖 Generated with Claude Code

…eaker, and Best Evaluator

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@claude claude Bot added the plan:review Factory: plan is up; answer its open questions, then add plan:approved label Nov 14, 2026
@claude

claude Bot commented Nov 14, 2026

Copy link
Copy Markdown
Author

plan — The plan ships web-link voting (A) and the native Zoom poll (B) in one PR, built in layers, as the issue requires.

  1. Shared ballot logic in packages/shared/polls.js: the default three-category ballot, candidates auto-filled from this meeting's reports by role, and tie-aware winners.
  2. Worker /api/polls: a Durable Object per poll keeps one vote per device per category, with exact counts at Close. Results can be read and closed only by the poll's owner. A 24 h expiry deletes the poll. A Worker-rendered /vote/<id> page on the www. host takes votes and has no sign-in.
  3. Club poll template: an admin or editor publishes it with PUT /api/club/poll-template, which bumps ver, the same flow as presets. A Pro user without a club gets a personal template, synced through SYNCED_KEYS.
  4. Results: stored under the club meeting in their own key, so archive compaction doesn't drop them.
  5. POLL tab in the Zoom app: the setup, Open (with sendMessageToChat as an optional capability, plus Copy link), live counts, Close & reveal, and an optional winners panel on the Stage.
  6. Native Zoom poll (B): for the host only. zoomSdk.authorize with PKCE runs, then the Worker creates one question per category through Zoom's REST API. It refuses instant meetings and stores no token.

Everything is behind the new flags polls and polls_zoom, both off by default. Risk is high: public vote endpoints, a new DO binding in wrangler.jsonc, and new Zoom scopes plus a Marketplace review for B.

Open questions (defaults in brackets):

  • Q1: Durable Object vs KV for votes [DO]
  • Q2: Zoom app only, web app in a follow-up [yes]
  • Q3: per-IP vote rate limiter [yes, 30/min]
  • Q4: someone must add meeting:write:poll and meeting:read:meeting in the Marketplace and submit for review. Until then B stays dark and its Zoom steps are ⏭ [as stated]
  • Q5: fetch native poll results after the meeting [no, follow-up]
  • Q6: winners on the report PNG and the /r/ page [no, follow-up]
  • Q7: the poll owner is the creating user [yes]
  • Q8 (proposed): a category with zero votes has no winner [yes]

@ShuhaoZQGG

Copy link
Copy Markdown
Contributor

Review answers (Q5, Q6). #80 isn't split, so both are in this PR, not follow-ups.

  • Q5: yes, in this PR. Fetch the native poll's results after the meeting (GET /past_meetings/{id}/polls) and attach them to the meeting's results. The plan has to cover what this adds:
    • the stored refresh token: where it lives, how it's protected, and when it's deleted;
    • the extra read scope, added to Q4's list for the Marketplace review;
    • what triggers the fetch, given Zoom's processing delay after the meeting ends.
  • Q6: yes, in this PR. The report image (packages/shared/reportImage.js) and the shared /r/ page show each category's winners.

Q1–Q4, Q7 and Q8 are still open.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

plan:review Factory: plan is up; answer its open questions, then add plan:approved

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant