Expand description
Path manipulation module.
Most functions are pure computation with no I/O.
Exception: absolute performs filesystem access (symlink resolution
via canonicalize) and is subject to the active
PathPolicy.
§absolute and sandboxed mode
path.absolute(p) internally calls std::fs::canonicalize, which
resolves symlinks and returns an absolute path. This is not
available in Sandboxed mode.
§Why it doesn’t work
[cap_std::fs::Dir] does have a canonicalize method, but it
returns a relative path (relative to the Dir handle) because
absolute paths break the capability model. path.absolute promises
callers an absolute path, and FsAccess
does not hold the sandbox root path, so there is no way to convert
cap_std’s relative result back to an absolute path.
Ref: https://docs.rs/cap-std/4.0.2/cap_std/fs/struct.Dir.html#method.canonicalize
§Workaround for sandboxed environments
Use the pure-computation functions that require no filesystem access:
-- Check if already absolute
if not path.is_absolute(p) then
-- Build absolute path from a known base
p = path.join(base_dir, p)
end§Future: std::path::absolute (Rust 1.79+)
std::path::absolute (stabilized in Rust 1.79.0) makes a path
absolute without filesystem access — it does not resolve symlinks
and works even if the path does not exist. Migrating to this
function would allow path.absolute to work in sandboxed mode,
but changes the semantics (symlinks would no longer be resolved).
Ref: https://doc.rust-lang.org/std/path/fn.absolute.html Ref: https://github.com/rust-lang/rust/pull/124335
§Encoding — UTF-8 only (by design)
All path arguments are received as Rust String (UTF-8).
Non-UTF-8 Lua strings are rejected at the FromLua boundary
with FromLuaConversionError. Returned paths use
to_string_lossy,
replacing any non-UTF-8 bytes with U+FFFD.
Raw byte (OsStr) round-tripping is intentionally unsupported.
mlua’s FromLua for String enforces UTF-8 validation before
handler code runs, so supporting raw bytes would require every
function to accept mlua::String + as_bytes() and return
via OsStr::as_bytes(). The added complexity is not justified
given the rarity of non-UTF-8 filenames on modern systems.
Ref: https://docs.rs/mlua/latest/mlua/struct.String.html
local path = std.path
local p = path.join("/usr", "local", "bin")
local dir = path.parent("/usr/local/bin/foo")
local name = path.filename("/usr/local/config.toml")
local base = path.stem("/usr/local/config.toml")
local ext = path.ext("/usr/local/config.toml")