# Project export: Farsight.fyi

This document was generated by HackStack to give an AI agent context about a hackathon project. Sections are labeled with their provenance; content marked as truncated was cut to keep this document small.

## Project metadata

- Hackathon: UC Berkeley AI Hackathon 2025
- Tagline: AI-powered layoff risk analysis
- Devpost: https://devpost.com/software/farsight-fyi
- GitHub: https://github.com/Jam-Cai/layoff-radar
- Team: 4 GitHub contributor(s) — larry-pan (16 commits), Brian (11 commits), jam-cai (7 commits), unknown (4 commits)

## Devpost submission (written by the team)

### Inspiration

Mass layoffs always feel like lightning bolts devastating but “out-of-the-blue.” We wanted to give employees, recruiters, and policymakers foresight instead of hindsight. With WARN filings, news rumors, and tiny LLMs all in the open, we realized we could surface an objective layoff-risk score weeks or months before the pink-slips hit. That vision became Farsight.fyi.

### What it does

Farsight.fyi is a hybrid AI-system web application that assesses the potential layoff risk of a company. Users enter a company name, and our system performs a multi-stage analysis in real-time: Data Aggregation: It scours the web for recent news articles and public data related to the company. Data Aggregation: It scours the web for recent news articles and public data related to the company. AI-Powered Feature Extraction: An LLM reads through the unstructured text of the articles to extract key risk factors. AI-Powered Feature Extraction: An LLM reads through the unstructured text of the articles to extract key risk factors. Predictive Modeling: These extracted features are fed into a CatBoost machine learning model, which calculates a quantitative risk score. Predictive Modeling: These extracted features are fed into a CatBoost machine learning model, which calculates a quantitative risk score. Insightful Reporting: The application presents the user with a final risk level, a detailed explanation of the contributing factors, and a summary of the key data points that influenced the score, all delivered through a clean and intuitive user interface. Insightful Reporting: The application presents the user with a final risk level, a detailed explanation of the contributing factors, and a summary of the key data points that influenced the score, all delivered through a clean and intuitive user interface.

### How we built it

Frontend: Built using React and TypeScript, using Vite for local dev, Tailwind for styling and various components from shadcn/ui Backend: Python and FastAPI Real-time Communication: Socket.IO Web Scraping: Beautiful Soup and Selenium AI & Machine Learning: Claude 4 and a CatBoost model Database: Simple SQLite database

### Challenges we ran into

Prompt Engineering: Designing prompts that could consistently and accurately extract specific, structured features from the diverse and noisy text of news articles required extensive iteration and refinement. Managing Asynchronous Tasks: Building a non-blocking, real-time user experience was complex. We had to carefully manage long-running analysis tasks on the backend to prevent timeouts and provide a smooth flow of status updates to the user via Socket.IO. Data Noise Reduction: Sifting through the vast amount of irrelevant information in news articles to isolate the true signals of company health was a significant data processing challenge.

### Accomplishments we're proud of

Hybrid AI System: We successfully created a powerful pipeline that combines the natural language understanding of an LLM with the predictive power of a traditional gradient-boosting model. This allows us to create structured insights from unstructured data effectively. End-to-End Real-time Analysis: We are proud of building a complete, end-to-end system that can perform a complex, multi-stage analysis and present the results to the user in a matter of seconds, all while showing live progress. Intuitive User Experience: We designed a clean, responsive, and intuitive interface that makes a complex data analysis process feel simple and accessible to any user.

### What we learned

Throughout this project, we gained deep insights into the practical application of modern AI and web technologies. We learned how to effectively chain different AI models together, the nuances of prompt engineering for data extraction, and the best practices for building responsive, asynchronous web applications with FastAPI and React.

### What's next

Broader Data Integration: We plan to incorporate more diverse data sources, including financial reports (SEC filings), employee sentiment from sites like Glassdoor, and public market data. Historical Trend Analysis: A key upcoming feature will be the ability to track a company's risk score over time, providing users with a historical perspective on its stability. User Accounts & Watchlists: We will introduce user accounts, allowing individuals to save a personalized watchlist of companies and receive notifications when a company's risk profile changes significantly. API Access: To extend our reach, we plan to offer a public API that will allow other developers and services to integrate our layoff risk analysis into their own applications.

