relativePosix
Function parameters
Parameters
Type definitions in this namespace
Types
Returns if the given byte is a valid path separator
Functions
- isSep
- Returns if the given byte is a valid path separator
- join
- Naively combines a series of paths with the native path separator.
- joinZ
- Naively combines a series of paths with the native path separator and null terminator.
- resolve
- On Windows, this calls `resolveWindows` and on POSIX it calls `resolvePosix`.
- resolveWindows
- This function is like a series of `cd` statements executed one after another.
- resolvePosix
- This function is like a series of `cd` statements executed one after another.
- dirname
- Strip the last component from a file path.
- relative
- Returns the relative path from `from` to `to`.
- extension
- Searches for a file extension separated by a `.` and returns the string after that `.`.
- stem
- Returns the last component of this path without its extension (if any):
- ComponentIterator
- A path component iterator that can move forwards and backwards.
- fmtAsUtf8Lossy
- Format a path encoded as bytes for display as UTF-8.
- fmtWtf16LeAsUtf8Lossy
- Format a path encoded as WTF-16 LE for display as UTF-8.
= '\\'
Values
- sep_windows
- = '\\'
- sep_posix
- = '/'
- sep
- = switch (native_os) { .windows, .uefi => sep_windows, else => sep_posix, }
- sep_str_windows
- = "\\"
- sep_str_posix
- = "/"
- sep_str
- = switch (native_os) { .windows, .uefi => sep_str_windows, else => sep_str_posix, }
- delimiter_windows
- = ';'
- delimiter_posix
- = ':'
- delimiter
- = if (native_os == .windows) delimiter_windows else delimiter_posix
Source
Implementation
pub fn relativePosix(allocator: Allocator, from: []const u8, to: []const u8) ![]u8 {
const cwd = try process.getCwdAlloc(allocator);
defer allocator.free(cwd);
const resolved_from = try resolvePosix(allocator, &[_][]const u8{ cwd, from });
defer allocator.free(resolved_from);
const resolved_to = try resolvePosix(allocator, &[_][]const u8{ cwd, to });
defer allocator.free(resolved_to);
var from_it = mem.tokenizeScalar(u8, resolved_from, '/');
var to_it = mem.tokenizeScalar(u8, resolved_to, '/');
while (true) {
const from_component = from_it.next() orelse return allocator.dupe(u8, to_it.rest());
const to_rest = to_it.rest();
if (to_it.next()) |to_component| {
if (mem.eql(u8, from_component, to_component))
continue;
}
var up_count: usize = 1;
while (from_it.next()) |_| {
up_count += 1;
}
const up_index_end = up_count * "../".len;
const result = try allocator.alloc(u8, up_index_end + to_rest.len);
errdefer allocator.free(result);
var result_index: usize = 0;
while (result_index < up_index_end) {
result[result_index..][0..3].* = "../".*;
result_index += 3;
}
if (to_rest.len == 0) {
// shave off the trailing slash
return allocator.realloc(result, result_index - 1);
}
@memcpy(result[result_index..][0..to_rest.len], to_rest);
return result;
}
return [_]u8{};
}