Skip to content

Humanity-Unleashed/Ballot-Builder-Prototype

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

273 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Ballot Builder

A Next.js application that helps users make informed voting decisions through personalized policy alignment matching. Users complete a civic values assessment to build their "Civic Blueprint," which is then used to provide personalized ballot recommendations.

Features

  • Authentication: Google OAuth and anonymous guest mode via better-auth
  • Civic Blueprint Assessment: Slider-based questionnaire across 17 policy axes grouped into 5 domains (Economic, Healthcare, Housing, Justice, Climate)
  • Schwartz Values Assessment: Personal values assessment based on the Schwartz theory of basic human values, with booster vignettes for deeper profiling
  • Ballot Explorer: Browse ballot items with personalized recommendations based on your civic profile
  • Vote Tracking: Persistent ballot vote selections stored locally via Zustand
  • Demographic Impact: See how ballot measures affect different demographic groups
  • Fine-Tuning: Adjust your blueprint axes after completing the assessment
  • Archetype Classification: Get classified into one of 8 civic archetypes based on your profile
  • Blueprint Insights: Personalized insights generated from your civic profile
  • Voting Squad: Form a small accountability group with friends and family — members can see binary status signals (registered, prepped, voted) but never see anyone's answers, values, or actual votes. Invites flow through a dedicated /join onboarding.
  • Analytics & Feedback: Vercel Web Analytics + custom event tracking and user feedback collection backed by a Neon Postgres database, with feedback mirrored to Google Sheets

Tech Stack

  • Framework: Next.js 16 (App Router)
  • Language: TypeScript 5.9
  • UI: React 19, Tailwind CSS v4, Framer Motion
  • Auth: better-auth (Google OAuth + anonymous sessions)
  • State Management: Zustand with localStorage persistence
  • Database: Neon Postgres (via Prisma 7 ORM)
  • Analytics: Vercel Web Analytics
  • Testing: Vitest (unit/integration) + Playwright (E2E)
  • CI/CD: GitHub Actions (build, lint, security audit)
  • Icons: Lucide React
  • Deployment: Vercel

Getting Started

Prerequisites

  • Node.js 20+
  • npm

Installation

# Clone the repository
git clone git@github.com:Humanity-Unleashed/Ballot-Builder-Prototype.git
cd Ballot-Builder-Prototype

# Install dependencies
npm install

# Pull environment variables from Vercel (see below)

# Start development server
npm run dev

Open http://localhost:3000 to view the app.

Environment Variables

