aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/main.zig75
1 files changed, 52 insertions, 23 deletions
diff --git a/src/main.zig b/src/main.zig
index 773dad8..fd2aa5c 100644
--- a/src/main.zig
+++ b/src/main.zig
@@ -114,33 +114,56 @@ pub fn main() !void {
// Download all the required files
- var root_dir = try get_minecraft_root_dir(allocator);
- defer root_dir.close();
- try download_version(allocator, &client, &root_dir, release_version);
- // std.mem.replace(comptime T: type, input: []const T, needle: []const T, replacement: []const T, output: []T)
-
- // check the latest.release
- // find that in the versions[] by key id
- // get the download URL for that https://piston-meta.mojang.com/v1/packages/1f376e6cb981265af345076889f9ef325bb6b9e8/1.20.1.json
-
- // get arguments.game and arguments.jvm ready to supply ...
- // probably just use the system java version for now
- //
+ var root_dir_path = try get_minecraft_root_dir(allocator);
+ defer allocator.free(root_dir_path);
+ // try download_version(allocator, &client, root_dir_path, release_version);
+ try play_version(allocator, root_dir_path, release_version);
}
-fn download_version(allocator: std.mem.Allocator, client: *HttpClient, root_dir: *const std.fs.Dir, version: Version) !void {
- const dir_path = try std.fs.path.join(allocator, &[_][]const u8{"versions", version.id});
+fn play_version(allocator: std.mem.Allocator, root_dir_path: []const u8, version: Version) !void {
+ // version dir
+ const dir_path = try version.dir_path(allocator, root_dir_path);
defer allocator.free(dir_path);
+ var dir = try std.fs.openDirAbsolute(dir_path, .{});
+ defer dir.close();
+ var cmd_buf = std.ArrayList([]const u8).init(allocator);
+ try cmd_buf.append("java");
+ try cmd_buf.append("-cp");
+ try cmd_buf.append("*");
+ // try cmd_buf.append(version.mainClass);
+ try cmd_buf.append("net.minecraft.client.main.Main");
+ try cmd_buf.append("-accessToken=foo");
+ try cmd_buf.append("-version=1.20.1");
+ const cmd = try cmd_buf.toOwnedSlice();
+ defer allocator.free(cmd);
+ const cmd_log = try std.mem.join(allocator, " ", cmd);
+ defer allocator.free(cmd_log);
+ log.info("running minecraft cmd [{s}] in cwd {s}", .{cmd_log, dir_path});
+ var proc = std.ChildProcess.init(cmd, allocator);
+ proc.stdin_behavior = .Ignore;
+ proc.cwd = dir_path;
+ proc.cwd_dir = null;
+ proc.env_map = null;
+ proc.expand_arg0 = .no_expand;
+ _ = try proc.spawnAndWait();
+}
+
+fn download_version(allocator: std.mem.Allocator, client: *HttpClient, root_dir_path: []const u8, version: Version) !void {
+ const dir_path = try version.dir_path(allocator, root_dir_path);
+ defer allocator.free(dir_path);
+ std.fs.makeDirAbsolute(dir_path) catch |e| switch (e) {
+ error.PathAlreadyExists => {}, // fine, swallow the error
+ else => return e,
+ };
log.info("downloading version {s} to {s}", .{version.id, dir_path});
- try root_dir.makePath(dir_path);
- const dir = try root_dir.openDir(dir_path, .{});
+ const dir = try std.fs.openDirAbsolute(dir_path, .{});
var client_jar = try dir.createFile("client.jar", .{});
defer client_jar.close();
try download_file(client, &client_jar, version.downloads.client.url);
var client_map = try dir.createFile("client.map", .{});
defer client_map.close();
- try download_file(client, &client_jar, version.downloads.client_mappings.url);
+ try download_file(client, &client_map, version.downloads.client_mappings.url);
// TODO server
// Dependencies...
@@ -334,6 +357,11 @@ const Version = struct {
releaseTime: []const u8,
time: []const u8,
type: []const u8,
+
+ /// Caller must free the result
+ fn dir_path(self: Version, allocator: std.mem.Allocator, root_dir_path: []const u8) ![]const u8 {
+ return try std.fs.path.join(allocator, &[_][]const u8{root_dir_path, "versions", self.id});
+ }
};
@@ -360,20 +388,21 @@ fn download_json(client: *HttpClient, comptime T: type, url: []const u8) !std.js
return res;
}
-fn get_minecraft_root_dir(allocator: std.mem.Allocator) !std.fs.Dir {
+/// Root of minecraft data directory.
+/// Calling ensures the directory exists.
+/// Caller owns the result and must free it
+fn get_minecraft_root_dir(allocator: std.mem.Allocator) ![]const u8 {
const home_dir = std.os.getenv("HOME") orelse {
return error.AppDataDirUnavailable;
};
const root_dir_path = try std.fs.path.join(allocator, &[_][]const u8{home_dir, ".minecraft"});
- defer allocator.free(root_dir_path);
- const root_dir = std.fs.openDirAbsolute(root_dir_path, .{}) catch |e| switch (e) {
- error.FileNotFound => blk: {
+ _ = std.fs.openDirAbsolute(root_dir_path, .{}) catch |e| switch (e) {
+ error.FileNotFound => {
try std.fs.makeDirAbsolute(root_dir_path);
- break :blk try std.fs.openDirAbsolute(root_dir_path, .{});
},
else => return e,
};
- return root_dir;
+ return root_dir_path;
}
test "heterogenous array" {