mmi 0.1.3 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.adoc +57 -19
- data/exe/mmi +13 -13
- data/lib/mmi/assets_processor.rb +29 -16
- data/lib/mmi/cached_download.rb +59 -0
- data/lib/mmi/github_api.rb +11 -0
- data/lib/mmi/interactive/assets.rb +208 -0
- data/lib/mmi/interactive/modloader.rb +139 -0
- data/lib/mmi/interactive/updater.rb +25 -138
- data/lib/mmi/interactive.rb +1 -2
- data/lib/mmi/mod_file_processor.rb +39 -26
- data/lib/mmi/modloader/fabric.rb +65 -36
- data/lib/mmi/modloader/none.rb +3 -1
- data/lib/mmi/modrinth_api.rb +14 -0
- data/lib/mmi/option_attributes.rb +38 -0
- data/lib/mmi/semver.rb +4 -4
- data/lib/mmi/source/github.rb +28 -28
- data/lib/mmi/source/modrinth.rb +79 -0
- data/lib/mmi/source/url.rb +59 -0
- data/lib/mmi/version.rb +1 -1
- data/lib/mmi.rb +2 -7
- metadata +82 -17
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 54e9d7ed91e3ac72f8c78ba1d9bb550de696e87b134e4bd1f5db393e99e7d7d2
|
4
|
+
data.tar.gz: 55df81f836288de4d0166c03488b7a3362992e6fc76304ccba2dc085758b1bb8
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 2c9e1954062c87ea12251b23103fee16b141a9c1f78ca88199c70441649090c16f5bb09481e5d6b158903f6553c201a754608346b12dbc208400fa973eebab73
|
7
|
+
data.tar.gz: '0481cffce09c9bf0439c1b739cb53cfeba1779a994c4b0ee203f45c3c17becd0164cc8c4b6c7400da01e26605e4e2065c4eeb141f0c6054fef06722f7bd7def2'
|
data/README.adoc
CHANGED
@@ -13,14 +13,29 @@ The application is currently CLI-only, but should work on Linux, MacOS and Windo
|
|
13
13
|
|
14
14
|
toc::[]
|
15
15
|
|
16
|
-
|
16
|
+
== Installation
|
17
17
|
|
18
|
-
|
18
|
+
=== Prerequisites
|
19
19
|
|
20
|
-
|
21
|
-
|
20
|
+
It is recommended to use MMI with Ruby 3.0 or higher.
|
21
|
+
While lower versions might work, further development is expected to ignore any specifics that may render those versions unusable.
|
22
22
|
|
23
|
-
|
23
|
+
=== Steps
|
24
|
+
|
25
|
+
==== Installation through rubygems.org
|
26
|
+
|
27
|
+
[example]
|
28
|
+
====
|
29
|
+
*Disclaimer:* While MMI releases are published on rubygems.org, they might not reflect current development.
|
30
|
+
If something does not work, try the manual installation.
|
31
|
+
====
|
32
|
+
|
33
|
+
[source,bash]
|
34
|
+
----
|
35
|
+
$ gem install mmi
|
36
|
+
----
|
37
|
+
|
38
|
+
==== Manual installation
|
24
39
|
|
25
40
|
Clone the repository and navigate into its root directory.
|
26
41
|
|
@@ -33,27 +48,32 @@ $ hg clone https://github.com/expeehaa/mmi.git
|
|
33
48
|
$ cd mmi
|
34
49
|
----
|
35
50
|
|
36
|
-
Install gem dependencies
|
51
|
+
Install gem dependencies using bundler
|
37
52
|
|
38
53
|
[source,bash]
|
39
54
|
----
|
40
55
|
$ bundle install
|
41
56
|
----
|
42
57
|
|
43
|
-
If you get an error
|
58
|
+
If you get an error saying the lockfile requires `bundler` version 2.0+, install it first.
|
44
59
|
|
45
60
|
[source,bash]
|
46
61
|
----
|
47
62
|
$ gem install bundler
|
48
63
|
----
|
49
64
|
|
50
|
-
|
65
|
+
Install the gem.
|
51
66
|
|
52
|
-
|
67
|
+
[source,bash]
|
68
|
+
----
|
69
|
+
$ rake install
|
70
|
+
----
|
71
|
+
|
72
|
+
== Basic usage
|
53
73
|
|
54
74
|
[source,text]
|
55
75
|
----
|
56
|
-
Syntax:
|
76
|
+
Syntax: mmi <config file> [action=install]
|
57
77
|
|
58
78
|
where action is one of
|
59
79
|
install - Install the modloader and assets as specified in the config file.
|
@@ -62,30 +82,48 @@ Syntax: exe/mmi <config file> [action=install]
|
|
62
82
|
----
|
63
83
|
|
64
84
|
The script currently does not support any arguments besides the ones listed above.
|
65
|
-
Trying to get help by running `
|
85
|
+
Trying to get help by running `mmi --help` or similar will not work.
|
66
86
|
|
67
|
-
|
87
|
+
== Example configs
|
68
88
|
|
69
89
|
Example configuration files can be found in `examples/`.
|
70
|
-
They
|
90
|
+
They can be parsed by the MMI version they come with.
|
91
|
+
Example configurations download and install files into `tmp/` so that your `.minecraft` folder will stay unharmed.
|
71
92
|
|
93
|
+
The files are intended to provide an overview of the different features of MMI.
|
94
|
+
They are not intended to create a working modded Minecraft environment and will therefore not be updated for each new Minecraft version.
|
72
95
|
|
73
|
-
|
96
|
+
== TODOs
|
74
97
|
|
75
98
|
* Improve argument parsing.
|
76
99
|
* Write tests.
|
77
100
|
* Add command to interactively create a config file.
|
78
101
|
* Be able to update/change modloader interactively.
|
79
102
|
* Be able to remove assets interactively.
|
80
|
-
* Think about advising
|
103
|
+
* Think about advising users to use another file extension than `.yaml` (e.g. `.mmi`, `.mmiconf`).
|
81
104
|
* Try to make a Java-executable `.jar` file using `warbler` and `JRuby`.
|
82
105
|
|
83
|
-
|
106
|
+
== Versioning
|
107
|
+
|
108
|
+
MMI uses semantic versioning with major, minor and patch versions.
|
109
|
+
|
110
|
+
Versions are coupled to the configuration file specification.
|
111
|
+
This means, within the same major version, every release must be backwards-compatible regarding config file interpreting and MMI releases with a lower minor version must still be able to interpret a config file with a higher minor version (although they are allowed and expected to not support some configurations).
|
112
|
+
|
113
|
+
An exception to this rule are all releases with the major version `0`.
|
114
|
+
There, within the same minor version, backwards compatibility can be expected, but different minor versions will (most likely) not be compatible.
|
115
|
+
|
116
|
+
== Contributing
|
117
|
+
|
118
|
+
Contributions are very welcome, as well as feature/bug requests.
|
119
|
+
|
120
|
+
In case you want to implement a feature, it would be best to create an issue beforehand so that we can discuss it.
|
121
|
+
This reduces the chance of a pull request being rejected.
|
84
122
|
|
85
|
-
Contributions are very welcome.
|
86
123
|
If you intend to create a pull request, please choose a branch name describing its changes (i.e. not some generic term like `master` or `fix`, but e.g. `fix_typo` or `add_interactive_update_command`).
|
87
124
|
|
88
125
|
Please be aware that I have a very specific code style and am interested in keeping it in this repository.
|
89
126
|
Some basic rules are specified in the `.editorconfig` file, which your editor should support.
|
90
|
-
|
91
|
-
|
127
|
+
Additionally, Rubocop has been configured using the existing code and every commit should pass Rubocop’s inspection.
|
128
|
+
There most likely are a lot of Rubocop rules that are currently not triggered and therefore not configured.
|
129
|
+
In such a case, either try to derive a style from existing code or feel free to ask.
|
data/exe/mmi
CHANGED
@@ -19,25 +19,25 @@ def processor(file)
|
|
19
19
|
end
|
20
20
|
end
|
21
21
|
|
22
|
-
if ARGV.
|
22
|
+
if !ARGV.empty?
|
23
23
|
file = ARGV.shift
|
24
24
|
action_param = ARGV.shift
|
25
25
|
action = action_param.nil? ? :install : action_param.to_sym
|
26
26
|
|
27
27
|
case action
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
28
|
+
when :install
|
29
|
+
processor(file).install
|
30
|
+
when :validate
|
31
|
+
processor(file)
|
32
|
+
|
33
|
+
puts 'File is valid.'
|
34
|
+
when :update
|
35
|
+
Mmi::Interactive.update(processor(file), file)
|
36
|
+
else
|
37
|
+
warn "Unknown action: #{action_param.inspect}."
|
38
|
+
Kernel.exit 1
|
39
39
|
end
|
40
40
|
else
|
41
41
|
puts 'No file given.'
|
42
42
|
Kernel.exit 1
|
43
|
-
end
|
43
|
+
end
|
data/lib/mmi/assets_processor.rb
CHANGED
@@ -1,41 +1,54 @@
|
|
1
|
+
require 'mmi/option_attributes'
|
1
2
|
require 'mmi/source/github'
|
3
|
+
require 'mmi/source/modrinth'
|
4
|
+
require 'mmi/source/url'
|
2
5
|
|
3
6
|
module Mmi
|
4
7
|
class AssetsProcessor
|
5
|
-
|
6
|
-
attr_reader :assets
|
8
|
+
include OptionAttributes
|
7
9
|
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
10
|
+
opt_accessor(:profile_dir) { Mmi.minecraft_dir }
|
11
|
+
opt_accessor(:items ) { [] }
|
12
|
+
|
13
|
+
attr_reader :parsed_items
|
14
|
+
|
15
|
+
def initialize(options)
|
16
|
+
@options = options
|
12
17
|
|
13
|
-
|
14
|
-
|
18
|
+
parse!
|
19
|
+
end
|
20
|
+
|
21
|
+
def parse!
|
22
|
+
if self.items.is_a?(Array)
|
23
|
+
@parsed_items = self.items.map.with_index do |asset, index|
|
15
24
|
source = asset['source']
|
16
25
|
|
17
26
|
if source
|
18
27
|
type = source['type']
|
19
28
|
|
20
29
|
case type
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
30
|
+
when 'github'
|
31
|
+
Source::Github.new(source)
|
32
|
+
when 'modrinth'
|
33
|
+
Source::Modrinth.new(source)
|
34
|
+
when 'url'
|
35
|
+
Source::Url.new(source)
|
36
|
+
else
|
37
|
+
raise Mmi::InvalidAttributeError, %Q(Invalid "source.type" in asset #{index.inspect}: #{type.inspect})
|
25
38
|
end
|
26
39
|
else
|
27
|
-
raise Mmi::MissingAttributeError, %Q
|
40
|
+
raise Mmi::MissingAttributeError, %Q(Missing "source" in asset #{index.inspect}.)
|
28
41
|
end
|
29
42
|
end
|
30
43
|
else
|
31
|
-
raise Mmi::InvalidAttributeError, %Q
|
44
|
+
raise Mmi::InvalidAttributeError, %Q(Invalid "assets": expected Array or nothing, got #{self.items.inspect}.)
|
32
45
|
end
|
33
46
|
end
|
34
47
|
|
35
48
|
def install
|
36
|
-
|
49
|
+
self.parsed_items.each do |asset|
|
37
50
|
asset.install(self.profile_dir)
|
38
51
|
end
|
39
52
|
end
|
40
53
|
end
|
41
|
-
end
|
54
|
+
end
|
@@ -0,0 +1,59 @@
|
|
1
|
+
require 'digest'
|
2
|
+
require 'fileutils'
|
3
|
+
require 'open-uri'
|
4
|
+
|
5
|
+
module Mmi
|
6
|
+
module CachedDownload
|
7
|
+
class << self
|
8
|
+
def open_cached(path, sha512: nil)
|
9
|
+
if File.exist?(path)
|
10
|
+
File.open(path).tap do |f|
|
11
|
+
if !sha512 || sha512 == Digest::SHA512.hexdigest(f.read)
|
12
|
+
f.seek(0)
|
13
|
+
f
|
14
|
+
else
|
15
|
+
nil
|
16
|
+
end
|
17
|
+
end
|
18
|
+
else
|
19
|
+
nil
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
def download(uri, sha512: nil)
|
24
|
+
URI.parse(uri).open.tap do |stream|
|
25
|
+
if sha512
|
26
|
+
actual_sha512 = Digest::SHA512.hexdigest(stream.read)
|
27
|
+
|
28
|
+
if sha512 == actual_sha512
|
29
|
+
stream.seek(0)
|
30
|
+
else
|
31
|
+
Mmi.fail! "Expected download to have SHA512 sum #{expected_hexdigest.inspect} but received #{actual_sha512.inspect}."
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def download_cached(uri, download_path, sha512_uri: nil)
|
38
|
+
ensure_cache_dir_exists!
|
39
|
+
|
40
|
+
expected_hexdigest = URI.parse(sha512_uri).open.read
|
41
|
+
cached_file = open_cached(download_path, sha512: expected_hexdigest)
|
42
|
+
|
43
|
+
if !cached_file
|
44
|
+
stream = download(uri, sha512: expected_hexdigest)
|
45
|
+
|
46
|
+
IO.copy_stream(stream, download_path)
|
47
|
+
else
|
48
|
+
Mmi.info "Using cached version of #{uri.inspect} from #{download_path.inspect}."
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
private
|
53
|
+
|
54
|
+
def ensure_cache_dir_exists!
|
55
|
+
FileUtils.mkdir_p(Mmi.cache_dir)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
@@ -0,0 +1,208 @@
|
|
1
|
+
require 'cli/ui'
|
2
|
+
|
3
|
+
require 'mmi/github_api'
|
4
|
+
require 'mmi/source/github'
|
5
|
+
|
6
|
+
module Mmi
|
7
|
+
module Interactive
|
8
|
+
module Assets
|
9
|
+
def update_assets
|
10
|
+
loop do
|
11
|
+
assets = processor.parsed_assets.parsed_items
|
12
|
+
|
13
|
+
choice = CLI::UI::Prompt.ask('Which asset do you want to change?') do |handler|
|
14
|
+
assets.each do |asset|
|
15
|
+
handler.option(asset.display_name) do
|
16
|
+
asset
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
handler.option('add', &:to_sym)
|
21
|
+
handler.option('quit', &:to_sym)
|
22
|
+
end
|
23
|
+
|
24
|
+
case choice
|
25
|
+
when :quit
|
26
|
+
break
|
27
|
+
when :add
|
28
|
+
add_asset
|
29
|
+
else
|
30
|
+
update_asset_version(choice)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
def add_asset
|
36
|
+
source_type = CLI::UI::Prompt.ask('Choose a source type.') do |handler|
|
37
|
+
%w[
|
38
|
+
github
|
39
|
+
modrinth
|
40
|
+
url
|
41
|
+
].each do |type|
|
42
|
+
handler.option(type, &:to_sym)
|
43
|
+
end
|
44
|
+
|
45
|
+
handler.option('quit', &:to_sym)
|
46
|
+
end
|
47
|
+
|
48
|
+
opts, source =
|
49
|
+
case source_type
|
50
|
+
when :quit
|
51
|
+
return false
|
52
|
+
when :github
|
53
|
+
options = {
|
54
|
+
'source' => {
|
55
|
+
'type' => 'github',
|
56
|
+
'asset_id' => 0,
|
57
|
+
},
|
58
|
+
}
|
59
|
+
|
60
|
+
options['source']['owner' ] = CLI::UI::Prompt.ask('Who is the owner of the source repository?').strip
|
61
|
+
options['source']['repo' ] = CLI::UI::Prompt.ask('What is the name of the source repository?').strip
|
62
|
+
options['source']['install_dir'] = CLI::UI::Prompt.ask('In which directory should the asset be placed?', default: 'mods').strip
|
63
|
+
options['source']['filename' ] = CLI::UI::Prompt.ask('Under which filename should the asset be saved? (leave empty for release asset name)', allow_empty: true).strip.then do |filename|
|
64
|
+
filename == '' ? nil : filename
|
65
|
+
end
|
66
|
+
|
67
|
+
options['source'].compact!
|
68
|
+
|
69
|
+
[options, Mmi::Source::Github.new(options['source'])]
|
70
|
+
when :modrinth
|
71
|
+
options = {
|
72
|
+
'source' => {
|
73
|
+
'type' => 'modrinth',
|
74
|
+
'version' => '0',
|
75
|
+
'version_file' => '0',
|
76
|
+
},
|
77
|
+
}
|
78
|
+
|
79
|
+
options['source']['name' ] = CLI::UI::Prompt.ask('What is the name of the mod in the Modrinth URL?').strip
|
80
|
+
options['source']['install_dir'] = CLI::UI::Prompt.ask('In which directory should the asset be placed?', default: 'mods').strip
|
81
|
+
options['source']['filename' ] = CLI::UI::Prompt.ask('Under which filename should the asset be saved? (leave empty for release asset name)', allow_empty: true).strip.then do |filename|
|
82
|
+
filename == '' ? nil : filename
|
83
|
+
end
|
84
|
+
|
85
|
+
options['source'].compact!
|
86
|
+
|
87
|
+
[options, Mmi::Source::Modrinth.new(options['source'])]
|
88
|
+
when :url
|
89
|
+
options = {
|
90
|
+
'source' => {
|
91
|
+
'type' => 'url',
|
92
|
+
'url' => '',
|
93
|
+
},
|
94
|
+
}
|
95
|
+
|
96
|
+
options['source']['install_dir'] = CLI::UI::Prompt.ask('In which directory should the asset be placed?', default: 'mods').strip
|
97
|
+
options['source']['filename' ] = CLI::UI::Prompt.ask('Under which filename should the asset be saved? (leave empty for release asset name)', allow_empty: true).strip.then do |filename|
|
98
|
+
filename == '' ? nil : filename
|
99
|
+
end
|
100
|
+
|
101
|
+
options['source'].compact!
|
102
|
+
|
103
|
+
[options, Mmi::Source::Url.new(options['source'])]
|
104
|
+
end
|
105
|
+
|
106
|
+
if update_asset_version(source)
|
107
|
+
self.processor.parsed_assets.items.push(opts)
|
108
|
+
self.processor.parsed_assets.parsed_items.push(source)
|
109
|
+
|
110
|
+
true
|
111
|
+
else
|
112
|
+
CLI::UI.puts('Aborting asset addition. No change will be made.', color: CLI::UI::Color::RED)
|
113
|
+
|
114
|
+
false
|
115
|
+
end
|
116
|
+
end
|
117
|
+
|
118
|
+
def update_asset_version(asset)
|
119
|
+
case asset
|
120
|
+
when Mmi::Source::Github
|
121
|
+
github_releases = Mmi::GithubApi.client.releases("#{asset.owner}/#{asset.repo}")
|
122
|
+
|
123
|
+
github_release = CLI::UI::Prompt.ask('Choose a release.') do |handler|
|
124
|
+
github_releases.select do |release|
|
125
|
+
release.assets.any?
|
126
|
+
end.each do |release|
|
127
|
+
handler.option(release.name) do
|
128
|
+
release
|
129
|
+
end
|
130
|
+
end
|
131
|
+
|
132
|
+
handler.option('quit', &:to_sym)
|
133
|
+
end
|
134
|
+
|
135
|
+
case github_release
|
136
|
+
when :quit
|
137
|
+
false
|
138
|
+
else
|
139
|
+
release_asset = CLI::UI::Prompt.ask('Choose an asset.') do |handler|
|
140
|
+
github_release.assets.each do |a|
|
141
|
+
handler.option(a.name) do
|
142
|
+
a
|
143
|
+
end
|
144
|
+
end
|
145
|
+
|
146
|
+
handler.option('quit', &:to_sym)
|
147
|
+
end
|
148
|
+
|
149
|
+
case release_asset
|
150
|
+
when :quit
|
151
|
+
false
|
152
|
+
else
|
153
|
+
asset.release = nil
|
154
|
+
asset.file = nil
|
155
|
+
|
156
|
+
asset.asset_id = release_asset.id
|
157
|
+
|
158
|
+
true
|
159
|
+
end
|
160
|
+
end
|
161
|
+
when Mmi::Source::Modrinth
|
162
|
+
mod_version = CLI::UI::Prompt.ask('Choose a version.') do |handler|
|
163
|
+
asset.cached_mod_versions.select do |version|
|
164
|
+
version['files'].any?
|
165
|
+
end.each do |version|
|
166
|
+
handler.option("#{version['name']} (for game versions #{version['game_versions'].join('/')})") do
|
167
|
+
version
|
168
|
+
end
|
169
|
+
end
|
170
|
+
|
171
|
+
handler.option('quit', &:to_sym)
|
172
|
+
end
|
173
|
+
|
174
|
+
case mod_version
|
175
|
+
when :quit
|
176
|
+
false
|
177
|
+
else
|
178
|
+
version_file = CLI::UI::Prompt.ask('Choose a version file.') do |handler|
|
179
|
+
mod_version['files'].each do |file|
|
180
|
+
handler.option(file['filename']) do
|
181
|
+
file
|
182
|
+
end
|
183
|
+
end
|
184
|
+
|
185
|
+
handler.option('quit', &:to_sym)
|
186
|
+
end
|
187
|
+
|
188
|
+
case version_file
|
189
|
+
when :quit
|
190
|
+
false
|
191
|
+
else
|
192
|
+
asset.version = mod_version['name']
|
193
|
+
asset.version_file = version_file['filename']
|
194
|
+
|
195
|
+
true
|
196
|
+
end
|
197
|
+
end
|
198
|
+
when Mmi::Source::Url
|
199
|
+
asset.url = CLI::UI::Prompt.ask('What is the URL of the file that should be downloaded?', default: asset.url).strip
|
200
|
+
else
|
201
|
+
CLI::UI.puts('This asset cannot be updated.', color: CLI::UI::Color::RED)
|
202
|
+
|
203
|
+
false
|
204
|
+
end
|
205
|
+
end
|
206
|
+
end
|
207
|
+
end
|
208
|
+
end
|
@@ -0,0 +1,139 @@
|
|
1
|
+
require 'cli/ui'
|
2
|
+
|
3
|
+
require 'mmi/modloader/fabric'
|
4
|
+
require 'mmi/modloader/none'
|
5
|
+
|
6
|
+
module Mmi
|
7
|
+
module Interactive
|
8
|
+
module Modloader
|
9
|
+
def update_modloader
|
10
|
+
choice = CLI::UI::Prompt.ask('What do you want to do?') do |handler|
|
11
|
+
[
|
12
|
+
(["Update current modloader #{self.processor.modloader['name']}", :update_current] unless self.processor.parsed_modloader.is_a?(Mmi::Modloader::None)),
|
13
|
+
['quit', :quit ],
|
14
|
+
].each do |name, result|
|
15
|
+
handler.option(name) do
|
16
|
+
result
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
case choice
|
22
|
+
when :update_current
|
23
|
+
update_modloader_current
|
24
|
+
when :quit
|
25
|
+
# Pass.
|
26
|
+
else
|
27
|
+
raise 'Consider yourself lucky, you found a bug.'
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
def update_modloader_current
|
32
|
+
ml = self.processor.parsed_modloader
|
33
|
+
|
34
|
+
case ml
|
35
|
+
when Mmi::Modloader::None
|
36
|
+
CLI::UI.puts('There is currently no modloader set, please choose one first.', color: CLI::UI::Color::RED)
|
37
|
+
when Mmi::Modloader::Fabric
|
38
|
+
loop do
|
39
|
+
choice = CLI::UI::Prompt.ask('What do you want to update?') do |handler|
|
40
|
+
[
|
41
|
+
['Installer version', :version ],
|
42
|
+
['Minecraft version', :mc_version ],
|
43
|
+
['Download Minecraft?', :download_mc ],
|
44
|
+
['Install directory', :install_dir ],
|
45
|
+
['Install type', :install_type],
|
46
|
+
['quit', :quit ],
|
47
|
+
].each do |name, result|
|
48
|
+
handler.option(name) do
|
49
|
+
result
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
case choice
|
55
|
+
when :version
|
56
|
+
choice2 = CLI::UI::Prompt.ask('Choose a fabric installer version') do |handler|
|
57
|
+
ml.available_versions.sort.reverse.each do |v|
|
58
|
+
handler.option(v, &:itself)
|
59
|
+
end
|
60
|
+
|
61
|
+
handler.option('quit', &:to_sym)
|
62
|
+
end
|
63
|
+
|
64
|
+
case choice2
|
65
|
+
when :quit
|
66
|
+
# Pass.
|
67
|
+
else
|
68
|
+
ml.version = choice2
|
69
|
+
end
|
70
|
+
when :mc_version
|
71
|
+
choice2 =
|
72
|
+
begin
|
73
|
+
CLI::UI::Prompt.ask('Which Minecraft version do you need?')
|
74
|
+
rescue Interrupt
|
75
|
+
:quit
|
76
|
+
end
|
77
|
+
|
78
|
+
case choice2
|
79
|
+
when :quit
|
80
|
+
# Pass.
|
81
|
+
else
|
82
|
+
ml.mcversion = choice2
|
83
|
+
end
|
84
|
+
when :download_mc
|
85
|
+
choice2 =
|
86
|
+
begin
|
87
|
+
CLI::UI::Prompt.confirm('Download minecraft when installing the modloader? (Ctrl+C for no change)', default: ml.download_mc)
|
88
|
+
rescue Interrupt
|
89
|
+
:quit
|
90
|
+
end
|
91
|
+
|
92
|
+
case choice2
|
93
|
+
when :quit
|
94
|
+
# Pass.
|
95
|
+
else
|
96
|
+
ml.download_mc = choice2
|
97
|
+
end
|
98
|
+
when :install_dir
|
99
|
+
choice2 =
|
100
|
+
begin
|
101
|
+
CLI::UI::Prompt.ask('In which directory should the modloader be installed? ', is_file: true)
|
102
|
+
rescue Interrupt
|
103
|
+
:quit
|
104
|
+
end
|
105
|
+
|
106
|
+
case choice2
|
107
|
+
when :quit
|
108
|
+
# Pass.
|
109
|
+
else
|
110
|
+
ml.install_dir = choice2.strip.empty? ? nil : choice2
|
111
|
+
end
|
112
|
+
when :install_type
|
113
|
+
choice2 = CLI::UI::Prompt.ask('What type of installation do you want?') do |handler|
|
114
|
+
ml.allowed_install_types.each do |type|
|
115
|
+
handler.option(type, &:itself)
|
116
|
+
end
|
117
|
+
|
118
|
+
handler.option('quit', &:to_sym)
|
119
|
+
end
|
120
|
+
|
121
|
+
case choice2
|
122
|
+
when :quit
|
123
|
+
# Pass.
|
124
|
+
else
|
125
|
+
ml.install_type = choice2
|
126
|
+
end
|
127
|
+
when :quit
|
128
|
+
break
|
129
|
+
else
|
130
|
+
raise 'Consider yourself lucky, you found a bug.'
|
131
|
+
end
|
132
|
+
end
|
133
|
+
else
|
134
|
+
CLI::UI.puts("Modloader #{self.processor.modloader['name']} is not supported.", color: CLI::UI::Color::RED)
|
135
|
+
end
|
136
|
+
end
|
137
|
+
end
|
138
|
+
end
|
139
|
+
end
|