Crucible is a Rust interpreter for a PL/SQL-like block language. The goal is to stay close to the original PL/SQL model where practical while keeping the implementation small, testable, and easy to extend. It parses anonymous blocks, executes them against an in-memory database, and supports a growing subset of procedural SQL features including DML, transactions, cursors, and row-level triggers.
Recent changes are tracked in CHANGELOG.md.
- Added
BOOLas a type keyword and boolean runtime support. - Added double-quoted string literals.
- Added
DATEliteral syntax andSYSDATEinitialization that respects the declared target type. - Updated the REPL to print each evaluated statement inside a
BEGINblock. - Added procedures and functions with parameters, return types, and cross-block calls.
- Expanded query support to include
INNER,LEFT,RIGHT, andOUTERjoins with alias-aware name resolution.
- Anonymous PL/SQL-style blocks with optional
DECLARE, requiredBEGIN&END, and optionalEXCEPTIONsections. - Variable declarations, exception declarations, cursor declarations, and trigger declarations.
- Expressions with arithmetic, comparison, logical operators, numbers, and dotted field access.
- Control flow with
IF/ELSIF/ELSE,WHILE,LOOP, numericFOR, cursorFOR, andEXIT WHEN. - Exception handling with named handlers and
RAISE. - In-memory DML simulation for
SELECT INTO,INSERT,UPDATE, andDELETE. - In-memory table creation with
CREATE TABLE, stored in the current database snapshot. - In-memory schema changes with
ALTER TABLE ... ADD CONSTRAINTandDROP TABLE. - Transaction support with
COMMITandROLLBACK. - Cursor support with
CURSOR,OPEN,FETCH INTO,CLOSE, and cursor loops. - Row triggers with
BEFOREandAFTERtiming forINSERT,UPDATE, andDELETE. -
OLDandNEWpseudo-records inside trigger bodies, including the ability to mutateNEWinBEFOREtriggers. - Nested blocks and scoped execution.
- Package-level state and package bodies.
- Savepoints and more complete transactional control.
- Statement-level triggers and richer trigger conditions.
- Broader SQL support, including subqueries, aggregation, and set operations.
- Reading, parsing, and validating SQL files in later versions.
- File-backed schema and table persistence.
- Stronger type checking and explicit conversions closer to PL/SQL semantics.
- Benchmarking heavy queries with
criterion. - Multi-threading for parallel execution of queries with
rayon. - Async execution for I/O with
tokio.
DECLARE
TRIGGER boost_salary BEFORE INSERT ON employees
BEGIN
NEW.salary := NEW.salary + 50;
END;
BEGIN
INSERT INTO employees (id, name, salary) VALUES (3, 'Carol', 300);
END;In this example, the trigger adjusts the inserted row before it is committed to the table snapshot.
Start the interactive prompt with:
cargo runThe CLI will prompt for a PL/SQL block, then parse and execute it against a fresh in-memory environment.
Run the test suite with:
cargo testsrc/parserparses blocks, expressions, DML, cursors, transactions, and triggers.src/runtimeexecutes blocks, manages variables, handles DML, cursors, transactions, and triggers.src/dbcontains the in-memory database and table model.src/exprdefines runtime values and expression evaluation.testscontains integration tests that exercise the interpreter end to end.
This project is intentionally incremental, but the long-term direction is to remain recognizable to PL/SQL users instead of becoming a generic scripting language with SQL-like syntax.