mirror of
https://github.com/packwiz/packwiz.git
synced 2025-04-19 13:06:30 +02:00
Add option to specify additional game versions (closes #25)
This commit is contained in:
parent
6557719c1f
commit
7bedd820c2
@ -73,3 +73,8 @@ For use on servers, add the `-g` flag to disable the GUI and `-s server` to down
|
|||||||
- `packwiz cf install Sodium` (by search)
|
- `packwiz cf install Sodium` (by search)
|
||||||
- `packwiz cf install --addon-id 394468 --file-id 3067101` (if all else fails)
|
- `packwiz cf install --addon-id 394468 --file-id 3067101` (if all else fails)
|
||||||
- If files aren't being found, try running the `packwiz refresh` command to update the index!
|
- If files aren't being found, try running the `packwiz refresh` command to update the index!
|
||||||
|
|
||||||
|
## Options
|
||||||
|
- Additional options can be configured in the `[options]` section of `pack.toml`, as follows:
|
||||||
|
- `mods-folder` The folder to save mod metadata files into, for the install commands
|
||||||
|
- `acceptable-game-versions` A list of additional Minecraft versions to accept when installing or updating mods
|
@ -26,6 +26,7 @@ type Pack struct {
|
|||||||
Client map[string]toml.Primitive `toml:"client"`
|
Client map[string]toml.Primitive `toml:"client"`
|
||||||
Server map[string]toml.Primitive `toml:"server"`
|
Server map[string]toml.Primitive `toml:"server"`
|
||||||
Export map[string]map[string]interface{} `toml:"export"`
|
Export map[string]map[string]interface{} `toml:"export"`
|
||||||
|
Options map[string]interface{} `toml:"options"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// LoadPack loads the modpack metadata to a Pack struct
|
// LoadPack loads the modpack metadata to a Pack struct
|
||||||
@ -35,6 +36,14 @@ func LoadPack() (Pack, error) {
|
|||||||
return Pack{}, err
|
return Pack{}, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Read options into viper
|
||||||
|
if modpack.Options != nil {
|
||||||
|
err := viper.MergeConfigMap(modpack.Options)
|
||||||
|
if err != nil {
|
||||||
|
return Pack{}, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if len(modpack.Index.File) == 0 {
|
if len(modpack.Index.File) == 0 {
|
||||||
modpack.Index.File = "index.toml"
|
modpack.Index.File = "index.toml"
|
||||||
}
|
}
|
||||||
|
@ -2,6 +2,7 @@ package curseforge
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
|
"github.com/spf13/viper"
|
||||||
"regexp"
|
"regexp"
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
@ -199,6 +200,34 @@ func createModFile(modInfo modInfo, fileInfo modFileInfo, index *core.Index) err
|
|||||||
return index.RefreshFileWithHash(path, format, hash, true)
|
return index.RefreshFileWithHash(path, format, hash, true)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func matchGameVersion(mcVersion string, modMcVersion string) bool {
|
||||||
|
if getCurseforgeVersion(mcVersion) == modMcVersion {
|
||||||
|
return true
|
||||||
|
} else {
|
||||||
|
for _, v := range viper.GetStringSlice("acceptable-game-versions") {
|
||||||
|
if getCurseforgeVersion(v) == modMcVersion {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func matchGameVersions(mcVersion string, modMcVersions []string) bool {
|
||||||
|
for _, modMcVersion := range modMcVersions {
|
||||||
|
if getCurseforgeVersion(mcVersion) == modMcVersion {
|
||||||
|
return true
|
||||||
|
} else {
|
||||||
|
for _, v := range viper.GetStringSlice("acceptable-game-versions") {
|
||||||
|
if getCurseforgeVersion(v) == modMcVersion {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
type cfUpdateData struct {
|
type cfUpdateData struct {
|
||||||
ProjectID int `mapstructure:"project-id"`
|
ProjectID int `mapstructure:"project-id"`
|
||||||
FileID int `mapstructure:"file-id"`
|
FileID int `mapstructure:"file-id"`
|
||||||
@ -271,7 +300,7 @@ func (u cfUpdater) CheckUpdate(mods []core.Mod, mcVersion string) ([]core.Update
|
|||||||
// For snapshots, curseforge doesn't put them in GameVersionLatestFiles
|
// For snapshots, curseforge doesn't put them in GameVersionLatestFiles
|
||||||
for _, v := range modInfos[i].LatestFiles {
|
for _, v := range modInfos[i].LatestFiles {
|
||||||
// Choose "newest" version by largest ID
|
// Choose "newest" version by largest ID
|
||||||
if sliceContainsString(v.GameVersions, getCurseforgeVersion(mcVersion)) && v.ID > fileID {
|
if matchGameVersions(mcVersion, v.GameVersions) && v.ID > fileID {
|
||||||
updateAvailable = true
|
updateAvailable = true
|
||||||
fileID = v.ID
|
fileID = v.ID
|
||||||
fileInfoData = v
|
fileInfoData = v
|
||||||
@ -284,7 +313,7 @@ func (u cfUpdater) CheckUpdate(mods []core.Mod, mcVersion string) ([]core.Update
|
|||||||
// TODO: change to timestamp-based comparison??
|
// TODO: change to timestamp-based comparison??
|
||||||
// TODO: manage alpha/beta/release correctly, check update channel?
|
// TODO: manage alpha/beta/release correctly, check update channel?
|
||||||
// Choose "newest" version by largest ID
|
// Choose "newest" version by largest ID
|
||||||
if file.GameVersion == getCurseforgeVersion(mcVersion) && file.ID > fileID {
|
if matchGameVersion(mcVersion, file.GameVersion) && file.ID > fileID {
|
||||||
updateAvailable = true
|
updateAvailable = true
|
||||||
fileID = file.ID
|
fileID = file.ID
|
||||||
fileName = file.Name
|
fileName = file.Name
|
||||||
|
@ -5,6 +5,7 @@ import (
|
|||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"github.com/sahilm/fuzzy"
|
"github.com/sahilm/fuzzy"
|
||||||
|
"github.com/spf13/viper"
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
@ -268,7 +269,13 @@ func (r modResultsList) Len() int {
|
|||||||
func searchCurseforgeInternal(args []string, mcVersion string) (bool, modInfo) {
|
func searchCurseforgeInternal(args []string, mcVersion string) (bool, modInfo) {
|
||||||
fmt.Println("Searching CurseForge...")
|
fmt.Println("Searching CurseForge...")
|
||||||
searchTerm := strings.Join(args, " ")
|
searchTerm := strings.Join(args, " ")
|
||||||
results, err := getSearch(searchTerm, getCurseforgeVersion(mcVersion))
|
|
||||||
|
// If there are more than one acceptable version, we shouldn't filter by game version at all (as we can't filter by multiple)
|
||||||
|
filterGameVersion := getCurseforgeVersion(mcVersion)
|
||||||
|
if len(viper.GetStringSlice("acceptable-game-versions")) > 0 {
|
||||||
|
filterGameVersion = ""
|
||||||
|
}
|
||||||
|
results, err := getSearch(searchTerm, filterGameVersion)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
fmt.Println(err)
|
fmt.Println(err)
|
||||||
os.Exit(1)
|
os.Exit(1)
|
||||||
@ -343,7 +350,7 @@ func getLatestFile(modInfoData modInfo, mcVersion string, fileID int) (modFileIn
|
|||||||
|
|
||||||
for _, v := range modInfoData.LatestFiles {
|
for _, v := range modInfoData.LatestFiles {
|
||||||
// Choose "newest" version by largest ID
|
// Choose "newest" version by largest ID
|
||||||
if sliceContainsString(v.GameVersions, getCurseforgeVersion(mcVersion)) && v.ID > fileID {
|
if matchGameVersions(mcVersion, v.GameVersions) && v.ID > fileID {
|
||||||
fileID = v.ID
|
fileID = v.ID
|
||||||
fileInfoData = v
|
fileInfoData = v
|
||||||
fileInfoObtained = true
|
fileInfoObtained = true
|
||||||
@ -352,7 +359,7 @@ func getLatestFile(modInfoData modInfo, mcVersion string, fileID int) (modFileIn
|
|||||||
// TODO: change to timestamp-based comparison??
|
// TODO: change to timestamp-based comparison??
|
||||||
for _, v := range modInfoData.GameVersionLatestFiles {
|
for _, v := range modInfoData.GameVersionLatestFiles {
|
||||||
// Choose "newest" version by largest ID
|
// Choose "newest" version by largest ID
|
||||||
if v.GameVersion == getCurseforgeVersion(mcVersion) && v.ID > fileID {
|
if matchGameVersion(mcVersion, v.GameVersion) && v.ID > fileID {
|
||||||
fileID = v.ID
|
fileID = v.ID
|
||||||
fileInfoObtained = false // Make sure we get the file info
|
fileInfoObtained = false // Make sure we get the file info
|
||||||
}
|
}
|
||||||
@ -363,7 +370,7 @@ func getLatestFile(modInfoData modInfo, mcVersion string, fileID int) (modFileIn
|
|||||||
}
|
}
|
||||||
|
|
||||||
if fileID == 0 {
|
if fileID == 0 {
|
||||||
return modFileInfo{}, errors.New("mod not available for this minecraft version")
|
return modFileInfo{}, errors.New("mod not available for the configured Minecraft version(s) (use the acceptable-remote-versions option to accept more)")
|
||||||
}
|
}
|
||||||
|
|
||||||
fileInfoData, err := getFileInfo(modInfoData.ID, fileID)
|
fileInfoData, err := getFileInfo(modInfoData.ID, fileID)
|
||||||
|
@ -3,6 +3,7 @@ package modrinth
|
|||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"github.com/spf13/viper"
|
||||||
"os"
|
"os"
|
||||||
"regexp"
|
"regexp"
|
||||||
"strings"
|
"strings"
|
||||||
@ -97,7 +98,7 @@ func installViaSearch(query string, pack core.Pack) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
results, err := getModIdsViaSearch(query, mcVersion)
|
results, err := getModIdsViaSearch(query, append([]string{mcVersion}, viper.GetStringSlice("acceptable-game-versions")...))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -142,7 +143,7 @@ func installMod(mod Mod, pack core.Pack) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if latestVersion.ID == "" {
|
if latestVersion.ID == "" {
|
||||||
return errors.New("mod is not available for this minecraft version or mod loader")
|
return errors.New("mod is not available for this Minecraft version (use the acceptable-remote-versions option to accept more) or mod loader")
|
||||||
}
|
}
|
||||||
|
|
||||||
return installVersion(mod, latestVersion, pack)
|
return installVersion(mod, latestVersion, pack)
|
||||||
|
@ -3,6 +3,7 @@ package modrinth
|
|||||||
import (
|
import (
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"errors"
|
"errors"
|
||||||
|
"github.com/spf13/viper"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"net/http"
|
"net/http"
|
||||||
"net/url"
|
"net/url"
|
||||||
@ -115,14 +116,22 @@ type VersionFile struct {
|
|||||||
Primary bool // Is the file the primary file?
|
Primary bool // Is the file the primary file?
|
||||||
}
|
}
|
||||||
|
|
||||||
func getModIdsViaSearch(query string, version string) ([]ModResult, error) {
|
func getModIdsViaSearch(query string, versions []string) ([]ModResult, error) {
|
||||||
baseUrl := *modrinthApiUrlParsed
|
baseUrl := *modrinthApiUrlParsed
|
||||||
baseUrl.Path += "mod"
|
baseUrl.Path += "mod"
|
||||||
|
|
||||||
params := url.Values{}
|
params := url.Values{}
|
||||||
params.Add("limit", "5")
|
params.Add("limit", "5")
|
||||||
params.Add("index", "relevance")
|
params.Add("index", "relevance")
|
||||||
params.Add("facets", "[[\"versions:"+version+"\"]]")
|
facets := make([]string, 0)
|
||||||
|
for _, v := range versions {
|
||||||
|
facets = append(facets, "\"versions:"+v+"\"")
|
||||||
|
}
|
||||||
|
facetsEncoded, err := json.Marshal(facets)
|
||||||
|
if err != nil {
|
||||||
|
return []ModResult{}, err
|
||||||
|
}
|
||||||
|
params.Add("facets", "["+string(facetsEncoded)+"]")
|
||||||
params.Add("query", query)
|
params.Add("query", query)
|
||||||
|
|
||||||
baseUrl.RawQuery = params.Encode()
|
baseUrl.RawQuery = params.Encode()
|
||||||
@ -156,6 +165,11 @@ func getLatestVersion(modID string, pack core.Pack) (Version, error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return Version{}, err
|
return Version{}, err
|
||||||
}
|
}
|
||||||
|
gameVersions := append([]string{mcVersion}, viper.GetStringSlice("acceptable-game-versions")...)
|
||||||
|
gameVersionsEncoded, err := json.Marshal(gameVersions)
|
||||||
|
if err != nil {
|
||||||
|
return Version{}, err
|
||||||
|
}
|
||||||
|
|
||||||
loader := getLoader(pack)
|
loader := getLoader(pack)
|
||||||
|
|
||||||
@ -165,7 +179,7 @@ func getLatestVersion(modID string, pack core.Pack) (Version, error) {
|
|||||||
baseUrl.Path += "/version"
|
baseUrl.Path += "/version"
|
||||||
|
|
||||||
params := url.Values{}
|
params := url.Values{}
|
||||||
params.Add("game_versions", "[\""+mcVersion+"\"]")
|
params.Add("game_versions", string(gameVersionsEncoded))
|
||||||
if loader != "any" {
|
if loader != "any" {
|
||||||
params.Add("loaders", "[\""+loader+"\"]")
|
params.Add("loaders", "[\""+loader+"\"]")
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user