Eradicate variable-size integer types where not used by interface or as index (fixes #107)

This commit is contained in:
comp500 2022-06-16 21:32:15 +01:00
parent d051932bbb
commit d5290ebd32
12 changed files with 125 additions and 112 deletions

View File

@ -117,7 +117,7 @@ var urlRegexes = [...]*regexp.Regexp{
regexp.MustCompile("^(?P<slug>[a-z][\\da-z\\-_]{0,127})$"),
}
func parseSlugOrUrl(url string) (game string, category string, slug string, fileID int, err error) {
func parseSlugOrUrl(url string) (game string, category string, slug string, fileID uint32, err error) {
for _, r := range urlRegexes {
matches := r.FindStringSubmatch(url)
if matches != nil {
@ -132,7 +132,9 @@ func parseSlugOrUrl(url string) (game string, category string, slug string, file
}
if i := r.SubexpIndex("fileID"); i >= 0 {
if matches[i] != "" {
fileID, err = strconv.Atoi(matches[i])
var f uint64
f, err = strconv.ParseUint(matches[i], 10, 32)
fileID = uint32(f)
}
}
return
@ -214,7 +216,7 @@ func createModFile(modInfo modInfo, fileInfo modFileInfo, index *core.Index, opt
return index.RefreshFileWithHash(path, format, hash, true)
}
func getSearchLoaderType(pack core.Pack) int {
func getSearchLoaderType(pack core.Pack) modloaderType {
dependencies := pack.Versions
_, hasFabric := dependencies["fabric"]
@ -235,7 +237,7 @@ func getSearchLoaderType(pack core.Pack) int {
}
}
func matchLoaderType(packLoaders []string, modLoaderType int) bool {
func matchLoaderType(packLoaders []string, modLoaderType modloaderType) bool {
if len(packLoaders) == 0 || modLoaderType == modloaderTypeAny {
return true
} else {
@ -290,8 +292,8 @@ func matchGameVersions(mcVersion string, modMcVersions []string) bool {
}
type cfUpdateData struct {
ProjectID int `mapstructure:"project-id"`
FileID int `mapstructure:"file-id"`
ProjectID uint32 `mapstructure:"project-id"`
FileID uint32 `mapstructure:"file-id"`
}
func (u cfUpdateData) ToMap() (map[string]interface{}, error) {
@ -311,13 +313,13 @@ func (u cfUpdater) ParseUpdate(updateUnparsed map[string]interface{}) (interface
type cachedStateStore struct {
modInfo
hasFileInfo bool
fileID int
fileID uint32
fileInfo modFileInfo
}
func (u cfUpdater) CheckUpdate(mods []core.Mod, mcVersion string, pack core.Pack) ([]core.UpdateCheck, error) {
results := make([]core.UpdateCheck, len(mods))
modIDs := make([]int, len(mods))
modIDs := make([]uint32, len(mods))
modInfos := make([]modInfo, len(mods))
for i, v := range mods {
@ -438,7 +440,7 @@ func (u cfUpdater) DoUpdate(mods []*core.Mod, cachedState []interface{}) error {
}
type cfExportData struct {
ProjectID int `mapstructure:"project-id"`
ProjectID uint32 `mapstructure:"project-id"`
}
func (e cfExportData) ToMap() (map[string]interface{}, error) {
@ -461,9 +463,9 @@ func (c cfDownloader) GetFilesMetadata(mods []*core.Mod) ([]core.MetaDownloaderD
}
downloaderData := make([]core.MetaDownloaderData, len(mods))
indexMap := make(map[int]int)
indexMap := make(map[uint32]int)
projectMetadata := make([]cfUpdateData, len(mods))
fileIDs := make([]int, len(mods))
fileIDs := make([]uint32, len(mods))
for i, v := range mods {
updateData, ok := v.GetParsedUpdateData("curseforge")
if !ok {
@ -480,7 +482,7 @@ func (c cfDownloader) GetFilesMetadata(mods []*core.Mod) ([]core.MetaDownloaderD
return nil, fmt.Errorf("failed to get CurseForge file metadata: %w", err)
}
modIDsToLookup := make([]int, 0)
modIDsToLookup := make([]uint32, 0)
fileNames := make([]string, len(mods))
for _, file := range fileData {
if _, ok := indexMap[file.ModID]; !ok {
@ -509,7 +511,7 @@ func (c cfDownloader) GetFilesMetadata(mods []*core.Mod) ([]core.MetaDownloaderD
downloaderData[indexMap[mod.ID]] = &cfDownloadMetadata{
noDistribution: true, // Inverted so the default value is not this (probably doesn't matter)
name: mod.Name,
websiteUrl: mod.Links.WebsiteURL + "/files/" + strconv.Itoa(fileIDs[indexMap[mod.ID]]),
websiteUrl: mod.Links.WebsiteURL + "/files/" + strconv.FormatUint(uint64(fileIDs[indexMap[mod.ID]]), 10),
fileName: fileNames[indexMap[mod.ID]],
}
}

View File

@ -32,8 +32,8 @@ var detectCmd = &cobra.Command{
}
// Walk files in the mods folder
var hashes []int
modPaths := make(map[int]string)
var hashes []uint32
modPaths := make(map[uint32]string)
err = filepath.Walk("mods", func(path string, info os.FileInfo, err error) error {
if err != nil {
return err
@ -51,8 +51,8 @@ var detectCmd = &cobra.Command{
return err
}
hash := getByteArrayHash(bytes)
hashes = append(hashes, int(hash))
modPaths[int(hash)] = path
hashes = append(hashes, hash)
modPaths[hash] = path
return nil
})
if err != nil {
@ -132,8 +132,8 @@ func init() {
curseforgeCmd.AddCommand(detectCmd)
}
func getByteArrayHash(bytes []byte) uint64 {
return uint64(murmur.MurmurHash2(computeNormalizedArray(bytes), 1))
func getByteArrayHash(bytes []byte) uint32 {
return murmur.MurmurHash2(computeNormalizedArray(bytes), 1)
}
func computeNormalizedArray(bytes []byte) []byte {

View File

@ -238,7 +238,7 @@ func createModlist(zw *zip.Writer, mods []*core.Mod) error {
continue
}
project := projectRaw.(cfUpdateData)
_, err = w.WriteString("<li><a href=\"https://www.curseforge.com/projects/" + strconv.Itoa(project.ProjectID) + "\">" + mod.Name + "</a></li>\r\n")
_, err = w.WriteString("<li><a href=\"https://www.curseforge.com/projects/" + strconv.FormatUint(uint64(project.ProjectID), 10) + "\">" + mod.Name + "</a></li>\r\n")
if err != nil {
return err
}

View File

@ -185,7 +185,7 @@ var importCmd = &cobra.Command{
}
modsList := packImport.Mods()
modIDs := make([]int, len(modsList))
modIDs := make([]uint32, len(modsList))
for i, v := range modsList {
modIDs[i] = v.ProjectID
}
@ -198,17 +198,17 @@ var importCmd = &cobra.Command{
os.Exit(1)
}
modInfosMap := make(map[int]modInfo)
modInfosMap := make(map[uint32]modInfo)
for _, v := range modInfos {
modInfosMap[v.ID] = v
}
// TODO: multithreading????
modFileInfosMap := make(map[int]modFileInfo)
modFileInfosMap := make(map[uint32]modFileInfo)
referencedModPaths := make([]string, 0, len(modsList))
successes := 0
remainingFileIDs := make([]int, 0, len(modsList))
remainingFileIDs := make([]uint32, 0, len(modsList))
// 1st pass: query mod metadata for every CurseForge file
for _, v := range modsList {

View File

@ -46,7 +46,7 @@ var installCmd = &cobra.Command{
game := gameFlag
category := categoryFlag
var modID, fileID int
var modID, fileID uint32
var slug string
// If mod/file IDs are provided in command line, use those
@ -122,7 +122,7 @@ var installCmd = &cobra.Command{
if len(fileInfoData.Dependencies) > 0 {
var depsInstallable []installableDep
var depIDPendingQueue []int
var depIDPendingQueue []uint32
for _, dep := range fileInfoData.Dependencies {
if dep.Type == dependencyTypeRequired {
depIDPendingQueue = append(depIDPendingQueue, dep.ModID)
@ -133,7 +133,7 @@ var installCmd = &cobra.Command{
fmt.Println("Finding dependencies...")
cycles := 0
var installedIDList []int
var installedIDList []uint32
for len(depIDPendingQueue) > 0 && cycles < maxCycles {
if installedIDList == nil {
// Get modids of all mods
@ -278,14 +278,14 @@ func (r modResultsList) Len() int {
return len(r)
}
func searchCurseforgeInternal(searchTerm string, isSlug bool, game string, category string, mcVersion string, searchLoaderType int) (bool, modInfo) {
func searchCurseforgeInternal(searchTerm string, isSlug bool, game string, category string, mcVersion string, searchLoaderType modloaderType) (bool, modInfo) {
if isSlug {
fmt.Println("Looking up CurseForge slug...")
} else {
fmt.Println("Searching CurseForge...")
}
var gameID, categoryID, classID int
var gameID, categoryID, classID uint32
if game == "minecraft" {
gameID = 432
}
@ -308,7 +308,7 @@ func searchCurseforgeInternal(searchTerm string, isSlug bool, game string, categ
fmt.Printf("Failed to lookup game %s: selected game does not have a public API!\n", game)
os.Exit(1)
}
gameID = int(v.ID)
gameID = v.ID
break
}
}
@ -409,7 +409,7 @@ func searchCurseforgeInternal(searchTerm string, isSlug bool, game string, categ
}
}
func getLatestFile(modInfoData modInfo, mcVersion string, fileID int, packLoaders []string) (modFileInfo, error) {
func getLatestFile(modInfoData modInfo, mcVersion string, fileID uint32, packLoaders []string) (modFileInfo, error) {
if fileID == 0 {
var fileInfoData modFileInfo
fileInfoObtained := false
@ -455,8 +455,8 @@ func getLatestFile(modInfoData modInfo, mcVersion string, fileID int, packLoader
return fileInfoData, nil
}
var addonIDFlag int
var fileIDFlag int
var addonIDFlag uint32
var fileIDFlag uint32
var gameFlag string
var categoryFlag string
@ -464,8 +464,8 @@ var categoryFlag string
func init() {
curseforgeCmd.AddCommand(installCmd)
installCmd.Flags().IntVar(&addonIDFlag, "addon-id", 0, "The CurseForge project ID to use")
installCmd.Flags().IntVar(&fileIDFlag, "file-id", 0, "The CurseForge file ID to use")
installCmd.Flags().Uint32Var(&addonIDFlag, "addon-id", 0, "The CurseForge project ID to use")
installCmd.Flags().Uint32Var(&fileIDFlag, "file-id", 0, "The CurseForge file ID to use")
installCmd.Flags().StringVar(&gameFlag, "game", "minecraft", "The game to add files from (slug, as stored in URLs); the game in the URL takes precedence")
installCmd.Flags().StringVar(&categoryFlag, "category", "", "The category to add files from (slug, as stored in URLs); the category in the URL takes precedence")
}

View File

@ -52,7 +52,7 @@ var openCmd = &cobra.Command{
}
cfUpdateData := updateData.(cfUpdateData)
fmt.Println("Opening browser...")
url := "https://www.curseforge.com/projects/" + strconv.Itoa(cfUpdateData.ProjectID)
url := "https://www.curseforge.com/projects/" + strconv.FormatUint(uint64(cfUpdateData.ProjectID), 10)
err = open.Start(url)
if err != nil {
fmt.Println("Opening page failed, direct link:")

View File

@ -8,14 +8,14 @@ type cursePackMeta struct {
ModLoaders []modLoaderDef `json:"modLoaders"`
} `json:"minecraft"`
ManifestType string `json:"manifestType"`
ManifestVersion int `json:"manifestVersion"`
ManifestVersion uint32 `json:"manifestVersion"`
NameInternal string `json:"name"`
Version string `json:"version"`
Author string `json:"author"`
ProjectID int `json:"projectID"`
ProjectID uint32 `json:"projectID"`
Files []struct {
ProjectID int `json:"projectID"`
FileID int `json:"fileID"`
ProjectID uint32 `json:"projectID"`
FileID uint32 `json:"fileID"`
Required bool `json:"required"`
} `json:"files"`
Overrides string `json:"overrides"`

View File

@ -17,10 +17,10 @@ type twitchInstalledPackMeta struct {
} `json:"baseModLoader"`
ModpackOverrides []string `json:"modpackOverrides"`
ModsInternal []struct {
ID int `json:"addonID"`
ID uint32 `json:"addonID"`
File struct {
// I've given up on using this cached data, just going to re-request it
ID int `json:"id"`
ID uint32 `json:"id"`
// Used to determine if the mod is optional-disabled
FileNameOnDisk string
} `json:"installedFile"`

View File

@ -63,22 +63,22 @@ func ReadMetadata(s ImportPackSource) ImportPackMetadata {
// AddonFileReference is a struct to reference a single file on CurseForge
type AddonFileReference struct {
ProjectID int
FileID int
ProjectID uint32
FileID uint32
// OptionalDisabled is true if the file is optional and disabled (turned off in Twitch launcher)
OptionalDisabled bool
}
func WriteManifestFromPack(pack core.Pack, fileRefs []AddonFileReference, projectID int, out io.Writer) error {
func WriteManifestFromPack(pack core.Pack, fileRefs []AddonFileReference, projectID uint32, out io.Writer) error {
files := make([]struct {
ProjectID int `json:"projectID"`
FileID int `json:"fileID"`
ProjectID uint32 `json:"projectID"`
FileID uint32 `json:"fileID"`
Required bool `json:"required"`
}, len(fileRefs))
for i, fr := range fileRefs {
files[i] = struct {
ProjectID int `json:"projectID"`
FileID int `json:"fileID"`
ProjectID uint32 `json:"projectID"`
FileID uint32 `json:"fileID"`
Required bool `json:"required"`
}{ProjectID: fr.ProjectID, FileID: fr.FileID, Required: !fr.OptionalDisabled}
}

View File

@ -85,16 +85,20 @@ func (c *cfApiClient) makePost(endpoint string, body io.Reader) (*http.Response,
return resp, nil
}
type fileType uint8
//noinspection GoUnusedConst
const (
fileTypeRelease int = iota + 1
fileTypeRelease fileType = iota + 1
fileTypeBeta
fileTypeAlpha
)
type dependencyType uint8
//noinspection GoUnusedConst
const (
dependencyTypeEmbedded int = iota + 1
dependencyTypeEmbedded dependencyType = iota + 1
dependencyTypeOptional
dependencyTypeRequired
dependencyTypeTool
@ -102,10 +106,12 @@ const (
dependencyTypeInclude
)
type modloaderType uint8
//noinspection GoUnusedConst
const (
// modloaderTypeAny should not be passed to the API - it does not work
modloaderTypeAny int = iota
modloaderTypeAny modloaderType = iota
modloaderTypeForge
modloaderTypeCauldron
modloaderTypeLiteloader
@ -131,9 +137,11 @@ var modloaderIds = [...]string{
"quilt",
}
type hashAlgo uint8
//noinspection GoUnusedConst
const (
hashAlgoSHA1 int = iota + 1
hashAlgoSHA1 hashAlgo = iota + 1
hashAlgoMD5
)
@ -142,7 +150,7 @@ type modInfo struct {
Name string `json:"name"`
Summary string `json:"summary"`
Slug string `json:"slug"`
ID int `json:"id"`
ID uint32 `json:"id"`
GameID uint32 `json:"gameId"`
PrimaryCategoryID uint32 `json:"primaryCategoryId"`
ClassID uint32 `json:"classId"`
@ -151,10 +159,10 @@ type modInfo struct {
// TODO: check how twitch launcher chooses which one to use, when you are on beta/alpha channel?!
// or does it not have the concept of release channels?!
GameVersion string `json:"gameVersion"`
ID int `json:"fileId"`
ID uint32 `json:"fileId"`
Name string `json:"filename"`
FileType int `json:"releaseType"`
Modloader int `json:"modLoader"`
FileType fileType `json:"releaseType"`
Modloader modloaderType `json:"modLoader"`
} `json:"latestFilesIndexes"`
ModLoaders []string `json:"modLoaders"`
Links struct {
@ -162,12 +170,12 @@ type modInfo struct {
} `json:"links"`
}
func (c *cfApiClient) getModInfo(modID int) (modInfo, error) {
func (c *cfApiClient) getModInfo(modID uint32) (modInfo, error) {
var infoRes struct {
Data modInfo `json:"data"`
}
idStr := strconv.Itoa(modID)
idStr := strconv.FormatUint(uint64(modID), 10)
resp, err := c.makeGet("/v1/mods/" + idStr)
if err != nil {
return modInfo{}, fmt.Errorf("failed to request addon data for ID %d: %w", modID, err)
@ -185,13 +193,13 @@ func (c *cfApiClient) getModInfo(modID int) (modInfo, error) {
return infoRes.Data, nil
}
func (c *cfApiClient) getModInfoMultiple(modIDs []int) ([]modInfo, error) {
func (c *cfApiClient) getModInfoMultiple(modIDs []uint32) ([]modInfo, error) {
var infoRes struct {
Data []modInfo `json:"data"`
}
modIDsData, err := json.Marshal(struct {
ModIDs []int `json:"modIds"`
ModIDs []uint32 `json:"modIds"`
}{
ModIDs: modIDs,
})
@ -214,32 +222,31 @@ func (c *cfApiClient) getModInfoMultiple(modIDs []int) ([]modInfo, error) {
// modFileInfo is a subset of the deserialised JSON response from the Curse API for mod files
type modFileInfo struct {
ID int `json:"id"`
ModID int `json:"modId"`
ID uint32 `json:"id"`
ModID uint32 `json:"modId"`
FileName string `json:"fileName"`
FriendlyName string `json:"displayName"`
Date time.Time `json:"fileDate"`
Length int `json:"fileLength"`
FileType int `json:"releaseType"`
// fileStatus? means latest/preferred?
Length uint64 `json:"fileLength"`
FileType fileType `json:"releaseType"`
// According to the CurseForge API T&Cs, this must not be saved or cached
DownloadURL string `json:"downloadUrl"`
GameVersions []string `json:"gameVersions"`
Fingerprint int `json:"fileFingerprint"`
Fingerprint uint32 `json:"fileFingerprint"`
Dependencies []struct {
ModID int `json:"modId"`
Type int `json:"relationType"`
ModID uint32 `json:"modId"`
Type dependencyType `json:"relationType"`
} `json:"dependencies"`
Hashes []struct {
Value string `json:"value"`
Algorithm int `json:"algo"`
Algorithm hashAlgo `json:"algo"`
} `json:"hashes"`
}
func (i modFileInfo) getBestHash() (hash string, hashFormat string) {
// TODO: check if the hash is invalid (e.g. 0)
hash = strconv.Itoa(i.Fingerprint)
hash = strconv.FormatUint(uint64(i.Fingerprint), 10)
hashFormat = "murmur2"
hashPreferred := 0
@ -263,13 +270,13 @@ func (i modFileInfo) getBestHash() (hash string, hashFormat string) {
return
}
func (c *cfApiClient) getFileInfo(modID int, fileID int) (modFileInfo, error) {
func (c *cfApiClient) getFileInfo(modID uint32, fileID uint32) (modFileInfo, error) {
var infoRes struct {
Data modFileInfo `json:"data"`
}
modIDStr := strconv.Itoa(modID)
fileIDStr := strconv.Itoa(fileID)
modIDStr := strconv.FormatUint(uint64(modID), 10)
fileIDStr := strconv.FormatUint(uint64(fileID), 10)
resp, err := c.makeGet("/v1/mods/" + modIDStr + "/files/" + fileIDStr)
if err != nil {
@ -288,13 +295,13 @@ func (c *cfApiClient) getFileInfo(modID int, fileID int) (modFileInfo, error) {
return infoRes.Data, nil
}
func (c *cfApiClient) getFileInfoMultiple(fileIDs []int) ([]modFileInfo, error) {
func (c *cfApiClient) getFileInfoMultiple(fileIDs []uint32) ([]modFileInfo, error) {
var infoRes struct {
Data []modFileInfo `json:"data"`
}
fileIDsData, err := json.Marshal(struct {
FileIDs []int `json:"fileIds"`
FileIDs []uint32 `json:"fileIds"`
}{
FileIDs: fileIDs,
})
@ -315,16 +322,16 @@ func (c *cfApiClient) getFileInfoMultiple(fileIDs []int) ([]modFileInfo, error)
return infoRes.Data, nil
}
func (c *cfApiClient) getSearch(searchTerm string, slug string, gameID int, classID int, categoryID int, gameVersion string, modloaderType int) ([]modInfo, error) {
func (c *cfApiClient) getSearch(searchTerm string, slug string, gameID uint32, classID uint32, categoryID uint32, gameVersion string, modloaderType modloaderType) ([]modInfo, error) {
var infoRes struct {
Data []modInfo `json:"data"`
}
q := url.Values{}
q.Set("gameId", strconv.Itoa(gameID))
q.Set("gameId", strconv.FormatUint(uint64(gameID), 10))
q.Set("pageSize", "10")
if classID != 0 {
q.Set("classId", strconv.Itoa(classID))
q.Set("classId", strconv.FormatUint(uint64(classID), 10))
}
if slug != "" {
q.Set("slug", slug)
@ -332,7 +339,7 @@ func (c *cfApiClient) getSearch(searchTerm string, slug string, gameID int, clas
// If classID and slug are provided, don't bother filtering by anything else (should be unique)
if classID == 0 && slug == "" {
if categoryID != 0 {
q.Set("categoryId", strconv.Itoa(categoryID))
q.Set("categoryId", strconv.FormatUint(uint64(categoryID), 10))
}
if searchTerm != "" {
q.Set("searchFilter", searchTerm)
@ -341,7 +348,7 @@ func (c *cfApiClient) getSearch(searchTerm string, slug string, gameID int, clas
q.Set("gameVersion", gameVersion)
}
if modloaderType != modloaderTypeAny {
q.Set("modLoaderType", strconv.Itoa(modloaderType))
q.Set("modLoaderType", strconv.FormatUint(uint64(modloaderType), 10))
}
}
@ -358,9 +365,11 @@ func (c *cfApiClient) getSearch(searchTerm string, slug string, gameID int, clas
return infoRes.Data, nil
}
type gameStatus uint8
//noinspection GoUnusedConst
const (
gameStatusDraft int = iota + 1
gameStatusDraft gameStatus = iota + 1
gameStatusTest
gameStatusPendingReview
gameStatusRejected
@ -368,9 +377,11 @@ const (
gameStatusLive
)
type gameApiStatus uint8
//noinspection GoUnusedConst
const (
gameApiStatusPrivate int = iota + 1
gameApiStatusPrivate gameApiStatus = iota + 1
gameApiStatusPublic
)
@ -378,8 +389,8 @@ type cfGame struct {
ID uint32 `json:"id"`
Name string `json:"name"`
Slug string `json:"slug"`
Status int `json:"status"`
APIStatus int `json:"apiStatus"`
Status gameStatus `json:"status"`
APIStatus gameApiStatus `json:"apiStatus"`
}
func (c *cfApiClient) getGames() ([]cfGame, error) {
@ -401,18 +412,18 @@ func (c *cfApiClient) getGames() ([]cfGame, error) {
}
type cfCategory struct {
ID int `json:"id"`
ID uint32 `json:"id"`
Slug string `json:"slug"`
IsClass bool `json:"isClass"`
ClassID int `json:"classId"`
ClassID uint32 `json:"classId"`
}
func (c *cfApiClient) getCategories(gameID int) ([]cfCategory, error) {
func (c *cfApiClient) getCategories(gameID uint32) ([]cfCategory, error) {
var infoRes struct {
Data []cfCategory `json:"data"`
}
resp, err := c.makeGet("/v1/categories?gameId=" + strconv.Itoa(gameID))
resp, err := c.makeGet("/v1/categories?gameId=" + strconv.FormatUint(uint64(gameID), 10))
if err != nil {
return []cfCategory{}, fmt.Errorf("failed to retrieve category list for game %v: %w", gameID, err)
}
@ -428,24 +439,24 @@ func (c *cfApiClient) getCategories(gameID int) ([]cfCategory, error) {
type addonFingerprintResponse struct {
IsCacheBuilt bool `json:"isCacheBuilt"`
ExactMatches []struct {
ID int `json:"id"`
ID uint32 `json:"id"`
File modFileInfo `json:"file"`
LatestFiles []modFileInfo `json:"latestFiles"`
} `json:"exactMatches"`
ExactFingerprints []int `json:"exactFingerprints"`
PartialMatches []int `json:"partialMatches"`
ExactFingerprints []uint32 `json:"exactFingerprints"`
PartialMatches []uint32 `json:"partialMatches"`
PartialMatchFingerprints struct{} `json:"partialMatchFingerprints"`
InstalledFingerprints []int `json:"installedFingerprints"`
UnmatchedFingerprints []int `json:"unmatchedFingerprints"`
InstalledFingerprints []uint32 `json:"installedFingerprints"`
UnmatchedFingerprints []uint32 `json:"unmatchedFingerprints"`
}
func (c *cfApiClient) getFingerprintInfo(hashes []int) (addonFingerprintResponse, error) {
func (c *cfApiClient) getFingerprintInfo(hashes []uint32) (addonFingerprintResponse, error) {
var infoRes struct {
Data addonFingerprintResponse `json:"data"`
}
hashesData, err := json.Marshal(struct {
Fingerprints []int `json:"fingerprints"`
Fingerprints []uint32 `json:"fingerprints"`
}{
Fingerprints: hashes,
})

View File

@ -56,7 +56,7 @@ type Mod struct {
} `json:"license"`
ClientSide string `json:"client_side"` //The support range for the client mod - required, optional, unsupported, or unknown
ServerSide string `json:"server_side"` //The support range for the server mod - required, optional, unsupported, or unknown
Downloads int `json:"downloads"` //The total number of downloads the mod has
Downloads uint32 `json:"downloads"` //The total number of downloads the mod has
Categories []string `json:"categories"` //A list of the categories that the mod is in
Versions []string `json:"versions"` //A list of ids for versions of the mod
IconUrl string `json:"icon_url"` //The URL of the icon of the mod (Optional)
@ -74,7 +74,7 @@ type ModResult struct {
Description string `json:"description"` //A short description of the mod
Categories []string `json:"categories"` //A list of the categories the mod is in
Versions []string `json:"versions"` //A list of the minecraft versions supported by the mod
Downloads int `json:"downloads"` //The total number of downloads for the mod
Downloads uint32 `json:"downloads"` //The total number of downloads for the mod
PageUrl string `json:"page_url"` //A link to the mod's main page;
IconUrl string `json:"icon_url"` //The url of the mod's icon
AuthorUrl string `json:"author_url"` //The url of the mod's author
@ -89,9 +89,9 @@ type ModResult struct {
type ModSearchResult struct {
Hits []ModResult `json:"hits"` //The list of results
Offset int `json:"offset"` //The number of results that were skipped by the query
Limit int `json:"limit"` //The number of mods returned by the query
TotalHits int `json:"total_hits"` //The total number of mods that the query found
Offset uint32 `json:"offset"` //The number of results that were skipped by the query
Limit uint32 `json:"limit"` //The number of mods returned by the query
TotalHits uint32 `json:"total_hits"` //The total number of mods that the query found
}
type Version struct {
@ -103,7 +103,7 @@ type Version struct {
VersionNumber string `json:"version_number"` //The version number. Ideally will follow semantic versioning
Changelog string `json:"changelog"` //The changelog for this version of the mod. (Optional)
DatePublished string `json:"date_published"` //The date that this version was published
Downloads int `json:"downloads"` //The number of downloads this specific version has
Downloads uint32 `json:"downloads"` //The number of downloads this specific version has
VersionType string `json:"version_type"` //The type of the release - alpha, beta, or release
Files []VersionFile `json:"files"` //A list of files available for download for this version
//Dependencies []string `json:"dependencies"` //A list of specific versions of mods that this version depends on

View File

@ -1,7 +1,7 @@
package modrinth
type Pack struct {
FormatVersion int `json:"formatVersion"`
FormatVersion uint32 `json:"formatVersion"`
Game string `json:"game"`
VersionID string `json:"versionId"`
Name string `json:"name"`