## README (from the GitHub repository)

# Farsight.fyi Dashboard

A responsive, AI-powered dashboard for analyzing company layoff risks. Built with React, Vite, TypeScript, and Tailwind CSS.

## Features

- **Risk Analysis**: Visual gauge showing layoff risk score (0-100)
- **Factor Analysis**: SHAP-style visualization of contributing factors
- **Trend Tracking**: 30-day sparkline chart showing risk history
- **Dark Mode**: Toggle between light and dark themes
- **Recent Lookups**: Quick access to recently searched companies
- **Responsive Design**: Mobile-first approach with adaptive layouts

## Getting Started

### Prerequisites

- Node.js (version 16 or higher)
- npm or yarn

### Installation

1. Clone the repository:
```bash
git clone <repository-url>
cd layoff-radar
```

2. Install dependencies:
```bash
npm install
```

3. Set up environment variables:
```bash
cp .env.example .env
# Edit .env with your API configuration
```

4. Start the development server:
```bash
npm run dev
```

5. Open your browser and visit `http://localhost:5173`

## API Integration

The dashboard expects a REST API endpoint at `/score/<company>` that returns:

```json
{
  "company": "Tesla",
  "risk": 82,
  "top_factors": [
    {"name": "Executive exits", "value": 0.34},
    {"name": "Layoff-intent news", "value": 0.28},
    {"name": "Funding cushion", "value": -0.05}
  ],
  "history": [
    {"date": "2025-06-11", "risk": 78}
  ],
  "explanation": "High risk mainly because..."
}
```

## Configuration

Set your API base URL in the `.env` file:

```env
VITE_API_BASE_URL=https://your-api-domain.com
```

## Building for Production

```bash
npm run build
```

The built files will be in the `dist` directory.

## Technologies Used

- **React** - UI framework
- **Vite** - Build tool and dev server
- **TypeScript** - Type safety
- **Tailwind CSS** - Styling
- **Recharts** - Data visualization
- **Radix UI** - Accessible components
- **Lucide React** - Icons

## License

MIT License


## Detected evidence (automated analysis)

Indexed codebase: 87 recognized source files, 229 KB.
- Anthropic (technology) — detected in the code
- CSS (language) — detected in the code
- FastAPI (technology) — detected in the code
- HTML (language) — detected in the code
- JavaScript (language) — detected in the code
- Python (language) — detected in the code
- React (technology) — detected in the code
- Tailwind CSS (technology) — detected in the code
- TypeScript (language) — detected in the code

## Codebase structure (from repository index)

### Files (102 of 102)

