Module Basics

Modules are the foundation of code organization in Simplex. They help you group related functionality, control visibility, and create reusable components.

math.sx
// Define a module with the 'module' keyword
module math {
    // Public function - accessible from outside
    pub fn add(a: i64, b: i64) -> i64 {
        a + b
    }

    pub fn multiply(a: i64, b: i64) -> i64 {
        a * b
    }

    // Private function - only accessible within this module
    fn internal_helper(x: i64) -> i64 {
        x * x
    }

    // Nested module
    pub module advanced {
        pub fn power(base: i64, exp: i64) -> i64 {
            if exp == 0 { 1 }
            else { base * power(base, exp - 1) }
        }
    }
}

Visibility Modifiers

Simplex provides fine-grained control over visibility with three levels:

visibility.sx
module mylib {
    // pub - Public: accessible from anywhere
    pub struct PublicConfig {
        pub name: String,
        pub version: String,
    }

    // private (default) - Only accessible within this module
    struct InternalState {
        counter: i64,
        cache: Map<String, Data>,
    }

    // pub(modulus) - Accessible within the same package only
    pub(modulus) fn package_internal() -> String {
        "This is only for other modules in this package"
    }

    pub struct User {
        pub name: String,           // Public field
        pub(modulus) id: i64,       // Package-internal field
        password_hash: String,     // Private field
    }
}

Visibility Levels

pub = public everywhere, pub(modulus) = visible within package, no modifier = private to module. Use the most restrictive visibility that works.

Import Syntax

Use the use keyword to import items from modules:

imports.sx
// Import a single item from a local module
use math::add
use math::advanced::power

// Import multiple items
use math::{add, multiply}

// Import all public items
use math::*

// Import with an alias
use math::multiply as mul

// Import from external packages (use modulus::)
use modulus::json::{parse, stringify}
use modulus::http::{Client, Request, Response}
use modulus::crypto::hash::sha256

fn main() {
    let sum = add(5, 3)
    let product = mul(4, 7)
    let result = power(2, 10)

    print("Sum: {sum}, Product: {product}, Power: {result}")
}

File-Based Modules

Each .sx file can be a module. The file name becomes the module name:

Project Structure
my_project/
  sxpm.toml
  src/
    main.sx           // Entry point
    utils.sx          // Module: utils
    models/
      mod.sx          // Module: models (directory module)
      user.sx         // Module: models::user
      product.sx      // Module: models::product
src/models/mod.sx
// Re-export submodules
pub module user
pub module product

// Common types for the models module
pub trait Model {
    fn id(&self) -> i64
    fn validate(&self) -> Result<(), ValidationError>
}
src/main.sx
use utils::format_date
use models::{Model, user::User, product::Product}

fn main() {
    let user = User::new("Alice", "alice@example.com")
    user.validate()?

    print("User ID: {user.id()}")
}

Creating a Project with sxpm

The sxpm (Simplex Package Manager) tool helps you create and manage projects:

Terminal
# Create a new binary project
$ sxpm new my_app
     Created binary (application) `my_app` package

# Create a new library project
$ sxpm new my_lib --lib
     Created library `my_lib` package

# Create with specific template
$ sxpm new web_api --template actix
     Created binary (application) `web_api` package

$ cd my_app
$ tree
.
├── sxpm.toml
├── src
│   └── main.sx
└── tests
    └── main_test.sx

Package Manifest (sxpm.toml)

The sxpm.toml file defines your package metadata and dependencies:

sxpm.toml
[package]
name = "my_app"
version = "0.1.0"
authors = ["Your Name <you@example.com>"]
edition = "2024"
description = "A sample Simplex application"
license = "MIT"
repository = "https://github.com/username/my_app"
keywords = ["web", "api", "simplex"]

[dependencies]
http = "1.2.0"
json = "2.0.1"
crypto = { version = "1.0", features = ["aes", "rsa"] }

[dev-dependencies]
test_utils = "0.5.0"
mock_server = "1.1.0"

[build]
target = "native"           # or "wasm", "llvm"
optimization = "release"    # or "debug"

[features]
default = ["json"]
full = ["json", "xml", "yaml"]
experimental = []

Managing Dependencies

Add, remove, and update dependencies with sxpm:

Terminal
# Add a dependency
$ sxpm add http
    Adding http v1.2.0 to dependencies

# Add with specific version
$ sxpm add json@2.0.1
    Adding json v2.0.1 to dependencies

# Add with features
$ sxpm add crypto --features aes,rsa
    Adding crypto v1.0.0 to dependencies

# Add a dev dependency
$ sxpm add --dev test_utils
    Adding test_utils v0.5.0 to dev-dependencies

# Add from git repository
$ sxpm add mylib --git https://github.com/user/mylib
    Adding mylib (git) to dependencies

# Remove a dependency
$ sxpm remove json
    Removing json from dependencies

# Update dependencies
$ sxpm update
    Updating http v1.2.0 -> v1.3.0
    Updating crypto v1.0.0 -> v1.0.2

# List dependencies
$ sxpm list
my_app v0.1.0
├── http v1.3.0
├── json v2.0.1
└── crypto v1.0.2
    └── rand v0.8.0

Building and Testing

Build, run, and test your project with sxpm:

Terminal
# Build the project
$ sxpm build
   Compiling my_app v0.1.0
    Finished dev [unoptimized + debuginfo] in 0.42s

