# Language Reference: Syntax

Complete syntax reference for Lux.

## Lexical Structure

### Comments

```lux
// Single-line comment

/* Multi-line
   comment */

/// Documentation comment (for declarations)
```

### Identifiers

```
identifier     = letter (letter | digit | '_')*
type_name      = upper_letter (letter | digit)*
```

Examples: `foo`, `myVar`, `Type`, `Option`

### Literals

```lux
// Integers
42
-17
1_000_000      // Underscores for readability

// Floats
3.14
-1.5

// Strings
"hello"
"line1\nline2"              // Escape sequences
"value: {expression}"       // String interpolation
"multi
line
string"

// Characters
'a'
'\n'
'🎉'

// Booleans
true
false

// Unit
()

// Lists
[]
[1, 2, 3]
["a", "b", "c"]

// Records
{}
{ x: 1, y: 2 }
{ name: "Alice", age: 30 }
```

### Escape Sequences

| Sequence | Meaning |
|----------|---------|
| `\n` | Newline |
| `\t` | Tab |
| `\r` | Carriage return |
| `\0` | Null character |
| `\\` | Backslash |
| `\"` | Double quote |
| `\'` | Single quote |
| `\{` | Literal brace (in interpolated strings) |

Note: Invalid escape sequences (e.g., `\z`) produce a parse error.

## Declarations

### Functions

```lux
// Basic function
fn name(param: Type): ReturnType = body

// Multiple parameters
fn add(a: Int, b: Int): Int = a + b

// Block body
fn complex(x: Int): Int = {
    let y = x * 2
    y + 1
}

// With effects
fn greet(name: String): Unit with {Console} =
    Console.print("Hello, " + name)

// With type parameters
fn identity<T>(x: T): T = x

// With constraints
fn show<T>(x: T): String where T: Show = x.show()

// With behavioral properties
fn pure_add(a: Int, b: Int): Int is pure = a + b

// With visibility
pub fn exported(): Int = 42

// With documentation
/// Computes the factorial of n
pub fn factorial(n: Int): Int =
    if n <= 1 then 1 else n * factorial(n - 1)
```

### Types

```lux
// Type alias
type UserId = Int

// Enum (sum type)
type Color =
    | Red
    | Green
    | Blue

// With data
type Option<T> =
    | Some(T)
    | None

// With named fields
type Person =
    | Person { name: String, age: Int }

// Record type
type Point = { x: Int, y: Int }

// With visibility
pub type PublicType = ...
```

### Effects

```lux
effect EffectName {
    fn operation1(param: Type): ReturnType
    fn operation2(): Type
}

// Example
effect Logger {
    fn log(level: String, message: String): Unit
    fn getLevel(): String
}
```

### Handlers

```lux
handler handlerName: EffectName {
    fn operation1(param) = {
        // implementation
        resume(value)
    }
}

// Example
handler consoleLogger: Logger {
    fn log(level, msg) = {
        Console.print("[" + level + "] " + msg)
        resume(())
    }
    fn getLevel() = resume("debug")
}
```

### Traits

```lux
trait TraitName {
    fn method(self): ReturnType
    fn method2(self, param: Type): ReturnType
}

impl TraitName for Type {
    fn method(self): ReturnType = ...
    fn method2(self, param: Type): ReturnType = ...
}
```

### Let Bindings

```lux
// Top-level
let name = value
let name: Type = value
pub let exported = value

// Local (in blocks)
let x = 42
let (a, b) = (1, 2)
```

## Expressions

### Literals

See Lexical Structure above.

### Variables

```lux
x
myVariable
Some
```

### Function Application

```lux
f(x)
f(x, y, z)
moduleName.function(arg)
```

### Operators

```lux
// Arithmetic
a + b    // Addition
a - b    // Subtraction
a * b    // Multiplication
a / b    // Division
a % b    // Remainder
-a       // Negation

// Comparison
a == b   // Equal
a != b   // Not equal
a < b    // Less than
a > b    // Greater than
a <= b   // Less or equal
a >= b   // Greater or equal

// Boolean
a && b   // And
a || b   // Or
!a       // Not

// String
s1 + s2  // Concatenation
```

### Conditionals

```lux
if condition then expr1 else expr2

if condition then
    expr1
else
    expr2

// Chained
if c1 then e1
else if c2 then e2
else e3
```

### Match Expressions

```lux
match value {
    pattern1 => expr1,
    pattern2 => expr2,
    _ => default
}

// With guards
match value {
    n if n > 0 => "positive",
    n if n < 0 => "negative",
    _ => "zero"
}

// Nested patterns
match expr {
    Add(Num(0), x) => x,
    Mul(x, Num(1)) => x,
    _ => expr
}
```

### Blocks

```lux
{
    statement1
    statement2
    result_expression
}

// Statements can be:
// - let bindings
// - expressions (for side effects)
```

### Lambda Expressions

```lux
fn(x: Type): ReturnType => body

// Examples
fn(x: Int): Int => x * 2
fn(a: Int, b: Int): Int => a + b
fn(): Unit => Console.print("hi")
```

### Run Expressions

```lux
run expr with {}

run expr with {
    Effect1 = handler1,
    Effect2 = handler2
}

// Example
run computation() with {
    Logger = consoleLogger,
    Database = mockDb
}
```

### Field Access

```lux
record.field
module.function
```

### Tuple Construction

```lux
(a, b)
(x, y, z)
```

### Record Construction

```lux
{ field1: value1, field2: value2 }

// Update
{ ...existing, field: newValue }
```

### List Construction

```lux
[]
[1, 2, 3]
[head, ...tail]
```

## Patterns

Used in match expressions and let bindings:

```lux
// Literal
42
"hello"
true

// Variable (binds the value)
x
name

// Wildcard (matches anything)
_

// Constructor
Some(x)
None
Pair(a, b)

// Tuple
(x, y)
(a, b, c)

// List
[]
[x]
[x, y]
[head, ...tail]

// Record
{ name, age }
{ name: n, age: a }

// With guard
x if x > 0
```

## Type Expressions

```lux
// Primitive
Int
Float
Bool
String
Char
Unit

// Named
TypeName
ModuleName.TypeName

// Generic application
Option<Int>
Result<String, Error>
List<T>

// Function
fn(Int): Int
fn(Int, String): Bool
fn(T): T with {Effect}

// Tuple
(Int, String)
(A, B, C)

// Record
{ x: Int, y: Int }
{ name: String, age: Int }

// List
List<Int>
```

## Modules

### Imports

```lux
// Full module
import path/to/module

// With alias
import path/to/module as alias

// Selective
import path/to/module.{item1, item2}

// Wildcard
import path/to/module.*
```

### Exports

```lux
// Public declarations
pub fn publicFunction(): Int = ...
pub type PublicType = ...
pub let publicValue = ...

// Private (default)
fn privateFunction(): Int = ...
```

## Grammar Summary

```
program      = import* declaration*

import       = 'import' path ('as' ident)?
             | 'import' path '.{' ident (',' ident)* '}'
             | 'import' path '.*'

declaration  = function | type | effect | handler | trait | impl | let

function     = 'pub'? 'fn' ident type_params? '(' params ')' ':' type
               ('with' '{' effects '}')? ('is' properties)?
               ('where' constraints)? '=' expr

type         = 'pub'? 'type' ident type_params? '=' type_def

effect       = 'effect' ident '{' operation* '}'

handler      = 'handler' ident ':' ident '{' impl* '}'

expr         = literal | ident | application | binary | unary
             | if | match | block | lambda | run | field

pattern      = literal | ident | '_' | constructor | tuple | list | record
```
