Emil Lerch
a8a560a480
All checks were successful
Generic zig build / build (push) Successful in 1m6s
56 lines
2.5 KiB
Zig
56 lines
2.5 KiB
Zig
const std = @import("std");
|
|
|
|
specified_region: ?[]const u8,
|
|
allocator: std.mem.Allocator,
|
|
/// internal state, please do not use
|
|
_calculated_region: ?[]const u8 = null,
|
|
const Region = @This();
|
|
pub fn region(self: *Region) ![]const u8 {
|
|
if (self.specified_region) |r| return r; // user specified
|
|
if (self._calculated_region) |r| return r; // cached
|
|
self._calculated_region = try findRegionFromSystem(self.allocator);
|
|
return self._calculated_region.?;
|
|
}
|
|
|
|
// AWS_CONFIG_FILE (default is ~/.aws/config
|
|
// AWS_DEFAULT_REGION
|
|
fn findRegionFromSystem(allocator: std.mem.Allocator) ![]const u8 {
|
|
const env_map = try std.process.getEnvMap(allocator);
|
|
if (env_map.get("AWS_DEFAULT_REGION")) |r| return r;
|
|
const config_file_path = env_map.get("AWS_CONFIG_FILE") orelse
|
|
try std.fs.path.join(allocator, &[_][]const u8{
|
|
env_map.get("HOME") orelse env_map.get("USERPROFILE").?,
|
|
".aws",
|
|
"config",
|
|
});
|
|
const config_file = try std.fs.openFileAbsolute(config_file_path, .{});
|
|
defer config_file.close();
|
|
const config_bytes = try config_file.readToEndAlloc(allocator, 1024 * 1024);
|
|
const profile = env_map.get("AWS_PROFILE") orelse "default";
|
|
var line_iterator = std.mem.split(u8, config_bytes, "\n");
|
|
var in_profile = false;
|
|
while (line_iterator.next()) |line| {
|
|
const trimmed = std.mem.trim(u8, line, " \t\r");
|
|
if (trimmed.len == 0 or trimmed[0] == '#') continue;
|
|
if (!in_profile) {
|
|
if (trimmed[0] == '[' and trimmed[trimmed.len - 1] == ']') {
|
|
// this is a profile directive!
|
|
// std.debug.print("profile: {s}, in file: {s}\n", .{ profile, trimmed[1 .. trimmed.len - 1] });
|
|
if (std.mem.eql(u8, profile, trimmed[1 .. trimmed.len - 1])) {
|
|
in_profile = true;
|
|
}
|
|
}
|
|
continue; // we're only looking for a profile at this point
|
|
}
|
|
// look for our region directive
|
|
if (trimmed[0] == '[' and trimmed[trimmed.len - 1] == ']')
|
|
return error.RegionNotFound; // we've hit another profile without getting our region
|
|
if (!std.mem.startsWith(u8, trimmed, "region")) continue;
|
|
var equalityiterator = std.mem.split(u8, trimmed, "=");
|
|
_ = equalityiterator.next() orelse return error.RegionNotFound;
|
|
const raw_val = equalityiterator.next() orelse return error.RegionNotFound;
|
|
return try allocator.dupe(u8, std.mem.trimLeft(u8, raw_val, " \t"));
|
|
}
|
|
return error.RegionNotFound;
|
|
}
|