# Build for release
$ sxpm build --release
   Compiling my_app v0.1.0
    Finished release [optimized] in 1.23s

# Run the project
$ sxpm run
   Compiling my_app v0.1.0
    Finished dev in 0.38s
     Running `target/debug/my_app`
Hello, Simplex!

# Run with arguments
$ sxpm run -- --port 8080 --verbose

# Run tests
$ sxpm test
   Compiling my_app v0.1.0
    Finished test in 0.56s
     Running tests/main_test.sx

running 4 tests
test test_add ... ok
test test_multiply ... ok
test test_async_fetch ... ok
test test_error_handling ... ok

test result: ok. 4 passed; 0 failed; 0 ignored

# Run specific tests
$ sxpm test test_add
$ sxpm test --filter "async"

# Check for errors without building
$ sxpm check
    Checking my_app v0.1.0
    Finished dev in 0.15s
tests/main_test.sx
use modulus::test::{assert, assert_eq, assert_err}
use my_app::{add, multiply, fetch_data}

#[test]
fn test_add() {
    assert_eq(add(2, 3), 5)
    assert_eq(add(-1, 1), 0)
}

#[test]
fn test_multiply() {
    assert_eq(multiply(4, 5), 20)
}

#[test]
#[async]
fn test_async_fetch() {
    let result = await fetch_data("test_id")
    assert(result.is_ok())
}

#[test]
#[should_panic]
fn test_panic_case() {
    divide(10, 0)  // Should panic
}

Publishing Packages

Share your code with the Simplex community by publishing to the registry:

Terminal
# Login to the registry
$ sxpm login
Enter API token: ********
     Login successful for user@example.com

# Verify package before publishing
$ sxpm publish --dry-run
   Packaging my_lib v0.1.0
   Verifying my_lib v0.1.0
   Compiling my_lib v0.1.0
    Finished dev in 0.34s
     Packaged 12 files, 45.2KB total
     Ready to publish (dry run)

# Publish the package
$ sxpm publish
   Packaging my_lib v0.1.0
   Uploading my_lib v0.1.0
   Published my_lib v0.1.0 to simplex-registry

# Yank a version (remove from registry)
$ sxpm yank my_lib@0.1.0
    Yanking my_lib v0.1.0

# Search for packages
$ sxpm search json parser
json v2.0.1 - Fast JSON parsing and serialization
json-stream v1.0.0 - Streaming JSON parser
json-schema v0.8.0 - JSON Schema validation

Publishing Checklist

Before publishing: update version in sxpm.toml, write documentation, add a LICENSE file, ensure all tests pass, and review your package with sxpm publish --dry-run.

Standard Library Modules

Simplex comes with a comprehensive standard library. Here are the key modules:

Standard Library Overview
// CLI - Command line argument parsing and terminal I/O
use modulus::cli::{Args, Command, prompt, style}

let args = Args::parse()
let name = prompt("Enter your name: ")
print(style("Success!").green().bold())

// HTTP - Client and server functionality
use modulus::http::{Client, Server, Request, Response, StatusCode}

let client = Client::new()
let response = await client.get("https://api.example.com/data")

// JSON - Parsing and serialization
use modulus::json::{parse, stringify, Value}

let data: Value = parse("{\"name\": \"Alice\"}")?
let json_str = stringify(&my_struct)

// File System - File and directory operations
use modulus::fs::{read_file, write_file, exists, create_dir}

let content = await read_file("config.toml")?
await write_file("output.txt", data)?

// Collections - Advanced data structures
use modulus::collections::{HashMap, HashSet, BTreeMap, VecDeque}

let cache: HashMap<String, Data> = HashMap::new()

// Crypto - Cryptographic functions
use modulus::crypto::{hash, encrypt, decrypt, random}

let hashed = hash::sha256(data)
let token = random::bytes(32)

// Time - Date and time handling
use modulus::time::{DateTime, Duration, Instant}

let now = DateTime::now()
let timeout = Duration::seconds(30)

// Regex - Regular expressions
use modulus::regex::{Regex, Match}

let pattern = Regex::new(r"\d{3}-\d{4}")?
let matches = pattern.find_all(text)

// Async - Async utilities
use modulus::async::{spawn, sleep, timeout, parallel, select}

// AI - Built-in AI capabilities
use modulus::ai::{Model, prompt, embed}

Try It Yourself

Create a reusable library package:

  1. Use sxpm new myutils --lib to create a library
  2. Create modules for string utilities and math helpers
  3. Export public functions with proper visibility
  4. Write tests for all public functions
  5. Document your API with comments
  6. Try publishing with sxpm publish --dry-run

Summary

In this tutorial, you learned:

  • Defining modules with the module keyword
  • Controlling visibility with pub, private, and pub(modulus)
  • Importing items with use and external packages with modulus::
  • Organizing code with file-based modules
  • Creating projects with sxpm new
  • Configuring packages with sxpm.toml
  • Managing dependencies with sxpm add/remove/update
  • Building and testing with sxpm build/test
  • Publishing packages to the registry
  • Using standard library modules

Congratulations!

You have completed all 10 Simplex tutorials! You now have a solid foundation in the language, from basic syntax to advanced features like actors, AI integration, async programming, and the module system. You are ready to build real-world applications with Simplex. Happy coding!