1.7.0
November 4, 2025
Introduction
BoxLang 1.7.0 brings significant performance improvements, powerful new features for modern web development, and enhanced database capabilities. This release introduces Server-Sent Events (SSE) support for building real-time applications and AI agents, a new JDBC Cache Store for distributed caching, and bytecode compatibility versioning for improved module management. Performance optimizations across scheduled tasks, class loading, and ASM generation deliver faster execution, while over 40 bug fixes improve stability in file operations, HTTP handling, database queries, and CFML compatibility.
🚀 Major Highlights
🎯 Server-Sent Events (SSE)
New SSE() BIF and Emitter for web runtimes enables real-time server-to-client event streaming, perfect for building AI agents, live dashboards, progressive loading experiences, and real-time notifications. The implementation includes automatic keep-alive, CORS support, async execution, and graceful timeout handling.
Basic Usage:
// Simple synchronous streaming
SSE( ( emitter ) => {
emitter.send( "Hello from server!" );
emitter.send( { status: "processing", progress: 25 }, "update" );
emitter.close();
} );AI Streaming with Async Execution:
// Non-blocking AI response streaming
SSE(
callback: ( emitter ) => {
var response = callAIService();
while( !emitter.isClosed() && response.hasMoreTokens() ) {
emitter.send( response.getNextToken(), "token" );
}
emitter.send( { complete: true }, "done" );
},
async: true,
keepAliveInterval: 30000, // Send keep-alive every 30s
timeout: 300000 // Close after 5 minutes max
);Cross-Origin Streaming:
// Enable CORS for cross-domain requests
SSE(
callback: ( emitter ) => {
emitter.send( { message: "Hello from API" }, "greeting", 1 );
},
cors: "*" // or specific origin: "https://app.example.com"
);Available Parameters:
callback(required) - Closure/lambda that receives the emitter objectasync(default: false) - Run callback in background thread (non-blocking)retry(default: 0) - Client reconnect interval in millisecondskeepAliveInterval(default: 0) - Auto-send keep-alive comments intervaltimeout(default: 0) - Maximum execution time for async modecors(default: "") - CORS origin (* for all, or specific domain)
Emitter Methods:
send( data, [event], [id] )- Send SSE event (complex data auto-serialized to JSON)comment( text )- Send SSE comment for keep-aliveclose()- Gracefully close the streamisClosed()- Check if client disconnected
Implementation Features:
Automatic first-byte flush to establish connection quickly
Large data chunking (splits >32KB lines automatically)
Multi-line data support with proper SSE formatting
Client disconnect detection with graceful cleanup
Proxy/nginx buffering disabled for real-time delivery
🗄️ JDBC Cache Store
New distributed cache store backed by JDBC databases, enabling cache sharing across multiple BoxLang instances. Perfect for horizontal scaling scenarios where multiple application servers need to share cached data.
Basic Configuration:
// Configure JDBC cache store in boxlang.json
{
"caches": {
"distributedCache": {
"provider": "BoxCache",
"properties": {
"objectStore": "JDBCStore",
"datasource": "myDatasource",
"table": "boxlang_cache",
"autoCreate": true
}
}
}
}Advanced Configuration with Eviction:
{
"caches": {
"sharedCache": {
"provider": "BoxCache",
"properties": {
"objectStore": "JDBCStore",
"datasource": "prodDB",
"table": "app_cache",
"autoCreate": true,
// Standard BoxCache properties
"maxObjects": 1000,
"evictionPolicy": "LRU",
"evictCount": 100,
"defaultTimeout": 3600,
"defaultLastAccessTimeout": 1800,
"reapFrequency": 300
}
}
}
}Configuration Options:
datasource(required) - Name of the datasource to use for storagetable(default: "boxlang_cache") - Database table name for cache storageautoCreate(default: true) - Automatically create table and indexes if missingPlus all standard BoxCache properties (maxObjects, evictionPolicy, evictCount, etc.)
Supported Databases:
Oracle
MySQL / MariaDB
PostgreSQL
Microsoft SQL Server
Apache Derby
HSQLDB
SQLite
The implementation automatically detects the database vendor and generates optimized SQL for each platform, including proper handling of:
Database-specific data types (CLOB, TEXT, LONGTEXT, etc.)
Vendor-specific eviction queries (LIMIT, TOP, FETCH FIRST)
Index creation strategies
Transaction handling
Features:
Distributed: Mark as distributed store - cache data persists across instances
Automatic Schema Management: Creates table and indexes on first use
Serialization: Uses Base64-encoded object marshalling for complex types
Performance: Pre-compiled SQL statements for all operations
Eviction Support: Full support for LRU, LFU, and other eviction policies
Metadata Tracking: Stores hits, timeouts, and access timestamps
All cache stores now expose isDistributed() method for ecosystem tools to detect distribution capabilities.
🌳 BoxAST() - AST Generation
New BoxAST() BIF enables programmatic access to BoxLang's Abstract Syntax Tree (AST), perfect for building code analysis tools, linters, formatters, and code generation utilities. It supports parsing BoxLang script/template syntax as well as CFML/ColdFusion syntax for migration and compatibility tools.
// Parse BoxLang source code using BIF
ast = BoxAST( source: "x = 1 + 2; y = x * 3;" );
// Or use the convenient string member method
code = "function hello() { return 'world'; }";
ast = code.toAST();
// Parse from a file
ast = BoxAST( filepath: "myScript.bx" );
// Return as JSON for external tools
astJson = BoxAST(
source: "function hello() { return 'world'; }",
returnType: "json"
);
// Or with member method
astJson = "x = 1 + 2;".toAST( returnType: "json" );
// Return as text representation
astText = BoxAST(
filepath: "complex.bx",
returnType: "text"
);
// Parse BoxLang template syntax
templateAst = BoxAST(
source: "<bx:output>#now()#</bx:output>",
sourceType: "template"
);
// Parse CFML/ColdFusion script (for migration tools)
cfScriptAst = BoxAST(
source: "cfset x = 1; cfloop from='1' to='10' index='i' { writeOutput(i); }",
sourceType: "cfscript"
);
// Parse CFML/ColdFusion template (for migration tools)
cfTemplateAst = BoxAST(
source: "<cfset x = 1><cfoutput>#x#</cfoutput>",
sourceType: "cftemplate"
);Parameters:
source- BoxLang/CFML source code to parsefilepath- Path to file to parse (alternative to source)returnType- Output format: "struct" (default), "json", or "text"sourceType- Syntax type: "script" (default), "template", "cfscript", or "cftemplate"
Use Cases:
Code Analysis: Build custom linters and static analysis tools
Code Generation: Generate BoxLang code from templates or DSLs
Formatters: Create custom code formatting utilities
Documentation Generators: Extract function signatures and comments
Refactoring Tools: Analyze and transform code structures
IDE Tooling: Power syntax highlighting and code intelligence features
Migration Tools: Parse and analyze CFML code for BoxLang migration
🔧 Bytecode Compatibility Versioning
BoxLang now implements bytecode compatibility versioning, ensuring compiled classes remain compatible across runtime versions and improving module stability.
🤖 Core Runtime Updates
Performance Improvements
Scheduled Tasks: Significant performance boost by introducing non-concurrent maps for logging and closure suppliers
Static Initializers: Optimized execution of static class initializers
ASM Generation: Streamlined bytecode generation by eliminating disk-based class file operations
Cache Stores: Performance tuning across all cache store implementations
Enhanced Dumping
Renamed all
dump()member methods to.bxDump()to prevent conflicts with user-defined methodsImproved class dumping with better error handling for restricted Java fields
Fixed Java time type dumping (
java.sql.Time)Better handling of recursive class references in JSON serialization
Module System Enhancements
Added missing properties to
getModuleInfo()struct snapshotFixed module
publicMappingregistrationImproved IService lifecycle by ensuring
onConfigurationLoad()is called correctlyBetter validation of template URIs
HTTP Component Improvements
Added client certificate functionality support:
http url="https://secure-api.com" {
httpparam type="certificate" file="client-cert.p12" password="secret";
}Fixed double encoding of query parameters in HTTPParam
Better handling of
getAsBinary=nofor CFML compatibilityProper Optional unwrapping in HTTP result responses
📡 MiniServer Runtime Updates
Fixed rewrite file extension handling - no longer rewrites requests unnecessarily
Improved request body handling for empty payloads
Better error messages for empty request bodies
🤖 Servlet Runtime Updates
Fixed relative path resolution for mappings
Enabled
BOXLANG_DEBUGenvironment variable supportImproved session management - fixed jsessionid cookie handling to prevent AWS WAF issues
Better handling of in-progress
onApplicationStart()for concurrent requests
🥊 Developer Experience
Dynamic Object Creation
Enhanced createDynamicProxy() and createObject() to accept custom class loaders:
// Use custom class loader for dynamic object creation
customLoader = createObject( "java", "java.net.URLClassLoader" )
.init( [ url ] );
proxy = createDynamicProxy(
listener,
[ "com.example.Interface" ],
customLoader
);IStruct Convenience Method
New getAsChar() method on IStruct for convenient character extraction:
struct = { "code": "A" };
charValue = struct.getAsChar( "code" ); // Returns Character 'A'Configuration Improvements
JSON placeholders now applied immediately upon reading for consistent key replacement
Better handling of hyphens in pre-annotations to match post-annotation behavior
Fixed ignore of wildcard
*in valid template extensions when searching for Application descriptors
🐛 Notable Bug Fixes
Database & Stored Procedures
Fixed MSSQL connection issues when specifying
usernameandpasswordin cfqueryResolved multiple result set returns in CFStoredProc
Fixed stored procedure parameter errors and type casting for timestamps
Improved dynamic SQL type handling in CF transpiler
File Operations
Fixed
fileCopy()not respecting overwrite parameterCorrected file upload handling:
Files smaller than 10KB now properly stored on disk
Proper directory creation for absolute destination paths
Fixed template-relative destination path handling
Empty
allowargument now treated correctly
Fixed
getFileInfo()returning incorrect type string for directoriesResolved
expandPath()using wrong base path when Application.bx in different directory
List Operations
Fixed
listDeleteAt()incorrect behavior in both modesResolved appending null to list failures
Component & Class Handling
Better error messages for import statements in class bodies
Fixed class dump output showing keys twice instead of values
Improved loose struct converter error handling
Fixed duplicate() failures when encountering Optional types
Mail & Dates
Fixed
bx:mailcomponent string attribute handling for useSSL/useTLSResolved
dateConvert()errorsAdded handling for string dates with common masks
Path & Mapping
Normalized mapping paths with
../correctlyFixed CGI scope mapping returning null values
Improved abort exception handling (no longer caught inappropriately)
Dump Operations
Fixed
CFDUMPandWRITEDUMPfile output functionality
Windows Compatibility
Resolved Windows BoxLang REPL regression
🔧 Configuration Updates
No configuration changes required for this release. New features like SSE and JDBC cache store are opt-in and require explicit configuration.
⚡ Migration Notes
Breaking Changes
Dump Method Rename: All built-in member methods named dump() have been renamed to .bxDump() to avoid conflicts with user-defined methods. If you were calling .dump() on built-in objects, update to .bxDump():
// Old
array.dump();
// New
array.bxDump();Compatibility Improvements
Enhanced CFML compatibility for HTTP component behaviors
Better handling of empty file upload
allowparameterImproved stored procedure result set handling
More accurate CGI scope value mapping
🎶 Release Notes
Release notes - BoxLang - 1.7.0
Improvements
BL-1808 HTTP Component - Support Client Cert Functionality
BL-1818 allow hyphen in pre annotations to match post annotations
BL-1825 Performance improvement of all scheduled task calls by introducing non concurrent maps for logging and closure suppliers
BL-1830 Don't rewrite miniserver requests with rewrite file extension
BL-1836 Apply placeholders to JSON as soon as it's read to ensure all keys are replaced
BL-1838 Improve performance of running static initializer on class
BL-1839 Added missing properties to getModuleInfo() struct snapshot
BL-1846 Validate request URIs
BL-1848 Optimize ASM generation by not relying on disk class files
BL-1849 dump class improvements
BL-1853 Component annotation for ignoring ignore outpout only setting
BL-1855 Component annotation for auto-evaluating interpolated expressions
BL-1863 Rename all dump() member methods to be .bxDump() to avoid conflicts with actual methods named dump()
BL-1864 Catch Java access errors when getting Fields dynamically in class dump
BL-1865 Allow createDynamicProxy(), createObject() to accept a class loader
BL-1866 Ignore valid template extension setting of * when searching for Application descriptors
BL-1867 can't dump java.sql.Time
BL-1877 Performance tuning on cache stores
New Features
BL-1791 Implement bytecode compat version
BL-1861 New getAsChar() on IStruct for convenience
BL-1875 New JDBCStore for the Box Cache
BL-1876 Cache stores now have a isDistributed() interface method which allows cache providers and eco system to tell if the store can distribute content or be local only
BL-1880 New SSE() BIF and Emitter for Web Runtimes to allow for server side event streaming. Especially great when building AI Agents
BL-1883 New BoxAST() bif to help you return the AST of source or a filepath
Bugs
BL-1376 specifying `username` and `password` throws 'unable to open connection' in cfquery - mssql
BL-1685 CFStoredProc does not return multiple result sets when using a statement like an insert as first query
BL-1809 Servlet resolution of relative paths can return incorrect mapping
BL-1810 Prevent Double Encoding of Query Params passed by HTTParam
BL-1811 loose struct converter can error on getting public fields
BL-1812 Don't catch abort exceptions
BL-1814 appending null to list fails
BL-1815 listDeleteAt() is not working correctly on cfml compat mode or not
BL-1816 Stored Procedure errors out on missing parameter
BL-1817 FileCopy bif using overwrite is not using it.
BL-1820 mapping paths with ../ not always normalized
BL-1821 recursive class references cause stack overflow on JSON serialization
BL-1822 Compat: HTTP getAsBinary=no not always honored in other engines
BL-1823 Duplicate Fails When Encountering Optional
BL-1824 HTTP Component Returns Raw Optional for Result response When No Timeout is Specified
BL-1829 Module publicMapping is not being registered
BL-1831 dateConvert is throwing an error
BL-1833 bx:mail not handling string useSSL or useTLS attributes
BL-1834 CFDUMP and WRITEDUMP do not dump to a file
BL-1837 Instances of IService in BL Modules never call onConfigurationLoad
BL-1840 CF transpiler doesn't catch dynamic sql type on proc param
BL-1841 BOXLANG_DEBUG env var not used in servlet
BL-1842 Class dump doesn't output this scope values, just keys twice
BL-1845 subsequent requests do not respect in-progress onApplicationStart()
BL-1847 I am getting an error after server forget and server start
BL-1851 Better error for Import Statements in Class bodies
BL-1854 Web Compat: Empty `allow` argument to FileUpload is treated as "All" by other Engines
BL-1856 MiniServer Exchange GetRequestBody Method Throws Error when RequestBody Is Empty
BL-1857 GetFileInfo Returns Incorrect `type` string for Directory
BL-1858 File Uploads smaller than 10KB not being stored on disk
BL-1860 expandPath() uses wrong base path when application.xx is in different dir
BL-1870 stored proc param not casting timestamp
BL-1871 Regression Windows Boxlang REPL
BL-1872 FileUpload - When Temp directory is passed in explicitly in absolute destination path, directories should be created
BL-1873 FileUpload - Ensure correct handling for template relative destination paths
BL-1874 jsessionid cookie value set to null - breaks AWS WAF
BL-1878 Mapping CGI scope returns null values
BL-1879 Add handling for string dates as a common mask
Last updated
Was this helpful?
