Rework commands and add commands to interact with JGit

This commit is contained in:
Johannes Frohnmeyer 2022-01-04 17:48:01 +01:00
parent a577f5676f
commit 53ad3673d4
Signed by: Johannes
GPG Key ID: E76429612C2929F4
23 changed files with 651 additions and 143 deletions

View File

@ -2,7 +2,8 @@ package io.gitlab.jfronny.inceptum;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import io.gitlab.jfronny.inceptum.cli.InvokedCommandDescription;
import io.gitlab.jfronny.inceptum.cli.CommandResolution;
import io.gitlab.jfronny.inceptum.cli.Commands;
import io.gitlab.jfronny.inceptum.gson.*;
import io.gitlab.jfronny.inceptum.model.ComparableVersion;
import io.gitlab.jfronny.inceptum.model.inceptum.Config;
@ -51,9 +52,9 @@ public class Inceptum {
public static Config CONFIG;
public static boolean IS_GUI;
public static void main(String[] _args) throws Exception {
InvokedCommandDescription arg = new InvokedCommandDescription(_args);
if (arg.command.enableLog()) {
public static void main(String[] args) throws Exception {
CommandResolution command = Commands.resolve(args, false);
if (command.command().enableLog()) {
LOGGER.info("Launching Inceptum v" + MetaHolder.VERSION.version + " (" + MetaHolder.VERSION.flavor + ")");
LOGGER.info("Loading from " + MetaHolder.BASE_PATH);
}
@ -92,7 +93,7 @@ public class Inceptum {
});
}
arg.command.invoke(arg);
command.invoke();
}
public static void saveConfig() {

View File

@ -5,7 +5,7 @@ import imgui.ImGuiIO;
import imgui.flag.ImGuiConfigFlags;
import imgui.gl3.ImGuiImplGl3;
import imgui.glfw.ImGuiImplGlfw;
import io.gitlab.jfronny.inceptum.cli.InvokedCommandDescription;
import io.gitlab.jfronny.inceptum.cli.CommandArgs;
import io.gitlab.jfronny.inceptum.util.api.account.AccountManager;
import io.gitlab.jfronny.inceptum.windows.Window;
import org.lwjgl.glfw.Callbacks;
@ -34,7 +34,7 @@ public class InceptumGui {
protected static long handle;
private static String glslVersion = null;
public static void main(InvokedCommandDescription args, Runnable exec) {
public static void main(CommandArgs args, Runnable exec) {
AccountManager.loadAccounts();
Inceptum.LOGGER.info("Initializing UI");
init();

View File

@ -1,16 +1,20 @@
package io.gitlab.jfronny.inceptum.cli;
import java.util.Arrays;
import java.util.List;
import java.util.Locale;
import java.util.*;
public abstract class Command {
private final String help;
private final List<String> aliases;
private final Collection<Command> subCommands;
public Command(String help, String... aliases) {
this(help, Arrays.asList(aliases), List.of());
}
public Command(String help, List<String> aliases, List<Command> subCommands) {
this.help = help;
this.aliases = Arrays.asList(aliases);
this.aliases = List.copyOf(aliases);
this.subCommands = List.copyOf(subCommands);
}
public boolean isAlias(String text) {
@ -21,13 +25,32 @@ public abstract class Command {
return aliases.get(0);
}
public String getHelp() {
return help;
}
public boolean enableLog() {
return false;
}
public abstract void invoke(InvokedCommandDescription args);
protected abstract void invoke(CommandArgs args);
public CommandResolution resolve(CommandArgs args) {
if (args.length != 0) {
for (Command command : subCommands) {
if (command.isAlias(args.get(0))) {
CommandResolution resolution = command.resolve(args.subArgs());
if (!aliases.isEmpty())
resolution.resolvePath().add(0, aliases.get(0));
return resolution;
}
}
}
return new CommandResolution(this, args, aliases.isEmpty()
? new ArrayList<>()
: new ArrayList<>(List.of(aliases.get(0))));
}
public void buildHelp(HelpBuilder builder) {
builder.writeCommand(aliases, help);
for (Command command : subCommands) {
command.buildHelp(builder.beginSubcommand());
}
}
}

View File

@ -0,0 +1,59 @@
package io.gitlab.jfronny.inceptum.cli;
import java.util.*;
public class CommandArgs implements Iterable<String> {
protected final List<String> args;
public final int length;
public final boolean wrapped;
public CommandArgs(List<String> args, boolean wrapped) {
this.args = List.copyOf(args);
this.length = args.size();
this.wrapped = wrapped;
}
public boolean contains(String param) {
return args.contains(param.replaceAll("^[-/]*", "").toLowerCase(Locale.ROOT));
}
public String last() {
return args.get(args.size() - 1);
}
public String get(int index) {
return args.get(index);
}
public List<String> after(String param) {
List<String> yes = null;
for (String arg : args) {
if (yes != null)
yes.add(arg);
else if (arg.equals(param.replaceAll("^[-/]*", "").toLowerCase(Locale.ROOT)))
yes = new ArrayList<>();
}
return yes;
}
public List<String> after(int index) {
return index + 1 < length ? args.subList(index + 1, length) : new ArrayList<>();
}
public List<String> getArgs() {
return args;
}
@Override
public Iterator<String> iterator() {
return args.iterator();
}
public CommandArgs subArgs() {
return subArgs(wrapped);
}
public CommandArgs subArgs(boolean wrapped) {
return new CommandArgs(args.subList(1, args.size()), wrapped);
}
}

View File

@ -0,0 +1,9 @@
package io.gitlab.jfronny.inceptum.cli;
import java.util.List;
public record CommandResolution(Command command, CommandArgs args, List<String> resolvePath) {
public void invoke() {
command.invoke(args);
}
}

View File

@ -0,0 +1,37 @@
package io.gitlab.jfronny.inceptum.cli;
import io.gitlab.jfronny.inceptum.cli.commands.*;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class Commands {
private static final GuiCommand GUI_COMMAND = new GuiCommand();
public static final Command COMMANDS_ROOT = new Command("", List.of(), List.of(
new HelpCommand(),
GUI_COMMAND,
new LaunchCommand(),
new ListCommand(),
new GitCommand(),
new UpdateCheckCommand(),
new JvmStateCommand(),
new BatchCommand(),
new WrapperCommand()
)) {
@Override
protected void invoke(CommandArgs args) {
throw new RuntimeException("Could not find command: " + args.get(0));
}
@Override
public CommandResolution resolve(CommandArgs args) {
if (args.length == 0) return new CommandResolution(GUI_COMMAND, args, new ArrayList<>());
return super.resolve(args);
}
};
public static CommandResolution resolve(String[] args, boolean wrapped) {
return COMMANDS_ROOT.resolve(new CommandArgs(Arrays.asList(args), wrapped));
}
}

View File

@ -0,0 +1,45 @@
package io.gitlab.jfronny.inceptum.cli;
import java.util.List;
public class HelpBuilder {
private final boolean skip;
private final StringBuilder builder;
private final int level;
public HelpBuilder(boolean skipFirst) {
this.skip = skipFirst;
this.builder = new StringBuilder();
this.level = 0;
}
private HelpBuilder(int level, StringBuilder builder) {
this.skip = false;
this.builder = builder;
this.level = level;
}
public String getResult() {
return builder.length() > 0 ? builder.substring(1) : "";
}
public HelpBuilder beginSubcommand() {
return new HelpBuilder(skip ? level : level + 1, builder);
}
public void writeCommand(List<String> aliases, String help) {
if (skip) return;
builder.append('\n');
String indent = " ".repeat(level * 4);
builder.append(indent);
builder.append("- ");
for (int i = 0, aliasesSize = aliases.size(); i < aliasesSize; i++) {
String alias = aliases.get(i);
builder.append(alias);
if (i < aliasesSize - 1)
builder.append(", ");
}
builder.append(": ");
builder.append(help.replace("\n", "\n " + indent));
}
}

View File

@ -1,16 +0,0 @@
package io.gitlab.jfronny.inceptum.cli;
import io.gitlab.jfronny.inceptum.util.MetaHolder;
public class HelpCommand extends Command {
public HelpCommand() {
super("Displays this screen", "help");
}
@Override
public void invoke(InvokedCommandDescription args) {
System.out.println("Inceptum v" + MetaHolder.VERSION.version + " (" + MetaHolder.VERSION.flavor + ")\n\nCommands:");
for (Command command : InvokedCommandDescription.COMMANDS) {
System.out.println(" " + command.getName() + " - " + command.getHelp());
}
}
}

View File

@ -1,64 +0,0 @@
package io.gitlab.jfronny.inceptum.cli;
import java.util.*;
public class InvokedCommandDescription implements Iterable<String> {
public static final Set<Command> COMMANDS = Set.of(new HelpCommand(), new GuiCommand(), new LaunchCommand(), new UpdateCheckCommand(), new JvmStateCommand(), new BatchCommand());
private final List<String> args;
public final int length;
public final boolean wrapped;
public final Command command;
public InvokedCommandDescription(String[] args) throws Exception {
if (args.length == 0) args = new String[]{"gui"};
wrapped = args[0].equals("wrapper");
if (wrapped && args.length == 1) args = new String[] {"wrapper", "gui"};
{
String cmdSel = wrapped ? args[1] : args[0];
Command cmd = null;
for (Command command : COMMANDS) {
if (command.isAlias(cmdSel)) {
cmd = command;
break;
}
}
if (cmd == null) {
throw new Exception("Command not found: " + cmdSel);
}
command = cmd;
}
this.args = Arrays.asList(args).subList(wrapped ? 2 : 1, args.length);
this.length = args.length;
}
public boolean contains(String param) {
return args.contains(param.replaceAll("^[-/]*", "").toLowerCase(Locale.ROOT));
}
public String last() {
return args.get(args.size() - 1);
}
public String get(int index) {
return args.get(index);
}
public List<String> after(String param) {
List<String> yes = null;
for (String arg : args) {
if (yes != null)
yes.add(arg);
else if (arg.equals(param.replaceAll("^[-/]*", "").toLowerCase(Locale.ROOT)))
yes = new ArrayList<>();
}
return yes;
}
public List<String> after(int index) {
return index + 2 < length ? args.subList(index + 1, length) : new ArrayList<>();
}
@Override
public Iterator<String> iterator() {
return args.iterator();
}
}

View File

@ -1,6 +1,10 @@
package io.gitlab.jfronny.inceptum.cli;
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.Inceptum;
import io.gitlab.jfronny.inceptum.cli.Command;
import io.gitlab.jfronny.inceptum.cli.CommandArgs;
import io.gitlab.jfronny.inceptum.cli.CommandResolution;
import io.gitlab.jfronny.inceptum.cli.Commands;
import io.gitlab.jfronny.inceptum.util.ArgumentTokenizer;
import java.nio.file.Files;
@ -14,12 +18,12 @@ public class BatchCommand extends Command {
}
@Override
public void invoke(InvokedCommandDescription args) {
protected void invoke(CommandArgs args) {
if (args.length == 0) {
Inceptum.LOGGER.error("Could not start batch execution: No source file specified");
return;
}
Set<InvokedCommandDescription> argsSet = new LinkedHashSet<>();
Set<CommandResolution> resolved = new LinkedHashSet<>();
for (String arg : args) {
Path p = Path.of(arg);
if (!Files.exists(p)) {
@ -32,16 +36,17 @@ public class BatchCommand extends Command {
}
try {
for (String line : Files.readAllLines(p)) {
argsSet.add(new InvokedCommandDescription(ArgumentTokenizer.tokenize(line)));
CommandResolution resolution = Commands.resolve(ArgumentTokenizer.tokenize(line), args.wrapped);
if (resolution.command() instanceof WrapperCommand)
throw new Exception("You may not use the wrapper command in a command batch");
resolved.add(resolution);
}
} catch (Exception e) {
Inceptum.LOGGER.error("Could not read file", e);
return;
}
}
for (InvokedCommandDescription commandDescription : argsSet) {
commandDescription.command.invoke(commandDescription);
}
for (CommandResolution resolution : resolved) resolution.invoke();
}
@Override

View File

@ -0,0 +1,210 @@
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.Inceptum;
import io.gitlab.jfronny.inceptum.cli.Command;
import io.gitlab.jfronny.inceptum.cli.CommandArgs;
import io.gitlab.jfronny.inceptum.install.Steps;
import io.gitlab.jfronny.inceptum.model.inceptum.Config;
import io.gitlab.jfronny.inceptum.util.Utils;
import org.eclipse.jgit.api.Git;
import org.eclipse.jgit.api.errors.GitAPIException;
import org.eclipse.jgit.transport.CredentialsProvider;
import org.eclipse.jgit.transport.URIish;
import org.eclipse.jgit.transport.UsernamePasswordCredentialsProvider;
import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.List;
public class GitCommand extends Command {
public GitCommand() {
super("Aliases to some git commands. Intended to be used in batch commands", List.of("git", "sync"), List.of(
new CommitCommand(),
new PushCommand(),
new PullCommand(),
new ResetCommand(),
new CloneCommand()
));
}
@Override
protected void invoke(CommandArgs args) {
Inceptum.LOGGER.error("No known git command was specified");
}
private static abstract class BaseGitCommand extends Command {
public BaseGitCommand(String help, String... aliases) {
super(help, aliases);
}
@Override
protected void invoke(CommandArgs args) {
if (args.length == 0) {
Inceptum.LOGGER.error("You must specify an instance to commit in");
return;
}
Path instancePath = Inceptum.INSTANCE_DIR.resolve(args.get(0));
if (!Files.exists(instancePath.resolve("instance.json"))) {
Inceptum.LOGGER.error("Invalid instance: \"" + args.get(0) + "\"");
return;
}
try (Git git = Git.open(instancePath.toFile())) {
Config.GitConfig config = Inceptum.CONFIG.git.get(instancePath.getFileName().toString());
if (config == null) {
config = new Config.GitConfig();
Inceptum.saveConfig();
}
if (config.authorName == null) config.authorName = "Inceptum";
if (config.authorMail == null) config.authorMail = "inceptum@jfronny.gitlab.io";
if (config.sign == null) config.sign = false;
invoke(args.subArgs(), instancePath, git, config, config.username != null && config.password != null
? new UsernamePasswordCredentialsProvider(config.username, config.password)
: CredentialsProvider.getDefault());
} catch (IOException e) {
e.printStackTrace();
}
}
protected abstract void invoke(CommandArgs args, Path instancePath, Git git, Config.GitConfig config, CredentialsProvider credentials);
}
private static class CommitCommand extends BaseGitCommand {
public CommitCommand() {
super("Adds and commits all changes in the instance.\nUsage: inceptum git commit <instance> [message...]", "commit");
}
@Override
protected void invoke(CommandArgs args, Path instancePath, Git git, Config.GitConfig config, CredentialsProvider credentials) {
try {
git.commit()
.setAll(true)
.setMessage(args.length > 1
? String.join(" ", args.getArgs())
: "Commit at t" + System.currentTimeMillis())
.setSign(config.sign)
.setAuthor(config.authorName, config.authorMail)
.setCredentialsProvider(credentials)
.call();
} catch (GitAPIException e) {
e.printStackTrace();
}
}
}
private static class PushCommand extends BaseGitCommand {
public PushCommand() {
super("Pushes the current branch to the configured remote\nUsage: inceptum git push <instance>", "push");
}
@Override
protected void invoke(CommandArgs args, Path instancePath, Git git, Config.GitConfig config, CredentialsProvider credentials) {
try {
git.push()
.setCredentialsProvider(credentials)
.call();
} catch (GitAPIException e) {
e.printStackTrace();
}
}
}
private static class PullCommand extends BaseGitCommand {
public PullCommand() {
super("Pulls remote changes into the current branch and working tree\nUsage: inceptum git pull <instance>", "pull");
}
@Override
protected void invoke(CommandArgs args, Path instancePath, Git git, Config.GitConfig config, CredentialsProvider credentials) {
try {
git.pull()
.setRebase(true)
.setCredentialsProvider(credentials)
.call();
} catch (GitAPIException e) {
e.printStackTrace();
}
}
}
private static class ResetCommand extends BaseGitCommand {
public ResetCommand() {
super("Resets the current instance state to the last commit\nUsage: inceptum git reset <instance>", "reset");
}
@Override
protected void invoke(CommandArgs args, Path instancePath, Git git, Config.GitConfig config, CredentialsProvider credentials) {
try {
git.checkout()
.setAllPaths(true)
.call();
git.clean()
.setForce(true)
.setCleanDirectories(true)
.call();
} catch (GitAPIException e) {
e.printStackTrace();
}
}
}
private static class CloneCommand extends Command {
public CloneCommand() {
super("Clones an instance from a URL\nUsage: inceptum git clone <remote> [name]", "clone");
}
@Override
protected void invoke(CommandArgs args) {
if (args.length == 0) {
System.err.println("You haven't specified a remote");
return;
}
String name;
try {
name = args.length > 1 ? args.get(1) : new URIish(args.get(0)).getHumanishName();
} catch (URISyntaxException e) {
e.printStackTrace();
return;
}
name = name.replaceAll("^\\.*", "");
if (!name.matches("^[a-zA-Z0-9]+.*$")) {
System.err.println("Invalid name: " + name);
return;
}
Path instanceDir = Inceptum.INSTANCE_DIR.resolve(name);
if (Files.exists(instanceDir)) {
System.err.println("An instance by that name already exists");
return;
}
try {
Git.cloneRepository()
.setURI(args.get(0))
.setDirectory(instanceDir.toFile())
.call()
.close();
} catch (GitAPIException e) {
e.printStackTrace();
return;
}
Path instanceMeta = instanceDir.resolve("instance.json");
if (!Files.exists(instanceMeta)) {
System.err.println("Invalid repository: Contains no instance.json");
try {
Utils.deleteRecursive(instanceDir);
} catch (IOException e) {
e.printStackTrace();
}
return;
}
Config.GitConfig config = new Config.GitConfig();
Inceptum.CONFIG.git.put(name, config);
Inceptum.saveConfig();
try {
Steps.reDownload(instanceDir);
} catch (IOException e) {
e.printStackTrace();
}
}
}
}

View File

@ -1,7 +1,9 @@
package io.gitlab.jfronny.inceptum.cli;
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.Inceptum;
import io.gitlab.jfronny.inceptum.InceptumGui;
import io.gitlab.jfronny.inceptum.cli.Command;
import io.gitlab.jfronny.inceptum.cli.CommandArgs;
import io.gitlab.jfronny.inceptum.model.inceptum.UpdateInfo;
import io.gitlab.jfronny.inceptum.util.Utils;
import io.gitlab.jfronny.inceptum.windows.MainWindow;
@ -16,7 +18,7 @@ public class GuiCommand extends Command {
}
@Override
public void invoke(InvokedCommandDescription args) {
public void invoke(CommandArgs args) {
Inceptum.IS_GUI = true;
UpdateInfo update = UpdateCheckCommand.getUpdate();
InceptumGui.main(args, () -> {

View File

@ -0,0 +1,39 @@
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.cli.*;
import io.gitlab.jfronny.inceptum.util.MetaHolder;
import java.util.List;
public class HelpCommand extends Command {
public HelpCommand() {
super("Displays this screen", "help");
}
@Override
protected void invoke(CommandArgs args) {
HelpBuilder help;
if (args.length == 0) {
printHeader();
System.out.println("\nCommands:");
help = new HelpBuilder(true);
Commands.COMMANDS_ROOT.buildHelp(help);
}
else {
CommandResolution resolution = Commands.COMMANDS_ROOT.resolve(args);
if (resolution.resolvePath().isEmpty()) {
System.err.println("Could not find command matching your input");
invoke(new CommandArgs(List.of(), args.wrapped));
return;
}
printHeader();
System.out.println("\nFound matching: \"" + String.join(" ", resolution.resolvePath()) + "\"");
help = new HelpBuilder(false);
resolution.command().buildHelp(help);
}
System.out.println(help.getResult());
}
private static void printHeader() {
System.out.println("Inceptum v" + MetaHolder.VERSION.version + " (" + MetaHolder.VERSION.flavor + ")");
}
}

View File

@ -1,4 +1,7 @@
package io.gitlab.jfronny.inceptum.cli;
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.cli.Command;
import io.gitlab.jfronny.inceptum.cli.CommandArgs;
import java.net.URLClassLoader;
import java.util.Arrays;
@ -9,7 +12,7 @@ public class JvmStateCommand extends Command {
}
@Override
public void invoke(InvokedCommandDescription args) {
protected void invoke(CommandArgs args) {
System.out.println(System.getProperty("java.class.path"));
dumpClasspath(JvmStateCommand.class.getClassLoader());
}

View File

@ -1,6 +1,8 @@
package io.gitlab.jfronny.inceptum.cli;
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.Inceptum;
import io.gitlab.jfronny.inceptum.cli.Command;
import io.gitlab.jfronny.inceptum.cli.CommandArgs;
import io.gitlab.jfronny.inceptum.install.Steps;
import io.gitlab.jfronny.inceptum.model.inceptum.InstanceMeta;
import io.gitlab.jfronny.inceptum.util.InstanceLock;
@ -13,35 +15,39 @@ import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class LaunchCommand extends Command {
private final boolean server;
private final boolean restart;
public LaunchCommand() {
super("Launches the game. Optionally specify \"server\" [\"restart\"] or \"client\". Non-blocking (batch commands will continue if this is ran)", "run", "launch", "start");
super("Launches an instance of the game (client by default). Non-blocking (batch commands will continue if this is ran)",
List.of("run", "launch", "start"),
List.of(
new LaunchCommand("Explicitly launch a client", "client", false, false),
new LaunchCommand("Launch a server", "server", true, false,
new LaunchCommand("Restart the server if it stops", "restart", true, true)
)
));
this.server = false;
this.restart = false;
}
private LaunchCommand(String help, String name, boolean server, boolean restart, Command... subCommands) {
super(help, List.of(name), Arrays.asList(subCommands));
this.server = server;
this.restart = restart;
}
@Override
public void invoke(InvokedCommandDescription args) {
protected void invoke(CommandArgs args) {
if (args.length == 0) {
Inceptum.LOGGER.error("You must provide an instance name or path");
return;
}
int pArgIndex;
boolean restart = false;
boolean server = false;
if (args.get(0).equals("server")) {
server = true;
if (args.length > 1 && args.get(1).equals("restart")) {
if (args.length == 2) {
Inceptum.LOGGER.error("You must provide an instance name or path");
return;
}
restart = true;
pArgIndex = 2;
}
else pArgIndex = 1;
}
else pArgIndex = args.get(0).equals("client") ? 1 : 0;
String pArg = args.get(pArgIndex);
String pArg = args.get(0);
Path instanceDir = Files.exists(Path.of(pArg)) ? Path.of(pArg) : Inceptum.INSTANCE_DIR.resolve(pArg);
if (!Files.exists(instanceDir.resolve("instance.json"))) {
Inceptum.LOGGER.error("Not a valid instance");
@ -67,13 +73,13 @@ public class LaunchCommand extends Command {
Inceptum.showError("Not a valid instance", e);
return;
}
if (args.length > 2) {
if (args.length > 1) {
if (instance.arguments == null) instance.arguments = new InstanceMeta.Arguments();
instance.arguments.client = instance.arguments.client == null ? new ArrayList<>() : new ArrayList<>(instance.arguments.client);
instance.arguments.server = instance.arguments.server == null ? new ArrayList<>() : new ArrayList<>(instance.arguments.server);
instance.arguments.jvm = instance.arguments.jvm == null ? new ArrayList<>() : new ArrayList<>(instance.arguments.jvm);
instance.arguments.client.addAll(args.after(pArgIndex));
instance.arguments.server.addAll(args.after(pArgIndex));
instance.arguments.client.addAll(args.after(0));
instance.arguments.server.addAll(args.after(0));
}
try {
Steps.reDownload(instanceDir);

View File

@ -0,0 +1,54 @@
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.Inceptum;
import io.gitlab.jfronny.inceptum.cli.Command;
import io.gitlab.jfronny.inceptum.cli.CommandArgs;
import io.gitlab.jfronny.inceptum.model.inceptum.InstanceMeta;
import io.gitlab.jfronny.inceptum.util.InstanceLock;
import io.gitlab.jfronny.inceptum.util.Utils;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.List;
public class ListCommand extends Command {
public ListCommand() {
super("Lists all available instances", "list", "ls");
}
@Override
protected void invoke(CommandArgs args) {
try {
List<Path> paths = Utils.ls(Inceptum.INSTANCE_DIR);
if (paths.isEmpty()) System.out.println("No instances are currently present");
for (Path path : paths) {
if (!Files.exists(path.resolve("instance.json"))) {
System.out.println("- Invalid instance: " + path + " (no instance metadata)");
continue;
}
System.out.println("- \"" + path.getFileName().toString() + "\"");
if (InstanceLock.isSetupLocked(path)) {
System.out.println(" Status: Setting up");
continue;
}
InstanceMeta instance;
try {
instance = Utils.loadObject(path.resolve("instance.json"), InstanceMeta.class);
} catch (IOException e) {
Inceptum.LOGGER.error(" Could not load instance.json", e);
continue;
}
System.out.println(" Status: " + (InstanceLock.isRunningLocked(path) ? "Running" : "Stopped"));
System.out.println(" Version: " + instance.getMinecraftVersion());
if (instance.isFabric()) System.out.println(" Fabric Loader: " + instance.getLoaderVersion());
if (instance.java != null) System.out.println(" Custom Java: " + instance.java);
if (instance.minMem != null || instance.maxMem != null)
System.out.println(" Memory:" + (instance.minMem != null ? " Minimum: " + instance.minMem : "")
+ (instance.maxMem != null ? " Maximum: " + instance.maxMem : ""));
}
} catch (IOException e) {
e.printStackTrace();
}
}
}

View File

@ -1,6 +1,8 @@
package io.gitlab.jfronny.inceptum.cli;
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.Inceptum;
import io.gitlab.jfronny.inceptum.cli.Command;
import io.gitlab.jfronny.inceptum.cli.CommandArgs;
import io.gitlab.jfronny.inceptum.model.inceptum.UpdateInfo;
import io.gitlab.jfronny.inceptum.util.*;
@ -8,15 +10,25 @@ import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.List;
public class UpdateCheckCommand extends Command {
private final boolean install;
public UpdateCheckCommand() {
super("Checks for updates, allows updating if an update is discovered via the \"install\" flag", "update");
super("Checks for inceptum updates", List.of("update"), List.of(
new UpdateCheckCommand("Automatically install updates", "install", true)
));
install = false;
}
private UpdateCheckCommand(String help, String name, boolean install) {
super(help, name);
this.install = install;
}
@Override
public void invoke(InvokedCommandDescription args) {
if (args.contains("install") && !args.wrapped) {
protected void invoke(CommandArgs args) {
if (install && !args.wrapped) {
System.err.println("Automatic updates are not supported without the wrapper");
return;
}
@ -24,7 +36,7 @@ public class UpdateCheckCommand extends Command {
if (updateUrl == null) {
System.out.println("No update was found");
} else {
if (args.length > 1 && args.contains("install")) {
if (install) {
System.out.println("Installing from " + updateUrl);
try {
update(updateUrl, false);

View File

@ -0,0 +1,24 @@
package io.gitlab.jfronny.inceptum.cli.commands;
import io.gitlab.jfronny.inceptum.cli.*;
public class WrapperCommand extends Command {
public WrapperCommand() {
super("Invokes a command in a wrapper environment", "wrapper");
}
@Override
protected void invoke(CommandArgs args) {
throw new RuntimeException("Attempted to invoke wrapper command. This should not happen");
}
@Override
public CommandResolution resolve(CommandArgs args) {
return Commands.COMMANDS_ROOT.resolve(args);
}
@Override
public void buildHelp(HelpBuilder builder) {
// Don't show this in help
}
}

View File

@ -17,7 +17,7 @@ public class RulesDeserializer implements JsonDeserializer<Rules> {
throw new JsonParseException("Unexpected action in argument: " + actionType);
}
boolean matched = true;
if (ro.has("features")) { //TODO support has_custom_resolution
if (ro.has("features")) {
matched = false;
}
if (ro.has("os")) {

View File

@ -6,8 +6,18 @@ import io.gitlab.jfronny.inceptum.install.Step;
import io.gitlab.jfronny.inceptum.model.inceptum.InstanceMeta;
import io.gitlab.jfronny.inceptum.util.InstanceLock;
import io.gitlab.jfronny.inceptum.util.Utils;
import org.eclipse.jgit.api.CommitCommand;
import org.eclipse.jgit.api.Git;
import org.eclipse.jgit.api.errors.CanceledException;
import org.eclipse.jgit.api.errors.GitAPIException;
import org.eclipse.jgit.lib.CommitBuilder;
import org.eclipse.jgit.lib.GpgSigner;
import org.eclipse.jgit.lib.PersonIdent;
import org.eclipse.jgit.transport.ChainingCredentialsProvider;
import org.eclipse.jgit.transport.CredentialsProvider;
import org.eclipse.jgit.transport.NetRCCredentialsProvider;
import org.eclipse.jgit.transport.UsernamePasswordCredentialsProvider;
import org.eclipse.jgit.util.SystemReader;
import java.io.IOException;
import java.nio.file.Files;
@ -33,7 +43,8 @@ public class WriteMetadataStep implements Step {
.mixin.out/
.fabric/
*.lock
eula.txt""");
eula.txt
world/""");
}
Path gitDir = instance.resolve(".git");
if (!Files.exists(gitDir)) {
@ -41,11 +52,12 @@ public class WriteMetadataStep implements Step {
.setDirectory(instance.toFile())
.setGitDir(gitDir.toFile())
.call()) {
//TODO use proper git identity
git.add().addFilepattern(".").call();
git.commit().setMessage("Initial commit")
git.commit()
.setAll(true)
.setMessage("Initial commit")
.setSign(false)
.setAuthor("Inceptum", "inceptum@jfronny.gitlab.io").call();
.setAuthor("Inceptum", "inceptum@jfronny.gitlab.io")
.call();
} catch (GitAPIException e) {
Inceptum.showError("Could not initialize Git", e);
}

View File

@ -1,5 +1,8 @@
package io.gitlab.jfronny.inceptum.model.inceptum;
import java.util.HashMap;
import java.util.Map;
public class Config {
public boolean snapshots = false;
public boolean darkTheme = false;
@ -7,4 +10,13 @@ public class Config {
public String lastAccount;
public String offlineAccountLastName = null;
public UpdateChannel channel = UpdateChannel.Stable;
public Map<String, GitConfig> git = new HashMap<>();
public static class GitConfig {
public String username;
public String password;
public Boolean sign = false;
public String authorName;
public String authorMail;
}
}

View File

@ -15,7 +15,7 @@ public class AboutWindow extends Window {
@Override
public void draw() {
ImGui.text("Inceptum " + MetaHolder.VERSION.version + " (" + MetaHolder.VERSION.flavor + ") Copyright (C) 2021 JFronny");
ImGui.text("Inceptum " + MetaHolder.VERSION.version + " Copyright (C) 2021 JFronny");
ImGui.text("This program comes with ABSOLUTELY NO WARRANTY.");
ImGui.text("This is free software, and you are welcome to redistribute it under certain conditions.");

View File

@ -1,11 +1,13 @@
package io.gitlab.jfronny.inceptum.windows;
import imgui.ImGui;
import imgui.flag.ImGuiInputTextFlags;
import imgui.type.ImBoolean;
import imgui.type.ImString;
import io.gitlab.jfronny.inceptum.Inceptum;
import io.gitlab.jfronny.inceptum.InceptumGui;
import io.gitlab.jfronny.inceptum.install.Steps;
import io.gitlab.jfronny.inceptum.model.inceptum.Config;
import io.gitlab.jfronny.inceptum.model.inceptum.InstanceMeta;
import io.gitlab.jfronny.inceptum.model.inceptum.source.ModSource;
import io.gitlab.jfronny.inceptum.util.InstanceLock;
@ -23,23 +25,38 @@ import java.util.Set;
public class InstanceEditWindow extends Window {
private final Path path;
private final String name;
private final InstanceMeta instance;
private final InstanceManageControls imc;
private final ImBoolean customJava;
private final ImBoolean filterUpdates = new ImBoolean();
private final ImString customJavaPath = new ImString(128);
private final ImString customJavaPath = new ImString(512);
private final ImString gitUsername = new ImString(512);
private final ImString gitPassword = new ImString(512);
private final ImBoolean gitSign = new ImBoolean();
private final ImString gitAuthorName = new ImString(512);
private final ImString gitAuthorMail = new ImString(512);
private final ModsDirScanner mds;
private Path selected = null;
private boolean reDownload = false;
public InstanceEditWindow(Path path, InstanceMeta instance) {
super(path.getFileName().toString() + " - Edit");
name = path.getFileName().toString();
this.path = path;
this.instance = instance;
mds = new ModsDirScanner(path.resolve("mods"), instance);
mds.start();
customJava = new ImBoolean(instance.java != null);
imc = new InstanceManageControls(instance);
if (Inceptum.CONFIG.git.containsKey(name)) {
Config.GitConfig config = Inceptum.CONFIG.git.get(name);
gitUsername.set(config.username);
gitPassword.set(config.password);
gitSign.set(config.sign);
gitAuthorName.set(config.authorName);
gitAuthorMail.set(config.authorMail);
}
}
@Override
@ -240,6 +257,24 @@ public class InstanceEditWindow extends Window {
ImGui.endGroup();
ImGui.endTabItem();
}
if (ImGui.beginTabItem("Git")) {
ImGui.text("Authentication");
boolean update = ImGui.inputText("Username", gitUsername);
update |= ImGui.inputText("Password", gitPassword, ImGuiInputTextFlags.Password);
ImGui.text("Commits");
if (update) {
if (!Inceptum.CONFIG.git.containsKey(name))
Inceptum.CONFIG.git.put(name, new Config.GitConfig());
Config.GitConfig config = Inceptum.CONFIG.git.get(name);
config.username = gitUsername.get();
config.password = gitPassword.get();
config.sign = gitSign.get();
config.authorName = gitAuthorName.get();
config.authorMail = gitAuthorMail.get();
Inceptum.saveConfig();
}
ImGui.endTabItem();
}
ImGui.endTabBar();
}
}