```
.DS_Store
.gitignore
client/.env
client/.gitignore
client/bun.lockb
client/components.json
client/eslint.config.js
client/index.html
client/package.json
client/postcss.config.js
client/public/robots.txt
client/src/App.css
client/src/App.tsx
client/src/components/FactorCards.tsx
client/src/components/RiskGauge.tsx
client/src/components/ShapChart.tsx
client/src/components/SparklineChart.tsx
client/src/components/ui/accordion.tsx
client/src/components/ui/alert-dialog.tsx
client/src/components/ui/alert.tsx
client/src/components/ui/aspect-ratio.tsx
client/src/components/ui/avatar.tsx
client/src/components/ui/badge.tsx
client/src/components/ui/breadcrumb.tsx
client/src/components/ui/button.tsx
client/src/components/ui/calendar.tsx
client/src/components/ui/card.tsx
client/src/components/ui/carousel.tsx
client/src/components/ui/chart.tsx
client/src/components/ui/checkbox.tsx
client/src/components/ui/collapsible.tsx
client/src/components/ui/command.tsx
client/src/components/ui/context-menu.tsx
client/src/components/ui/dialog.tsx
client/src/components/ui/drawer.tsx
client/src/components/ui/dropdown-menu.tsx
client/src/components/ui/form.tsx
client/src/components/ui/hover-card.tsx
client/src/components/ui/input-otp.tsx
client/src/components/ui/input.tsx
client/src/components/ui/label.tsx
client/src/components/ui/menubar.tsx
client/src/components/ui/navigation-menu.tsx
client/src/components/ui/pagination.tsx
client/src/components/ui/popover.tsx
client/src/components/ui/progress.tsx
client/src/components/ui/radio-group.tsx
client/src/components/ui/resizable.tsx
client/src/components/ui/scroll-area.tsx
client/src/components/ui/select.tsx
client/src/components/ui/separator.tsx
client/src/components/ui/sheet.tsx
client/src/components/ui/sidebar.tsx
client/src/components/ui/skeleton.tsx
client/src/components/ui/slider.tsx
client/src/components/ui/sonner.tsx
client/src/components/ui/switch.tsx
client/src/components/ui/table.tsx
client/src/components/ui/tabs.tsx
client/src/components/ui/textarea.tsx
client/src/components/ui/toast.tsx
client/src/components/ui/toaster.tsx
client/src/components/ui/toggle-group.tsx
client/src/components/ui/toggle.tsx
client/src/components/ui/tooltip.tsx
client/src/components/ui/use-toast.ts
client/src/hooks/use-mobile.tsx
client/src/hooks/use-toast.ts
client/src/hooks/use-typing-animation.ts
client/src/hooks/useRiskData.ts
client/src/index.css
client/src/lib/storage.ts
client/src/lib/utils.ts
client/src/main.tsx
client/src/pages/Dashboard.tsx
client/src/pages/Index.tsx
client/src/pages/Landing.tsx
client/src/pages/NotFound.tsx
client/src/types/index.ts
client/src/utils/api.ts
client/src/utils/test.js
client/src/vite-env.d.ts
client/tailwind.config.ts
client/tsconfig.app.json
client/tsconfig.json
client/tsconfig.node.json
client/vite.config.ts
client/vite.config.ts.timestamp-1750599823873-d6498343644f3.mjs
database.py
features_model.py
get_features.py
main_new.py
main.py
model
models.py
package.json
predict.py
prompts_claude.py
README.md
requirements.txt
scrape.py
summary.py
```

### Dependencies

