Skip to content

Commit ecb1b54

Browse files
committed
fix: Fix potential SQL injection errors
1 parent 28af010 commit ecb1b54

1 file changed

Lines changed: 22 additions & 2 deletions

File tree

native/ecto_libsql/src/lib.rs

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1670,6 +1670,16 @@ fn release_savepoint(trx_id: &str, name: &str) -> NifResult<Atom> {
16701670
.get_mut(trx_id)
16711671
.ok_or_else(|| rustler::Error::Term(Box::new("Transaction not found")))?;
16721672

1673+
// Validate savepoint name is a valid SQL identifier (alphanumeric + underscore, not starting with digit)
1674+
if name.is_empty()
1675+
|| !name.chars().all(|c| c.is_alphanumeric() || c == '_')
1676+
|| name.chars().next().map_or(true, |c| c.is_ascii_digit())
1677+
{
1678+
return Err(rustler::Error::Term(Box::new(
1679+
"Invalid savepoint name: must be a valid SQL identifier",
1680+
)));
1681+
}
1682+
16731683
let sql = format!("RELEASE SAVEPOINT {}", name);
16741684

16751685
TOKIO_RUNTIME
@@ -1689,6 +1699,16 @@ fn rollback_to_savepoint(trx_id: &str, name: &str) -> NifResult<Atom> {
16891699
.get_mut(trx_id)
16901700
.ok_or_else(|| rustler::Error::Term(Box::new("Transaction not found")))?;
16911701

1702+
// Validate savepoint name is a valid SQL identifier (alphanumeric + underscore, not starting with digit)
1703+
if name.is_empty()
1704+
|| !name.chars().all(|c| c.is_alphanumeric() || c == '_')
1705+
|| name.chars().next().map_or(true, |c| c.is_ascii_digit())
1706+
{
1707+
return Err(rustler::Error::Term(Box::new(
1708+
"Invalid savepoint name: must be a valid SQL identifier",
1709+
)));
1710+
}
1711+
16921712
let sql = format!("ROLLBACK TO SAVEPOINT {}", name);
16931713

16941714
TOKIO_RUNTIME
@@ -1701,8 +1721,8 @@ fn rollback_to_savepoint(trx_id: &str, name: &str) -> NifResult<Atom> {
17011721
}
17021722

17031723
/// Get the current frame number from a remote replica database.
1704-
/// Returns 0 if not a replica or frame number unknown.
1705-
/// Note: libsql 0.9.27 doesn't expose frame number API yet
1724+
/// **Note**: This is currently a placeholder - libsql 0.9.27 doesn't expose the frame number API.
1725+
/// Always returns 0. Will be implemented when the upstream API becomes available.
17061726
#[rustler::nif(schedule = "DirtyIo")]
17071727
fn get_frame_number(conn_id: &str) -> NifResult<u64> {
17081728
let conn_map = safe_lock(&CONNECTION_REGISTRY, "get_frame_number conn_map")?;

0 commit comments

Comments
 (0)