Skip to content

Commit

Permalink
fix non standard UUIDs in slp response
Browse files Browse the repository at this point in the history
  • Loading branch information
Sch8ill committed Jan 8, 2024
1 parent d292d3f commit b3312c1
Showing 1 changed file with 41 additions and 0 deletions.
41 changes: 41 additions & 0 deletions slp/response.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,12 @@ import (
"encoding/json"
"errors"
"fmt"
"regexp"
"strings"
)

const MaxUUIDLen int = 32

// Response represents the Server List Ping (SLP) response.
type Response struct {
// Documentation link:
Expand Down Expand Up @@ -47,6 +50,27 @@ type Player struct {
ID string `json:"id"`
}

// UnmarshalJSON unmarshalls a player into a Player.
// It ensures that the player is parsed successfully, even if the ID is not a string.
// Not all Minecraft servers respond with correct player IDs.
// For example 2b2t.org: {"name":"§6In-game: 326","id":[0,1,0,1]}
func (p *Player) UnmarshalJSON(b []byte) error {
var raw map[string]json.RawMessage
if err := json.Unmarshal(b, &raw); err != nil {
return err
}

if err := json.Unmarshal(raw["name"], &p.Name); err != nil {
return err
}

if err := json.Unmarshal(raw["id"], &p.ID); err != nil {
p.ID = formatUUID(string(raw["id"]))
}

return nil
}

// ForgeData represents Forge mod data in the SLP response.
type ForgeData struct {
Channels []ForgeChannel `json:"channels"`
Expand Down Expand Up @@ -190,3 +214,20 @@ func (r *Response) Icon() ([]byte, error) {

return iconBytes, nil
}

// formatMinecraftUUID formats the given string as a Minecraft UUID.
func formatUUID(input string) string {
// Remove non-hex characters
re := regexp.MustCompile("[^a-fA-F0-9]")
cleaned := re.ReplaceAllString(input, "")

if len(cleaned) > 32 {
cleaned = cleaned[:32]
}

for len(cleaned) < 32 {
cleaned = cleaned + "0"
}

return cleaned[:8] + "-" + cleaned[8:12] + "-" + cleaned[12:16] + "-" + cleaned[16:20] + "-" + cleaned[20:]
}

0 comments on commit b3312c1

Please sign in to comment.