- client/package.json: @eslint/js@^9.9.0, @hookform/resolvers@^3.9.0, @radix-ui/react-accordion@^1.2.0, @radix-ui/react-alert-dialog@^1.1.1, @radix-ui/react-aspect-ratio@^1.1.0, @radix-ui/react-avatar@^1.1.0, @radix-ui/react-checkbox@^1.1.1, @radix-ui/react-collapsible@^1.1.0, @radix-ui/react-context-menu@^2.2.1, @radix-ui/react-dialog@^1.1.2, @radix-ui/react-dropdown-menu@^2.1.1, @radix-ui/react-hover-card@^1.1.1, @radix-ui/react-label@^2.1.0, @radix-ui/react-menubar@^1.1.1, @radix-ui/react-navigation-menu@^1.2.0, @radix-ui/react-popover@^1.1.1, @radix-ui/react-progress@^1.1.0, @radix-ui/react-radio-group@^1.2.0, @radix-ui/react-scroll-area@^1.1.0, @radix-ui/react-select@^2.1.1, @radix-ui/react-separator@^1.1.0, @radix-ui/react-slider@^1.2.0, @radix-ui/react-slot@^1.1.0, @radix-ui/react-switch@^1.1.0, @radix-ui/react-tabs@^1.1.0, @radix-ui/react-toast@^1.2.1, @radix-ui/react-toggle@^1.1.0, @radix-ui/react-toggle-group@^1.1.0, @radix-ui/react-tooltip@^1.1.4, @tailwindcss/typography@^0.5.15, @tanstack/react-query@^5.56.2, @types/lodash-es@^4.17.12, @types/node@^22.5.5, @types/react@^18.3.3, @types/react-dom@^18.3.0, @vitejs/plugin-react-swc@^3.5.0, autoprefixer@^10.4.20, axios@^1.10.0, class-variance-authority@^0.7.1, clsx@^2.1.1, cmdk@^1.0.0, date-fns@^3.6.0, embla-carousel-react@^8.3.0, eslint@^9.9.0, eslint-plugin-react-hooks@^5.1.0-rc.0, eslint-plugin-react-refresh@^0.4.9, globals@^15.9.0, input-otp@^1.2.4, lodash-es@^4.17.21, lucide-react@^0.462.0, next-themes@^0.3.0, postcss@^8.4.47, react@^18.3.1, react-day-picker@^8.10.1, react-dom@^18.3.1, react-hook-form@^7.53.0, react-icons@^5.5.0, react-resizable-panels@^2.1.3, react-router-dom@^6.26.2, recharts@^2.12.7, socket.io-client@^4.8.1, sonner@^1.5.0, tailwind-merge@^2.5.2, tailwindcss@^3.4.11, tailwindcss-animate@^1.0.7, typescript@^5.5.3, typescript-eslint@^8.0.1, vaul@^0.9.3, vite@^5.4.1, zod@^3.23.8
- package.json: axios@^1.10.0
- requirements.txt: aiohappyeyeballs@==2.6.1, aiohttp@==3.12.13, aiosignal@==1.3.2, aiosqlite@==0.19.0, annotated-types@==0.7.0, anthropic@==0.54.0, anyio@==3.7.1, attrs@==25.3.0, beautifulsoup4@==4.13.4, bidict@==0.23.1, catboost@==1.2.8, certifi@==2025.6.15, cffi@==1.17.1, charset-normalizer@==3.4.2, click@==8.2.1, colorama@==0.4.6, contourpy@==1.3.2, cycler@==0.12.1, distro@==1.9.0, fastapi@==0.104.1, fonttools@==4.58.4, frozenlist@==1.7.0, graphviz@==0.21, greenlet@==3.2.3, h11@==0.16.0, httpcore@==1.0.9, httptools@==0.6.4, httpx@==0.28.1, idna@==3.10, jiter@==0.10.0, kiwisolver@==1.4.8, matplotlib@==3.10.3, multidict@==6.5.0, narwhals@==1.43.1, netifaces@==0.11.0, numpy@==2.3.1, outcome@==1.3.0.post0, packaging@==25.0, pandas@==2.3.0, pillow@==11.2.1, plotly@==6.1.2, propcache@==0.3.2, pycparser@==2.22, pydantic@==2.5.0, pydantic_core@==2.14.1, pyparsing@==3.2.3, PySocks@==1.7.1, python-dateutil@==2.9.0.post0, python-dotenv@==1.1.0, python-engineio@==4.12.2, python-multipart@==0.0.6, python-socketio@==5.13.0, pytz@==2025.2, PyYAML@==6.0.2, requests@==2.32.4, scipy@==1.15.3, selenium@==4.33.0, setuptools@==80.9.0, simple-websocket@==1.1.0, six@==1.17.0, sniffio@==1.3.1, sortedcontainers@==2.4.0, soupsieve@==2.7, SQLAlchemy@==2.0.23, starlette@==0.27.0, trio@==0.30.0, trio-websocket@==0.12.2, typing_extensions@==4.13.2, tzdata@==2025.2, undetected-chromedriver@==3.5.5, urllib3@==2.4.0, uvicorn@==0.24.0, watchfiles@==1.1.0, websocket-client@==1.8.0, websockets@==15.0.1, wsproto@==1.2.0, yarl@==1.20.1

### Recent commits (newest first)

- refactoring
- refactoring
- llm improvement
- improved factorcards
- improved dashboard
- a
- added factor cards
- fix
- adjusted prompts
- fixed prediction
- a
- fix features
- a
- fix features
- fe
- key_points added to socket
- feat: migrated to socketio, added landing page
- added key_points to summary
- browser icon added
- prediction fix

## Key source files (fetched from GitHub, selected and truncated for size)

### package.json

```
{
  "dependencies": {
    "axios": "^1.10.0"
  }
}

```

### requirements.txt