The project uses Vercel-managed environment variables for database connections and secrets. To pull them to your local machine:

  1. Install the Vercel CLI (if you haven't already):

    npm i -g vercel
  2. Link your local project to the Vercel project (first time only):

    vercel link

    Select the Humanity-Unleashed team and the ballot-builder-prototype project when prompted.

  3. Pull environment variables to a local .env.local file:

    vercel env pull .env.local

This will create a .env.local file with all the required variables including DATABASE_URL and DIRECT_URL for the Neon Postgres database.

Note: Never commit .env.local to git — it contains secrets. See .env.example for a reference of all available variables.

Database

The project uses Neon Postgres as the database (connected via Prisma ORM). It stores analytics events and user feedback.

View the database: Team members with access can browse tables, run queries, and inspect analytics/feedback data via the Neon Console. The direct project link lives in the internal team wiki.

View feedback: Feedback entries are automatically mirrored to a Google Sheet (restricted to humun.org accounts) for easy browsing. The direct sheet link lives in the internal team wiki.

Database commands:

npm run db:generate       # Regenerate Prisma client
npm run db:push           # Push schema changes to the database
npm run db:migrate:dev    # Create and apply a new migration
npm run db:migrate:deploy # Apply pending migrations (production)
npm run db:studio         # Open Prisma Studio (visual DB browser)

Available Scripts

# Development
npm run dev              # Start development server
npm run build            # Build for production
npm run start            # Start production server
npm run lint             # Run ESLint
npm run lint:fix         # Auto-fix lint issues

# Testing
npm run test             # Run unit tests in watch mode
npm run test:run         # Run unit tests once
npm run test:coverage    # Run tests with coverage report
npm run test:e2e         # Run Playwright E2E tests
npm run test:e2e:ui      # Run E2E tests with interactive UI

# Database (see above)
npm run db:generate
npm run db:push
npm run db:migrate:dev
npm run db:studio

Project Structure

src/
├── app/                        # Next.js App Router
│   ├── (app)/                  # Main application routes
│   │   ├── ballot/             # Ballot explorer
│   │   └── blueprint/          # Blueprint assessment & viewer
│   ├── (auth)/                 # Authentication routes
│   │   ├── login/
│   │   └── register/
│   ├── api/                    # API routes (53 endpoints)
│   │   ├── analytics/          # Analytics event tracking
│   │   ├── assessment/         # Assessment session management
│   │   ├── auth/               # better-auth catch-all handler
│   │   ├── ballot/             # Ballot data endpoints
│   │   ├── blueprint/          # Blueprint endpoints
│   │   ├── candidates/         # Candidate information
│   │   ├── civic-axes/         # Civic axes specification & scoring
│   │   ├── contests/           # Contest endpoints
│   │   ├── feedback/           # User feedback collection
│   │   ├── fine-tuning/        # Fine-tuning session management
│   │   ├── measures/           # Ballot measure endpoints
│   │   ├── personas/           # Test persona endpoints
│   │   └── schwartz-values/    # Schwartz values assessment
│   ├── globals.css
│   ├── layout.tsx
│   └── page.tsx
├── components/                 # React components
│   ├── analytics/              # Analytics provider
│   ├── ballot/                 # Ballot browsing & voting
│   ├── blueprint/              # Assessment & blueprint views
│   ├── demographics/           # Demographic impact screens
│   ├── feedback/               # Feedback collection button
│   ├── layout/                 # Layout components (TopNav)
│   ├── schwartz/               # Schwartz assessment & boosters
│   └── ui/                     # Reusable UI primitives
├── context/                    # React Context providers
├── data/                       # Static data files
├── hooks/                      # Custom hooks (analytics, etc.)
├── lib/                        # Client-side utilities & auth config
├── server/                     # Server-side code
│   ├── data/                   # Data sources (ballot, civic axes, etc.)
│   ├── services/               # Business logic & DB services
│   ├── types/                  # Server-side type definitions
│   └── utils/                  # Server utilities
├── services/                   # API client (Axios)
├── stores/                     # Zustand stores (user, schwartz, ballot, etc.)
└── types/                      # TypeScript type definitions
prisma/
├── schema.prisma               # Database schema
└── migrations/                 # Database migrations
e2e/                            # Playwright E2E tests
docs/                           # Project documentation

Key Concepts

Civic Blueprint

A user's political profile consisting of:

  • 5 Domains: Economic, Healthcare, Housing, Justice, Climate
  • 17 Axes: Policy spectrums within each domain — Economic (4: safety net, investment, school choice, tax structure), Healthcare (3), Housing (3), Justice (4: policing, sentencing, firearms, reproductive), Climate (3)
  • Axis Values: 0-10 scale representing stance between two policy poles
  • Confidence Scores: Based on number of assessment items answered

Schwartz Values

Personal values assessment using the Portrait Values Questionnaire:

  • 10 Value Types: Power, Achievement, Hedonism, Stimulation, Self-Direction, Universalism, Benevolence, Tradition, Conformity, Security
  • 4 Higher-Order Dimensions: Self-Enhancement vs Self-Transcendence, Openness vs Conservation
  • Ipsatized Scoring: Scores relative to individual's mean rating
  • Booster Vignettes: Follow-up scenarios for deeper value profiling

Archetypes

Users are classified into one of 8 archetypes based on three meta-dimensions derived from their civic axes:

  • Responsibility Orientation: Community-led ↔ Individual-led
  • Change Tempo: Change-seeking ↔ Stability-seeking
  • Governance Style: Rules & standards ↔ Flexibility & choice

Documentation

See the docs folder for detailed documentation:

License

Private - All rights reserved

Releases

No releases published

Packages

 
 
 

Contributors

Languages