diff --git a/src/commands/migrate_possible.ts b/src/commands/migrate_possible.ts new file mode 100644 index 0000000..eec30b0 --- /dev/null +++ b/src/commands/migrate_possible.ts @@ -0,0 +1,36 @@ +import Subcommand from "./subcommand.js"; +import {Command} from "commander"; +import ModManager from "../mod-manager.js"; +import Mods from "../mods/mods.js"; +import MinecraftUtils from "../util/minecraft_utils.js"; +import PrintUtils from "../util/print_utils.js"; + +export default class MigratePossibleCommand implements Subcommand { + registerCommand(program: Command): void { + program.command("migrate-possible") + .description("Reports whether it is possible to upgrade to the provided Minecraft version") + .argument("[version]", "The Minecraft version to try and migrate to") + .action((version) => { + ModManager.execute(async () => { + // If no version is provided, prompt user for one + if (version === "" || version == undefined) { + version = await MinecraftUtils.getMinecraftVersionFromInput("What Minecraft version would you like to migrate to?"); + } + + // If version is valid, check if migration is possible + if (await MinecraftUtils.isValidVersion(version)) { + const possible = await Mods.isMigratePossible(version); + + if (possible) { + PrintUtils.success(`It is possible to migrate to version ${version}`) + } else { + PrintUtils.error(`It is not possible to migrate to version ${version}`) + } + } else { + PrintUtils.error(`${version} is not a valid Minecraft version`); + } + } + ) + }) + } +} \ No newline at end of file diff --git a/src/mod-manager.ts b/src/mod-manager.ts index ab34800..f20432d 100644 --- a/src/mod-manager.ts +++ b/src/mod-manager.ts @@ -12,6 +12,7 @@ import UninstallCommand from "./commands/uninstall_command.js"; import EssentialCommand from "./commands/essential_command.js"; import {readFileSync, unlinkSync} from "fs"; import UpgradeCommand from "./commands/upgrade_command.js"; +import MigratePossibleCommand from "./commands/migrate_possible.js"; export default class ModManager { @@ -25,7 +26,8 @@ export default class ModManager { new ListCommand(), new UninstallCommand(), new EssentialCommand(), - new UpgradeCommand() + new UpgradeCommand(), + new MigratePossibleCommand() ]; static FilePaths = class { diff --git a/src/mods/mods.ts b/src/mods/mods.ts index 7c448ff..4ad6a85 100644 --- a/src/mods/mods.ts +++ b/src/mods/mods.ts @@ -207,4 +207,35 @@ export default class Mods { return source } + + static async isMigratePossible(version: string): Promise { + const mods = this.getTrackedMods(); + + let availableList = []; + + // For every tracked mod + for (let mod of mods) { + // Get the latest version for each mod on the provided minecraft version + const spinner = new PrintUtils.Spinner(`Checking ${mod.name}...`); + spinner.start(); + + const source = this.getSourceFromName(mod.source); + try { + await source.getLatestVersion(mod.id, version) + // Report and record that this mod is available + spinner.succeed(`${mod.name} is available on Minecraft ${version}`) + availableList.push(true) + } catch (e) { + // Report and record that this mod is not available + spinner.error(`${mod.name} is not available on Minecraft ${version}`) + availableList.push(false); + } + } + + // Filter out all the true's from the list + availableList = availableList.filter(available => !available) + + // If the array is empty, all the mods reported as available, and a migration is possible + return Util.isArrayEmpty(availableList); + } } \ No newline at end of file diff --git a/src/util/initialiser.ts b/src/util/initialiser.ts index f5dd158..8d05132 100644 --- a/src/util/initialiser.ts +++ b/src/util/initialiser.ts @@ -2,9 +2,7 @@ import {existsSync, mkdirSync, writeFileSync} from "fs"; import path from "path"; import PrintUtils from "./print_utils.js"; import ModManager from "../mod-manager.js"; -import inquirer from "inquirer"; import MinecraftUtils from "./minecraft_utils.js"; -import MinecraftVersionError from "../errors/minecraft_version_error.js"; export default class Initialiser { public static async initialise(): Promise { @@ -13,7 +11,7 @@ export default class Initialiser { const success: boolean = this.setupFolderStructure(); if (success) { - const version = await this.getMinecraftVersionFromInput(); + const version = await MinecraftUtils.getMinecraftVersionFromInput("What Minecraft version is your server running?"); await MinecraftUtils.updateCurrentMinecraftVersion(version) PrintUtils.success("Sucessfully initialised Mod Manager!"); @@ -56,30 +54,4 @@ export default class Initialiser { return false; } } - - private static async getMinecraftVersionFromInput() { - let isVersionValid = false; - - let version: string | undefined = undefined; - while (!isVersionValid) { - const answer = await inquirer.prompt([{ - type: "input", - name: "minecraft_version", - message: "What version of Minecraft is the server running?" - }]) - version = answer.minecraft_version; - - if (await MinecraftUtils.isValidVersion(version)) { - isVersionValid = true; - } else { - PrintUtils.error(`${version} is not a valid Minecraft version for a Fabric server. Please try again`); - } - } - - if (version == undefined) { - throw new MinecraftVersionError("Escaped version input without a valid version") - } - - return version; - } } \ No newline at end of file diff --git a/src/util/minecraft_utils.ts b/src/util/minecraft_utils.ts index 59c9de9..532c97f 100644 --- a/src/util/minecraft_utils.ts +++ b/src/util/minecraft_utils.ts @@ -2,6 +2,8 @@ import {readFileSync, writeFileSync} from "fs"; import axios from "axios"; import ModManager from "../mod-manager.js"; import MinecraftVersionError from "../errors/minecraft_version_error.js"; +import inquirer from "inquirer"; +import PrintUtils from "./print_utils.js"; export default class MinecraftUtils { static async getCurrentMinecraftVersion(): Promise { @@ -34,5 +36,31 @@ export default class MinecraftUtils { } } + public static async getMinecraftVersionFromInput(question: string) { + let isVersionValid = false; + + let version: string | undefined = undefined; + while (!isVersionValid) { + const answer = await inquirer.prompt([{ + type: "input", + name: "minecraft_version", + message: question + }]) + version = answer.minecraft_version; + + if (await MinecraftUtils.isValidVersion(version)) { + isVersionValid = true; + } else { + PrintUtils.error(`${version} is not a valid Minecraft version for a Fabric server. Please try again`); + } + } + + if (version == undefined) { + throw new MinecraftVersionError("Escaped version input without a valid version") + } + + return version; + } + }