Files
lux/docs/PRIORITY_PLAN.md
Brandon Lucas bc1e5aa8a1 docs: add prioritized implementation plan
Based on analysis of what makes developers love languages:
- P0: Elm-quality errors, HTTP framework, PostgreSQL driver
- P1: Property-based testing, better REPL, benchmarks
- P2: LSP improvements, docs generator, schema tools
- P3: Effect visualization, package registry, production hardening

Focus on high-impact features that showcase Lux's unique advantages.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-02-16 01:07:36 -05:00

8.8 KiB

Lux Priority Implementation Plan

Based on analysis of what makes developers love languages

Core Insight

From studying successful languages (Rust, Elm, Go, Gleam), the pattern is clear:

  1. Elm has 0% runtime exceptions and legendary error messages → developers evangelize it
  2. Rust has "if it compiles, it works" confidence → 72% admiration
  3. Go has simplicity and fast feedback → massive adoption
  4. Gleam has type safety on BEAM → 70% admiration (2nd highest)

Lux's unique pitch: Effects you can see. Tests you can trust. No mocks needed.


Phase 1: Make Developers Smile (Highest Impact)

1.1 Elm-Quality Error Messages

Why: Elm's error messages are the #1 reason people recommend it. This is free marketing.

Current state: Basic errors with location Target state: Conversational, helpful, with suggestions

Current:
  Type error at 5:12: Cannot unify Int with String

Target:
  ── TYPE MISMATCH ─────────────────────────── src/main.lux

  The `age` field expects an Int, but I found a String:

  5│      age: "twenty-five"
               ^^^^^^^^^^^^

  Hint: Did you mean to use String.parseInt?

      age: String.parseInt("twenty-five") |> Option.getOrElse(0)

Implementation:

  • Add error code catalog (E001, E002, etc.)
  • "Did you mean?" suggestions using Levenshtein distance
  • Show expected vs actual with visual diff
  • Context-aware hints based on error type

Effort: 2-3 weeks Impact: HIGH - This is what people tweet about

1.2 HTTP Framework (Routing + Middleware)

Why: Web services are the most common use case. Without this, Lux is a toy.

// Target API
let app = Router.new()
    |> Router.get("/users", listUsers)
    |> Router.get("/users/:id", getUser)
    |> Router.post("/users", createUser)
    |> Router.use(loggerMiddleware)
    |> Router.use(authMiddleware)

fn main(): Unit with {HttpServer} =
    HttpServer.serve(app, 3000)

Implementation:

  • Path pattern matching with params
  • Middleware composition
  • Request/Response types
  • JSON body parsing integration

Effort: 2 weeks Impact: HIGH - Enables real projects

1.3 PostgreSQL Driver

Why: SQLite is nice for demos, real apps need Postgres/MySQL.

effect Postgres {
    fn connect(url: String): Connection
    fn query(conn: Connection, sql: String, params: List<Value>): List<Row>
    fn execute(conn: Connection, sql: String, params: List<Value>): Int
    fn transaction<T>(conn: Connection, f: fn(): T with {Postgres}): T
}

Implementation:

  • Native Rust driver (tokio-postgres)
  • Connection pooling
  • Parameterized queries (SQL injection prevention)
  • Transaction support

Effort: 2 weeks Impact: HIGH - Enables production backends


Phase 2: Showcase Unique Features

2.1 Property-Based Testing Framework

Why: This showcases behavioral types - Lux's most unique feature.

test "reverse is involutive" =
    forAll(listOf(int), fn(xs) =>
        List.reverse(List.reverse(xs)) == xs
    ) is pure is total  // Compiler verifies!

test "sort produces sorted output" =
    forAll(listOf(int), fn(xs) =>
        let sorted = List.sort(xs)
        isSorted(sorted) && sameElements(xs, sorted)
    ) where result is idempotent  // Compiler verifies!

Implementation:

  • Generator combinators (int, string, listOf, oneOf, etc.)
  • Shrinking for minimal failing cases
  • Integration with behavioral type checker
  • Nice failure output

Effort: 2 weeks Impact: HIGH - Unique selling point

2.2 Schema Evolution Showcase

Why: This is unique to Lux. Need a compelling demo.

Build: Database migration tool that generates SQL from Lux types

type User @v1 = { name: String, email: String }
type User @v2 = { name: String, email: String, age: Option<Int> }
    from @v1 = fn(u) => { ...u, age: None }

// Tool generates:
// ALTER TABLE users ADD COLUMN age INTEGER;

Effort: 1 week Impact: MEDIUM - Differentiator for data teams

2.3 Effect Visualization

Why: Make the invisible visible. Show effect flow in code.

lux visualize src/main.lux