```
aiohappyeyeballs==2.6.1
aiohttp==3.12.13
aiosignal==1.3.2
aiosqlite==0.19.0
annotated-types==0.7.0
anthropic==0.54.0
anyio==3.7.1
attrs==25.3.0
beautifulsoup4==4.13.4
bidict==0.23.1
catboost==1.2.8
certifi==2025.6.15
cffi==1.17.1
charset-normalizer==3.4.2
click==8.2.1
colorama==0.4.6
contourpy==1.3.2
cycler==0.12.1
distro==1.9.0
fastapi==0.104.1
fonttools==4.58.4
frozenlist==1.7.0
graphviz==0.21
greenlet==3.2.3
h11==0.16.0
httpcore==1.0.9
httptools==0.6.4
httpx==0.28.1
idna==3.10
jiter==0.10.0
kiwisolver==1.4.8
matplotlib==3.10.3
multidict==6.5.0
narwhals==1.43.1
netifaces==0.11.0
numpy==2.3.1
outcome==1.3.0.post0
packaging==25.0
pandas==2.3.0
pillow==11.2.1
plotly==6.1.2
propcache==0.3.2
pycparser==2.22
pydantic==2.5.0
pydantic_core==2.14.1
pyparsing==3.2.3
PySocks==1.7.1
python-dateutil==2.9.0.post0
python-dotenv==1.1.0
python-engineio==4.12.2
python-multipart==0.0.6
python-socketio==5.13.0
pytz==2025.2
PyYAML==6.0.2
requests==2.32.4
scipy==1.15.3
selenium==4.33.0
setuptools==80.9.0
simple-websocket==1.1.0
six==1.17.0
sniffio==1.3.1
sortedcontainers==2.4.0
soupsieve==2.7
SQLAlchemy==2.0.23
starlette==0.27.0
trio==0.30.0
trio-websocket==0.12.2
typing_extensions==4.13.2
tzdata==2025.2
undetected-chromedriver==3.5.5
urllib3==2.4.0
uvicorn==0.24.0
watchfiles==1.1.0
websocket-client==1.8.0
websockets==15.0.1
wsproto==1.2.0
yarl==1.20.1

```

### client/package.json

```
{
  "name": "vite_react_shadcn_ts",
  "private": true,
  "version": "0.0.0",
  "type": "module",
  "scripts": {
    "dev": "vite",
    "build": "vite build",
    "build:dev": "vite build --mode development",
    "lint": "eslint .",
    "preview": "vite preview"
  },
  "dependencies": {
    "@hookform/resolvers": "^3.9.0",
    "@radix-ui/react-accordion": "^1.2.0",
    "@radix-ui/react-alert-dialog": "^1.1.1",
    "@radix-ui/react-aspect-ratio": "^1.1.0",
    "@radix-ui/react-avatar": "^1.1.0",
    "@radix-ui/react-checkbox": "^1.1.1",
    "@radix-ui/react-collapsible": "^1.1.0",
    "@radix-ui/react-context-menu": "^2.2.1",
    "@radix-ui/react-dialog": "^1.1.2",
    "@radix-ui/react-dropdown-menu": "^2.1.1",
    "@radix-ui/react-hover-card": "^1.1.1",
    "@radix-ui/react-label": "^2.1.0",
    "@radix-ui/react-menubar": "^1.1.1",
    "@radix-ui/react-navigation-menu": "^1.2.0",
    "@radix-ui/react-popover": "^1.1.1",
    "@radix-ui/react-progress": "^1.1.0",
    "@radix-ui/react-radio-group": "^1.2.0",
    "@radix-ui/react-scroll-area": "^1.1.0",
    "@radix-ui/react-select": "^2.1.1",
    "@radix-ui/react-separator": "^1.1.0",
    "@radix-ui/react-slider": "^1.2.0",
    "@radix-ui/react-slot": "^1.1.0",
    "@radix-ui/react-switch": "^1.1.0",
    "@radix-ui/react-tabs": "^1.1.0",
    "@radix-ui/react-toast": "^1.2.1",
    "@radix-ui/react-toggle": "^1.1.0",
    "@radix-ui/react-toggle-group": "^1.1.0",
    "@radix-ui/react-tooltip": "^1.1.4",
    "@tanstack/react-query": "^5.56.2",
    "@types/lodash-es": "^4.17.12",
    "axios": "^1.10.0",
    "class-variance-authority": "^0.7.1",
    "clsx": "^2.1.1",
    "cmdk": "^1.0.0",
    "date-fns": "^3.6.0",
    "embla-carousel-react": "^8.3.0",
    "input-otp": "^1.2.4",
    "lodash-es": "^4.17.21",
    "lucide-react": "^0.462.0",
    "next-themes": "^0.3.0",
    "react": "^18.3.1",
    "react-day-picker": "^8.10.1",
    "react-dom": "^18.3.1",
    "react-hook-form": "^7.53.0",
    "react-icons": "^5.5.0",
    "react-resizable-panels": "^2.1.3",
    "react-router-dom": "^6.26.2",
    "recharts": "^2.12.7",
    "socket.io-client": "^4.8.1",
    "sonner": "^1.5.0",
    "tailwind-merge": "^2.5.2",
    "tailwindcss-animate": "^1.0.7",
    "vaul": "^0.9.3",
    "zod": "^3.23.8"
  },
  "devDependencies": {
    "@eslint/js": "^9.9.0",
    "@tailwindcss/typography": "^0.5.15",
    "@types/node": "^22.5.5",
    "@types/react": "^18.3.3",
    "@types/react-dom": "^18.3.0",
    "@vitejs/plugin-react-swc": "^3.5.0",
    "autoprefixer": "^10.4.20",
    "eslint": "^9.9.0",
    "eslint-plugin-react-hooks": "^5.1.0-rc.0",
    "eslint-plugin-react-refresh": "^0.4.9",
    "globals": "^15.9.0",
    "postcss": "^8.4.47",
    "tailwindcss": "^3.4.11",
    "typescript": "^5.5.3",
    "typescript-eslint": "^8.0.1",
    "vite": "^5.4.1"
  }
}

```

