-
Notifications
You must be signed in to change notification settings - Fork 116
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
5 changed files
with
445 additions
and
445 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,58 +1,58 @@ | ||
package main | ||
|
||
import ( | ||
"fmt" | ||
"os" | ||
"path/filepath" | ||
"strings" | ||
|
||
"github.com/google/uuid" | ||
) | ||
|
||
func readAdvancements(dir string, m map[uuid.UUID]UserCache) { | ||
entries, err := os.ReadDir(dir) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to open playerdata folder: %v", err) | ||
return | ||
} | ||
for _, files := range entries { | ||
filename := files.Name() | ||
if ext := filepath.Ext(filename); ext != ".json" { | ||
fmt.Fprintf(os.Stderr, "Unkown file type: %s\n", ext) | ||
continue | ||
} | ||
|
||
// Parse old UUID from filename | ||
oldID, err := uuid.Parse(strings.TrimSuffix(filename, ".json")) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Unable to parse filename as uuid: %v\n", err) | ||
continue | ||
} | ||
|
||
if ver := oldID.Version(); ver != 3 { // v3 is for offline players | ||
fmt.Printf("Ignoring UUID: %v version: %d\n", oldID, ver) | ||
continue | ||
} | ||
|
||
newUser, ok := m[oldID] | ||
if !ok { | ||
fmt.Printf("Skip user: %v\n", oldID) | ||
continue | ||
} | ||
|
||
content, err := os.ReadFile(filepath.Join(dir, filename)) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to read json file: %v\n", err) | ||
continue | ||
} | ||
|
||
newFile := newUser.UUID.String() + ".json" | ||
err = os.WriteFile(filepath.Join(dir, newFile), content, 0o666) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to write json file: %v\n", err) | ||
continue | ||
} | ||
|
||
fmt.Printf("Converted advancement file: %s\n", newFile) | ||
} | ||
} | ||
package main | ||
|
||
import ( | ||
"fmt" | ||
"os" | ||
"path/filepath" | ||
"strings" | ||
|
||
"github.com/google/uuid" | ||
) | ||
|
||
func readAdvancements(dir string, m map[uuid.UUID]UserCache) { | ||
entries, err := os.ReadDir(dir) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to open playerdata folder: %v", err) | ||
return | ||
} | ||
for _, files := range entries { | ||
filename := files.Name() | ||
if ext := filepath.Ext(filename); ext != ".json" { | ||
fmt.Fprintf(os.Stderr, "Unkown file type: %s\n", ext) | ||
continue | ||
} | ||
|
||
// Parse old UUID from filename | ||
oldID, err := uuid.Parse(strings.TrimSuffix(filename, ".json")) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Unable to parse filename as uuid: %v\n", err) | ||
continue | ||
} | ||
|
||
if ver := oldID.Version(); ver != 3 { // v3 is for offline players | ||
fmt.Printf("Ignoring UUID: %v version: %d\n", oldID, ver) | ||
continue | ||
} | ||
|
||
newUser, ok := m[oldID] | ||
if !ok { | ||
fmt.Printf("Skip user: %v\n", oldID) | ||
continue | ||
} | ||
|
||
content, err := os.ReadFile(filepath.Join(dir, filename)) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to read json file: %v\n", err) | ||
continue | ||
} | ||
|
||
newFile := newUser.UUID.String() + ".json" | ||
err = os.WriteFile(filepath.Join(dir, newFile), content, 0o666) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to write json file: %v\n", err) | ||
continue | ||
} | ||
|
||
fmt.Printf("Converted advancement file: %s\n", newFile) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,90 +1,90 @@ | ||
// playerdataconvert is a program to convert player data form offline server to online server. | ||
// | ||
// When a player with official account login connect to a offline-mode server, | ||
// the server store the player data with their "offline UUID". While you open | ||
// the online-mode switch, the player data loose. | ||
// | ||
// By using this tool, you can convert the offline data into online data. | ||
// The players will keep everything they got, yay! | ||
package main | ||
|
||
import ( | ||
"encoding/json" | ||
"flag" | ||
"fmt" | ||
"os" | ||
"path/filepath" | ||
|
||
"github.com/google/uuid" | ||
) | ||
|
||
var ( | ||
savePath = flag.String("save", ".", "The save folder with \"usercache.json\" file inside") | ||
convertPlayerData = flag.Bool("cplayerdata", true, "Whether convert files at /world/playerdata/*.dat") | ||
convertEntities = flag.Bool("centities", true, "Whether convert pets' Owner at /world/entities/*") | ||
convertAdvancements = flag.Bool("cadvancements", true, "Whether convert advancements at /world/advancements/*") | ||
) | ||
|
||
func main() { | ||
flag.Parse() | ||
|
||
usercaches, err := readUsercache(filepath.Join(*savePath, "usercache.json")) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to parse usercache file: %v\n", err) | ||
return | ||
} | ||
fmt.Printf("Successfully reading usercache\n") | ||
m := mappingUsers(usercaches) | ||
|
||
if *convertPlayerData { | ||
readPlayerdata(filepath.Join(*savePath, "world", "playerdata"), m) | ||
} | ||
|
||
if *convertEntities { | ||
readEntities(filepath.Join(*savePath, "world", "entities"), m) | ||
} | ||
|
||
if *convertAdvancements { | ||
readAdvancements(filepath.Join(*savePath, "world", "advancements"), m) | ||
} | ||
} | ||
|
||
type UserCache struct { | ||
Name string `json:"name"` | ||
UUID uuid.UUID `json:"uuid"` | ||
} | ||
|
||
func readUsercache(path string) ([]UserCache, error) { | ||
data, err := os.ReadFile(path) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
var usercache []UserCache | ||
err = json.Unmarshal(data, &usercache) | ||
if err != nil { | ||
return nil, err | ||
} | ||
return usercache, nil | ||
} | ||
|
||
func mappingUsers(users []UserCache) map[uuid.UUID]UserCache { | ||
m := make(map[uuid.UUID]UserCache) | ||
for _, user := range users { | ||
name := user.Name | ||
// // You can add your maps here | ||
// if v, ok := offlineOnlineMaps[name]; ok { | ||
// name = v | ||
// } | ||
|
||
name, id, err := usernameToUUID(name) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Unable to fetch username for %s from Mojang server: %v\n", name, err) | ||
continue | ||
} | ||
|
||
fmt.Printf("[%s] %v -> %v\n", name, user.UUID, id) | ||
m[user.UUID] = UserCache{name, id} | ||
} | ||
return m | ||
} | ||
// playerdataconvert is a program to convert player data form offline server to online server. | ||
// | ||
// When a player with official account login connect to a offline-mode server, | ||
// the server store the player data with their "offline UUID". While you open | ||
// the online-mode switch, the player data loose. | ||
// | ||
// By using this tool, you can convert the offline data into online data. | ||
// The players will keep everything they got, yay! | ||
package main | ||
|
||
import ( | ||
"encoding/json" | ||
"flag" | ||
"fmt" | ||
"os" | ||
"path/filepath" | ||
|
||
"github.com/google/uuid" | ||
) | ||
|
||
var ( | ||
savePath = flag.String("save", ".", "The save folder with \"usercache.json\" file inside") | ||
convertPlayerData = flag.Bool("cplayerdata", true, "Whether convert files at /world/playerdata/*.dat") | ||
convertEntities = flag.Bool("centities", true, "Whether convert pets' Owner at /world/entities/*") | ||
convertAdvancements = flag.Bool("cadvancements", true, "Whether convert advancements at /world/advancements/*") | ||
) | ||
|
||
func main() { | ||
flag.Parse() | ||
|
||
usercaches, err := readUsercache(filepath.Join(*savePath, "usercache.json")) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to parse usercache file: %v\n", err) | ||
return | ||
} | ||
fmt.Printf("Successfully reading usercache\n") | ||
m := mappingUsers(usercaches) | ||
|
||
if *convertPlayerData { | ||
readPlayerdata(filepath.Join(*savePath, "world", "playerdata"), m) | ||
} | ||
|
||
if *convertEntities { | ||
readEntities(filepath.Join(*savePath, "world", "entities"), m) | ||
} | ||
|
||
if *convertAdvancements { | ||
readAdvancements(filepath.Join(*savePath, "world", "advancements"), m) | ||
} | ||
} | ||
|
||
type UserCache struct { | ||
Name string `json:"name"` | ||
UUID uuid.UUID `json:"uuid"` | ||
} | ||
|
||
func readUsercache(path string) ([]UserCache, error) { | ||
data, err := os.ReadFile(path) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
var usercache []UserCache | ||
err = json.Unmarshal(data, &usercache) | ||
if err != nil { | ||
return nil, err | ||
} | ||
return usercache, nil | ||
} | ||
|
||
func mappingUsers(users []UserCache) map[uuid.UUID]UserCache { | ||
m := make(map[uuid.UUID]UserCache) | ||
for _, user := range users { | ||
name := user.Name | ||
// // You can add your maps here | ||
// if v, ok := offlineOnlineMaps[name]; ok { | ||
// name = v | ||
// } | ||
|
||
name, id, err := usernameToUUID(name) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Unable to fetch username for %s from Mojang server: %v\n", name, err) | ||
continue | ||
} | ||
|
||
fmt.Printf("[%s] %v -> %v\n", name, user.UUID, id) | ||
m[user.UUID] = UserCache{name, id} | ||
} | ||
return m | ||
} |
Oops, something went wrong.