processOrder: Order -> Receipt
  ├── Database.query (line 12)
  │   └── SQL: "SELECT * FROM inventory"
  ├── PaymentGateway.charge (line 18)
  │   └── Amount: order.total
  └── Email.send (line 25)
      └── To: order.customer.email

Effort: 1 week Impact: MEDIUM - Educational, impressive in demos


Phase 3: Developer Experience Polish

3.1 Better REPL

Why: First impression matters. REPL is how people try the language.

Add:

  • Syntax highlighting
  • Multi-line editing
  • Tab completion for modules
  • :doc command for documentation
  • :browse Module to list exports
  • Pretty-printed output

Effort: 1 week Impact: MEDIUM

3.2 LSP Improvements

Why: IDE experience is expected in 2025.

Add:

  • Inlay hints (show inferred types)
  • Code actions (import suggestions, fix suggestions)
  • Rename symbol
  • Find all references
  • Semantic highlighting

Effort: 2 weeks Impact: MEDIUM

3.3 Documentation Generator

Why: Rust's docs.rs is beloved. Good docs = adoption.

/// Calculate the factorial of a number.
///
/// # Examples
/// ```
/// factorial(5)  // => 120
/// ```
///
/// # Properties
/// - factorial(n) is pure
/// - factorial(n) is total for n >= 0
fn factorial(n: Int): Int is pure is total = ...

Effort: 1 week Impact: MEDIUM


Phase 4: Performance & Production

4.1 Performance Benchmarks

Why: Need to prove Lux is fast. Numbers matter.

Targets:

Benchmark Target Comparison
Fibonacci(40) < 1s Rust: 0.3s
HTTP req/sec > 50k Go: 100k
JSON parse 1MB < 50ms Node: 30ms

Effort: 1 week Impact: MEDIUM - Removes adoption blocker

4.2 Production Hardening

Why: Memory leaks and crashes kill adoption.

Add:

  • Memory leak detection in debug mode
  • Graceful shutdown handling
  • Signal handling (SIGTERM, SIGINT)
  • Structured logging

Effort: 2 weeks Impact: MEDIUM


Phase 5: Ecosystem Growth

5.1 Package Registry

Why: Central place to share code.

  • Host at packages.lux-lang.org
  • lux pkg publish
  • lux pkg search
  • Version resolution

Effort: 2 weeks Impact: HIGH long-term

5.2 Starter Templates

Why: Reduce friction for new projects.

lux new my-api --template web-api
lux new my-cli --template cli-tool
lux new my-lib --template library

Effort: 1 week Impact: LOW-MEDIUM


Implementation Order (Bang for Buck)

Priority Feature Effort Impact Why First
P0 Elm-quality errors 2-3 weeks HIGH Free marketing, retention
P0 HTTP framework 2 weeks HIGH Enables real projects
P0 PostgreSQL driver 2 weeks HIGH Production database
P1 Property testing 2 weeks HIGH Unique selling point
P1 Better REPL 1 week MEDIUM First impression
P1 Performance benchmarks 1 week MEDIUM Removes doubt
P2 LSP improvements 2 weeks MEDIUM Developer experience
P2 Documentation generator 1 week MEDIUM Ecosystem
P2 Schema evolution tool 1 week MEDIUM Differentiator
P3 Effect visualization 1 week MEDIUM Demos
P3 Package registry 2 weeks HIGH Long-term ecosystem
P3 Production hardening 2 weeks MEDIUM Enterprise readiness

Success Metrics

Short-term (3 months)

  • 10 example projects building without issues
  • Error messages rated "helpful" by 80% of users
  • HTTP "hello world" benchmark > 30k req/sec
  • 5 external contributors

Medium-term (6 months)

  • 1000 GitHub stars
  • 50 packages on registry
  • 3 production users
  • 1 conference talk

Long-term (1 year)

  • Self-hosted compiler
  • 100 packages
  • 10 production users
  • Featured in "State of Developer Ecosystem" survey

What NOT to Build (Yet)

Feature Why Skip
WASM backend JS backend covers browser use case
Mobile targets Small market, high effort
GUI framework Web handles most UI needs
AI/ML libraries Python dominates, wrong battle
Distributed systems Need core stability first
Advanced optimizations Correctness before speed

The Pitch After Phase 1

Lux: A functional language where the compiler tells you exactly what your code does.

  • See effects in signatures: fn save(user: User): Unit with {Database, Email}
  • Test without mocks: Just swap the handler. No DI framework needed.
  • Evolve your schemas: Types track versions. Migrations are code.
  • Compiler catches more: Pure, total, idempotent - verified, not hoped.

Effects you can see. Tests you can trust.