### main.py

```python
from fastapi import FastAPI, Depends, HTTPException
from sqlalchemy.ext.asyncio import AsyncSession
from sqlalchemy import select, delete
from typing import List
import asyncio

from database import engine, Base, get_database_session, Layover as DBLayover, AsyncSessionLocal
from models import Layover, addLayover

app = FastAPI(title="FastAPI with SQLite", description="A FastAPI application with SQLite database")

# Create database tables
async def create_tables():
    async with engine.begin() as conn:
        await conn.run_sync(Base.metadata.create_all)

# Initialize database on startup
@app.on_event("startup")
async def startup_event():
    await create_tables()

@app.get("/")
async def root():
    return {"message": "FastAPI with SQLite Database", "docs": "/docs"}    

# Layover endpoints
@app.get("/layovers", response_model=List[Layover])
async def get_layovers(db: AsyncSession = Depends(get_database_session)):
    """Get all layovers from the database"""
    result = await db.execute(select(DBLayover))
    layovers = result.scalars().all()
    return layovers

@app.get("/layovers/{company_name}", response_model=List[Layover])
async def get_layover_by_company(company_name: str, db: AsyncSession = Depends(get_database_session)):
    """Get layovers by company name"""
    result = await db.execute(select(DBLayover).where(DBLayover.company_name == company_name))
    layovers = result.scalars().all()
    if not layovers:
        raise HTTPException(status_code=404, detail="No layoffs found for this company")
    return layovers

@app.post("/layovers", response_model=Layover)
async def create_layover(layover: addLayover, db: AsyncSession = Depends(get_database_session)):
    """Create a new layover record in the database"""
    db_layover = DBLayover(**layover.model_dump())
    db.add(db_layover)
    await db.commit()
    await db.refresh(db_layover)
    return db_layover

# Get layovers by industry
@app.get("/layovers/industry/{industry}", response_model=List[Layover])
async def get_layovers_by_industry(industry: str, db: AsyncSession = Depends(get_database_session)):
    """Get all layovers by industry"""
    result = await db.execute(select(DBLayover).where(DBLayover.industry == industry))
    layovers = result.scalars().all()
    if not layovers:
        raise HTTPException(status_code=404, detail="No layoffs found for this industry")
    return layovers

# Get layovers by country
@app.get("/layovers/country/{country}", response_model=List[Layover])
async def get_layovers_by_country(country: str, db: AsyncSession = Depends(get_database_session)):
    """Get all layovers by country"""
    result = await db.execute(select(DBLayover).where(DBLayover.country == country))
    layovers = result.scalars().all()
    if not layovers:
        raise HTTPException(status_code=404, detail="No layoffs found for this country")
    return layovers

# Database stats endpoint
@app.get("/stats")
async def get_database_stats(db: AsyncSession = Depends(get_database_session)):
    """Get database statistics"""
    layovers_result = await db.execute(select(DBLayover))
    layovers_count = len(layovers_result.scalars().all())
    
    return {
        "total_layovers": layovers_count,
        "database_file": "app.db"
    }


@app.delete("/layovers")
async def deleteAllLayovers(db: AsyncSession = Depends(get_database_session)):
    """Delete all layovers from the database"""
    await db.execute(delete(DBLayover))
    await db.commit()
    return {"message": "All layovers deleted"}

@app.delete("/layovers/{company_name}")
async def deleteLayoverByCompany(company_name: str, db: AsyncSession = Depends(get_database_session)):
    """Delete a layover by company name"""
    await db.execute(delete(DBLayover).where(DBLayover.company_name == company_name))
    await db.commit()
    return {"message": "Layover deleted"}
```

