Skip to content

rdmontgomery/who-are-my-reps

Repository files navigation

Who Are My Reps

A single-page web app where users enter their address to discover their federal and state elected representatives, complete with contact information, photos, and party affiliation.

Features

  • Address Search: Enter your address to find representatives
  • Comprehensive Data: Pulls from both 5 Calls API and Open States API
  • Rich Contact Information: Phone, email, website, and social media links
  • Responsive Design: Works on mobile, tablet, and desktop
  • Real-time Feedback: Loading states and error handling

Tech Stack

  • Runtime: Node.js 18+
  • Framework: Next.js 14+ with App Router
  • Language: TypeScript (strict mode)
  • Styling: Tailwind CSS
  • Deployment: Vercel
  • External APIs:

Setup

Prerequisites

  • Node.js 18 or higher
  • npm or yarn

Installation

  1. Clone the repository:
git clone <repository-url>
cd who-are-my-reps
  1. Install dependencies:
npm install
  1. Set up environment variables:
cp .env.local.example .env.local
  1. Edit .env.local and add your Open States API key:
OPEN_STATES_API_KEY=your_api_key_here
FIVE_CALLS_API_URL=https://api.5calls.org/v1

Get your Open States API key at openstates.org/api.

Development

Start the development server:

npm run dev

Open http://localhost:3000 in your browser.

Production Build

Build for production:

npm run build
npm start

Deployment to Vercel

  1. Push your repository to GitHub
  2. Visit vercel.com
  3. Click "New Project" and import your repository
  4. Add environment variables in the Vercel dashboard:
    • OPEN_STATES_API_KEY: Your Open States API key
    • FIVE_CALLS_API_URL: https://api.5calls.org/v1
  5. Deploy

Project Structure

.
├── app/
│   ├── api/
│   │   └── reps/
│   │       └── route.ts          # Main API endpoint
│   ├── layout.tsx                # Root layout
│   ├── page.tsx                  # Home page
│   └── globals.css               # Global styles
├── components/
│   ├── AddressInput.tsx          # Address search input
│   ├── RepCard.tsx               # Individual representative card
│   └── RepList.tsx               # List of representatives
├── lib/
│   ├── types.ts                  # Shared TypeScript types
│   ├── five-calls.ts             # 5 Calls API client
│   ├── open-states.ts            # Open States API client
│   ├── merge.ts                  # Merge and deduplicate logic
│   └── geocode.ts                # Address geocoding
├── package.json
├── tsconfig.json
├── tailwind.config.ts
├── postcss.config.js
└── next.config.js

API Endpoint

GET /api/reps

Fetch representatives for an address.

Query Parameters:

  • address (required): The address to search for

Response:

{
  "representatives": [
    {
      "name": "John Doe",
      "photoUrl": "https://...",
      "party": "Democratic",
      "title": "U.S. Senator",
      "district": "CA",
      "level": "federal",
      "contact": {
        "phone": "(202) 224-3121",
        "email": "john@senate.gov",
        "website": "https://..."
      },
      "socialMedia": {
        "twitter": "johndoe",
        "facebook": "johndoe"
      }
    }
  ],
  "warnings": []
}

Error Handling

  • 400 Bad Request: Missing or invalid address parameter
  • 502 Bad Gateway: Both API sources failed
  • Partial Failures: If one API fails, the other's data is still returned with a warning

Development Notes

  • All components use React Server Components by default
  • Add "use client" only where needed (event handlers, state)
  • No database or state management library (pure React hooks)
  • TypeScript strict mode is enabled
  • All styling uses Tailwind CSS only

Type Checking

Run TypeScript type checking without building:

npx tsc --noEmit

License

ISC

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages