Claude
Skills
Sign in
Back

pyre-code-ml-practice

Included with Lifetime
$97 forever

Self-hosted ML coding practice platform with 68 problems covering Transformers, diffusion, RLHF, and more — instant browser feedback, no GPU required.

General

What this skill does


# Pyre Code ML Practice Platform

> Skill by [ara.so](https://ara.so) — Daily 2026 Skills collection.

Pyre Code is a self-hosted ML coding practice platform with 68 problems ranging from ReLU to flow matching. Users implement internals of modern AI systems (Transformers, vLLM, TRL, diffusion models) in a browser editor with instant pass/fail feedback, no GPU required.

---

## Installation

### Option A — One-liner (recommended)

```bash
git clone https://github.com/whwangovo/pyre-code.git
cd pyre-code
./setup.sh
npm run dev
```

`setup.sh` creates a `.venv` (prefers `uv`, falls back to `python3 -m venv`), installs all Python deps, then prints the start command.

### Option B — Conda

```bash
git clone https://github.com/whwangovo/pyre-code.git
cd pyre-code
conda create -n pyre python=3.11 -y && conda activate pyre
pip install -e ".[dev]"
npm install
npm run dev
```

### Option C — Docker

```bash
git clone https://github.com/whwangovo/pyre-code.git
cd pyre-code
docker compose up --build
```

Progress persists in a Docker volume. Reset with `docker compose down -v`.

### After installation

- **Grading service**: `http://localhost:8000`
- **Web app**: `http://localhost:3000`

---

## Project Structure

```
pyre/
├── web/                        # Next.js frontend
│   ├── src/app/                # Pages and API routes
│   ├── src/components/         # UI components
│   └── src/lib/                # Utilities, problem data
├── grading_service/            # FastAPI backend (grading API)
├── torch_judge/                # Judge engine — problem definitions + test runner
│   ├── problems/               # Individual problem modules
│   └── runner.py               # Test execution logic
├── setup.sh                    # Environment bootstrap script
├── package.json                # Dev scripts (runs frontend + backend concurrently)
└── pyproject.toml              # Python package config
```

---

## Key Commands

```bash
# Start both frontend and backend concurrently
npm run dev

# Start only the grading service (FastAPI)
cd grading_service && uvicorn main:app --reload --port 8000

# Start only the frontend (Next.js)
cd web && npm run dev

# Run Python tests
pytest torch_judge/

# Install Python package in editable mode with dev deps
pip install -e ".[dev]"

# Docker: build and start
docker compose up --build

# Docker: stop and remove volumes (reset progress)
docker compose down -v
```

---

## Configuration

### Environment Variables

Create `web/.env.local` to override defaults:

```bash
# URL of the FastAPI grading service
GRADING_SERVICE_URL=http://localhost:8000

# SQLite database path for progress tracking
DB_PATH=./data/pyre.db
```

### AI Help (Optional)

Copy `web/.env.example` to `web/.env` and configure:

```bash
AI_HELP_BASE_URL=https://api.openai.com/v1
AI_HELP_API_KEY=$OPENAI_API_KEY
AI_HELP_MODEL=gpt-4o-mini
```

Any OpenAI-compatible endpoint works: OpenAI, Anthropic via proxy, Ollama, etc. Users can also set their own key in the UI if no server-side config is present.

---

## Problem Categories

| Category | Examples |
|---|---|
| **Fundamentals** | ReLU, Softmax, GELU, SwiGLU, Dropout, Embedding, Linear, Kaiming Init |
| **Normalization** | LayerNorm, BatchNorm, RMSNorm |
| **Attention** | Scaled Dot-Product, Multi-Head, Causal, GQA, Flash, Differential, MLA |
| **Position Encoding** | Sinusoidal PE, RoPE, ALiBi, NTK-aware RoPE |
| **Architecture** | GPT-2 Block, ViT Block, Conv2D, MoE, Depthwise Conv |
| **Training** | Adam, Cosine LR, Gradient Clipping, Mixed Precision, Activation Checkpointing |
| **Distributed** | Tensor Parallel, FSDP, Ring Attention |
| **Inference** | KV Cache, Top-k Sampling, Beam Search, Speculative Decoding, Paged Attention |
| **Alignment** | DPO, GRPO, PPO, Reward Model |
| **Diffusion** | Noise Schedule, DDIM Step, Flow Matching, adaLN-Zero |
| **Adaptation** | LoRA, QLoRA |
| **Reasoning** | MCTS, Multi-Token Prediction |
| **SSM** | Mamba SSM |

---

## Adding a New Problem

Problems live in `torch_judge/problems/`. Each problem is a Python module with a standard structure:

```python
# torch_judge/problems/my_new_problem.py

import torch
import torch.nn as nn
from typing import Any

PROBLEM_ID = "my_new_problem"
TITLE = "My New Problem: Implement Foo"
DIFFICULTY = "medium"  # "easy" | "medium" | "hard"
CATEGORY = "Fundamentals"

DESCRIPTION = """
## My New Problem

Implement the `foo` function that does XYZ.

### Input
- `x` (Tensor): shape `(batch, dim)`

### Output
- Tensor of shape `(batch, dim)`

### Formula
$$\\text{foo}(x) = x^2 + 1$$
"""

STARTER_CODE = """
import torch

def foo(x: torch.Tensor) -> torch.Tensor:
    # Your implementation here
    pass
"""

REFERENCE_SOLUTION = """
import torch

def foo(x: torch.Tensor) -> torch.Tensor:
    return x ** 2 + 1
"""

def make_test_cases() -> list[dict[str, Any]]:
    \"\"\"Return a list of test cases, each with inputs and expected outputs.\"\"\"
    cases = []
    
    # Basic case
    x = torch.tensor([[1.0, 2.0, 3.0]])
    cases.append({
        "input": {"x": x},
        "expected": x ** 2 + 1,
        "description": "Basic 1x3 tensor",
    })
    
    # Batch case
    x = torch.randn(4, 16)
    cases.append({
        "input": {"x": x},
        "expected": x ** 2 + 1,
        "description": "Batch of 4, dim 16",
    })
    
    # Edge case: zeros
    x = torch.zeros(2, 8)
    cases.append({
        "input": {"x": x},
        "expected": torch.ones(2, 8),
        "description": "Zero tensor",
    })
    
    return cases


def grade(submission_code: str) -> dict[str, Any]:
    \"\"\"Execute submission and return grading results.\"\"\"
    namespace = {}
    exec(submission_code, namespace)
    
    if "foo" not in namespace:
        return {"passed": 0, "total": 0, "error": "Function 'foo' not found"}
    
    fn = namespace["foo"]
    test_cases = make_test_cases()
    results = []
    
    for i, case in enumerate(test_cases):
        try:
            output = fn(**case["input"])
            passed = torch.allclose(output, case["expected"], atol=1e-5)
            results.append({
                "case": i + 1,
                "description": case["description"],
                "passed": passed,
                "error": None if passed else f"Output mismatch: got {output}, expected {case['expected']}",
            })
        except Exception as e:
            results.append({
                "case": i + 1,
                "description": case["description"],
                "passed": False,
                "error": str(e),
            })
    
    passed = sum(r["passed"] for r in results)
    return {
        "passed": passed,
        "total": len(results),
        "results": results,
    }
```

### Register the problem

After creating the module, register it in the problem registry (typically `torch_judge/registry.py` or equivalent):

```python
from torch_judge.problems import my_new_problem

PROBLEMS = [
    # ... existing problems ...
    my_new_problem,
]
```

---

## Grading Service API

The FastAPI grading service at `http://localhost:8000` exposes:

```bash
# Health check
GET /health

# List all problems
GET /problems

# Get a specific problem
GET /problems/{problem_id}

# Submit a solution
POST /submit
Content-Type: application/json

{
  "problem_id": "relu",
  "code": "import torch\n\ndef relu(x):\n    return torch.clamp(x, min=0)"
}

# Response
{
  "problem_id": "relu",
  "passed": 3,
  "total": 3,
  "results": [
    {"case": 1, "description": "Basic positive values", "passed": true, "error": null},
    {"case": 2, "description": "Negative values", "passed": true, "error": null},
    {"case": 3, "description": "Mixed values", "passed": true, "error": null}
  ]
}
```

### Calling the grading API from Python

```python
import requests

response = requests.post(
    "http://localhost:8000/submit",
    json={
        "problem_id": "softmax",
        "code": """
import torch

def softmax(x: torch.Tensor, dim: int = -1) -> torch.Tensor:
    x_max

Related in General