### client/src/main.tsx

```typescript
import { createRoot } from 'react-dom/client'
import App from './App.tsx'
import './index.css'

createRoot(document.getElementById("root")!).render(<App />);

```

### client/src/App.tsx

```typescript
import { Toaster } from "@/components/ui/toaster";
import { Toaster as Sonner } from "@/components/ui/sonner";
import { TooltipProvider } from "@/components/ui/tooltip";
import { QueryClient, QueryClientProvider } from "@tanstack/react-query";
import { BrowserRouter, Routes, Route } from "react-router-dom";
import Landing from "./pages/Landing";
import Dashboard from "./pages/Dashboard";
import NotFound from "./pages/NotFound";

const queryClient = new QueryClient();

const App = () => (
  <QueryClientProvider client={queryClient}>
    <TooltipProvider>
      <Toaster />
      <Sonner />
      <BrowserRouter>
        <Routes>
          <Route path="/" element={<Landing />} />
          <Route path="/dashboard" element={<Dashboard />} />
          {/* ADD ALL CUSTOM ROUTES ABOVE THE CATCH-ALL "*" ROUTE */}
          <Route path="*" element={<NotFound />} />
        </Routes>
      </BrowserRouter>
    </TooltipProvider>
  </QueryClientProvider>
);

export default App;

```

### client/src/pages/Index.tsx

```typescript

import Dashboard from './Dashboard';

const Index = () => {
  return <Dashboard />;
};

export default Index;

```

### client/src/types/index.ts

```typescript

export interface Factor {
  name: string;
  value: number;
}

export interface HistoryPoint {
  date: string;
  risk: number;
}

export interface RiskData {
  company: string;
  risk: number;
  top_factors: Factor[];
  history: HistoryPoint[];
  explanation: string;
}

```

### features_model.py

```python
from pydantic import BaseModel
from typing import Optional

class Features(BaseModel):
    Location_HQ: str
    Industry: str
    Stage: str
    Year: int
    log10_Funds_Raised: int

```

### predict.py

```python
import pickle
import pandas as pd
from features_model import Features


def predict(features: Features):
    with open("model", "rb") as f:
        model = pickle.load(f)

    new_sample = pd.DataFrame([features.dict()])

    prediction = model.predict(new_sample)

    return prediction[0]


if __name__ == "__main__":
    features = Features(
        Location_HQ="Google",
        Industry="Tech",
        Stage="Stage 1",
        Year=2020,
        log10_Funds_Raised=10
    )
    print(predict(features))
```

[79 more indexed source files omitted to keep this export small. The full file list is in the Codebase structure section above.]