Skip to content

Commit 52952bb

Browse files
committed
Add ability to search by UUID
1 parent 60047f5 commit 52952bb

File tree

3 files changed

+113
-11
lines changed

3 files changed

+113
-11
lines changed

cache.go

+27-3
Original file line numberDiff line numberDiff line change
@@ -18,12 +18,13 @@ func SetupRedis(){
1818
})
1919
}
2020

21-
func StoreData(ctx context.Context, username string, response string) error {
21+
func StoreData(ctx context.Context, username string, uuid string, response string) error {
2222
client.Set(ctx, fmt.Sprintf("player:%s", username), response, time.Hour * 24)
23+
client.Set(ctx, fmt.Sprintf("uuid:%s", uuid), response, time.Hour * 24)
2324
return nil
2425
}
2526

26-
func HasData(ctx context.Context, username string) (bool, error) {
27+
func HasDataFromUsername(ctx context.Context, username string) (bool, error) {
2728
value, err := client.Exists(ctx, fmt.Sprintf("player:%s", username)).Result()
2829
if err == redis.Nil {
2930
return false, nil
@@ -36,7 +37,20 @@ func HasData(ctx context.Context, username string) (bool, error) {
3637
return true, nil
3738
}
3839

39-
func GetData(ctx context.Context, username string) (*string, error) {
40+
func HasDataFromUUID(ctx context.Context, uuid string) (bool, error) {
41+
value, err := client.Exists(ctx, fmt.Sprintf("uuid:%s", uuid)).Result()
42+
if err == redis.Nil {
43+
return false, nil
44+
} else if err != nil {
45+
return false, nil
46+
}
47+
if value == 0 {
48+
return false, nil
49+
}
50+
return true, nil
51+
}
52+
53+
func GetDataFromUsername(ctx context.Context, username string) (*string, error) {
4054
value, err := client.Get(ctx, fmt.Sprintf("player:%s", username)).Result()
4155
if err == redis.Nil {
4256
return nil, fmt.Errorf("does not exist")
@@ -45,3 +59,13 @@ func GetData(ctx context.Context, username string) (*string, error) {
4559
}
4660
return &value, nil
4761
}
62+
63+
func GetDataFromUUID(ctx context.Context, uuid string) (*string, error) {
64+
value, err := client.Get(ctx, fmt.Sprintf("uuid:%s", uuid)).Result()
65+
if err == redis.Nil {
66+
return nil, fmt.Errorf("does not exist")
67+
} else if err != nil {
68+
return nil, err
69+
}
70+
return &value, nil
71+
}

main.go

+69-6
Original file line numberDiff line numberDiff line change
@@ -5,14 +5,17 @@ import (
55
"encoding/base64"
66
"encoding/json"
77
"fmt"
8-
"github.com/google/uuid"
8+
uuid2 "github.com/google/uuid"
99
"github.com/gorilla/mux"
1010
"github.com/joho/godotenv"
1111
"image/png"
1212
"mymcuu.id/api/mojang"
1313
"net/http"
14+
"os"
1415
)
1516

17+
var CORS = "https://mymcuu.id"
18+
1619
type JsonError struct {
1720
Error string `json:"error"`
1821
}
@@ -23,7 +26,7 @@ type UUIDResponse struct {
2326
Avatar string `json:"avatar"`
2427
}
2528
func setupResponse(w *http.ResponseWriter, req *http.Request) {
26-
(*w).Header().Set("Access-Control-Allow-Origin", "https://mymcuu.id")
29+
(*w).Header().Set("Access-Control-Allow-Origin", CORS)
2730
(*w).Header().Set("Access-Control-Allow-Methods", "GET, OPTIONS")
2831
(*w).Header().Set("Access-Control-Allow-Headers", "Accept, Content-Type, Content-Length, Accept-Encoding, X-CSRF-Token, Authorization")
2932
}
@@ -41,8 +44,8 @@ func GetUUIDFromUsername(w http.ResponseWriter, r *http.Request) {
4144
}
4245
vars := mux.Vars(r)
4346
username := vars["username"]
44-
if ok, _ := HasData(r.Context(), username); ok {
45-
resp, err := GetData(r.Context(), username)
47+
if ok, _ := HasDataFromUsername(r.Context(), username); ok {
48+
resp, err := GetDataFromUsername(r.Context(), username)
4649
if err != nil {
4750
fmt.Fprintf(w, ErrorJson(err.Error()))
4851
return
@@ -62,7 +65,7 @@ func GetUUIDFromUsername(w http.ResponseWriter, r *http.Request) {
6265
headImage, err := mojang.GetHeadFromUUID(resp.UUID)
6366
buf := new(bytes.Buffer)
6467
png.Encode(buf, *headImage)
65-
withDashes, err := uuid.Parse(resp.UUID)
68+
withDashes, err := uuid2.Parse(resp.UUID)
6669
if err != nil {
6770
fmt.Fprintf(w, ErrorJson(err.Error()))
6871
return
@@ -77,7 +80,7 @@ func GetUUIDFromUsername(w http.ResponseWriter, r *http.Request) {
7780
return
7881
}
7982
jsonResponse := string(bytes)
80-
err = StoreData(r.Context(), username, jsonResponse)
83+
err = StoreData(r.Context(), username, withDashes.String(), jsonResponse)
8184
if err != nil {
8285
fmt.Printf("failed to save %s to cache", username)
8386
return
@@ -101,14 +104,74 @@ func GetHeadFromUUID(w http.ResponseWriter, r *http.Request){
101104
png.Encode(w, *resp)
102105
}
103106

107+
func GetUsernameFromUUID(w http.ResponseWriter, r *http.Request) {
108+
setupResponse(&w, r)
109+
if (*r).Method == "OPTIONS" {
110+
return
111+
}
112+
vars := mux.Vars(r)
113+
uuid := vars["uuid"]
114+
parsedUUID, err := uuid2.Parse(uuid)
115+
if err != nil {
116+
fmt.Fprintf(w, ErrorJson("invalid uuid"))
117+
return
118+
}
119+
if ok, _ := HasDataFromUUID(r.Context(), parsedUUID.String()); ok {
120+
resp, err := GetDataFromUUID(r.Context(), parsedUUID.String())
121+
if err != nil {
122+
fmt.Fprintf(w, ErrorJson(err.Error()))
123+
return
124+
}
125+
if resp != nil {
126+
w.WriteHeader(http.StatusOK)
127+
fmt.Fprintf(w, *resp)
128+
return
129+
}
130+
}
131+
profile, err := mojang.GetProfileFromUUID(uuid)
132+
w.Header().Set("Content-Type", "application/json")
133+
if err != nil {
134+
fmt.Fprintf(w, ErrorJson(err.Error()))
135+
return
136+
}
137+
headImage, err := mojang.GetHeadFromProfile(*profile)
138+
buf := new(bytes.Buffer)
139+
png.Encode(buf, *headImage)
140+
if err != nil {
141+
fmt.Fprintf(w, ErrorJson(err.Error()))
142+
return
143+
}
144+
bytes, err := json.Marshal(UUIDResponse{
145+
UUID: parsedUUID.String(),
146+
Username: profile.Name,
147+
Avatar: fmt.Sprintf("data:image/png;base64,%s", base64.StdEncoding.EncodeToString(buf.Bytes())),
148+
})
149+
if err != nil {
150+
fmt.Fprintf(w, ErrorJson(err.Error()))
151+
return
152+
}
153+
jsonResponse := string(bytes)
154+
err = StoreData(r.Context(), profile.Name, parsedUUID.String(), jsonResponse)
155+
if err != nil {
156+
fmt.Printf("failed to save %s to cache", profile.Name)
157+
return
158+
}
159+
w.WriteHeader(http.StatusOK)
160+
fmt.Fprintf(w, jsonResponse)
161+
}
162+
104163
func main(){
105164
err := godotenv.Load()
106165
if err != nil {
107166
//log.Fatal("Error loading .env file")
108167
}
168+
if len(os.Getenv("CORS")) > 0 {
169+
CORS = os.Getenv("CORS")
170+
}
109171
SetupRedis()
110172
r := mux.NewRouter()
111173
r.HandleFunc("/username/{username}", GetUUIDFromUsername)
174+
r.HandleFunc("/uuid/{uuid}", GetUsernameFromUUID)
112175
r.HandleFunc("/head/{uuid}", GetHeadFromUUID)
113176
http.Handle("/", r)
114177
http.ListenAndServe(":8080", nil)

mojang/api.go

+17-2
Original file line numberDiff line numberDiff line change
@@ -72,11 +72,10 @@ func GetUUIDFromUsername(username string) (*UUIDResponse, error) {
7272
return nil, fmt.Errorf("no such player")
7373
}
7474

75-
func GetHeadFromUUID(uuid string) (*image2.Image, error) {
75+
func GetProfileFromUUID(uuid string) (*ProfileResponse, error) {
7676
if len(uuid) < 1 {
7777
return nil, fmt.Errorf("invalid uuid")
7878
}
79-
fmt.Print()
8079
request, err := http.NewRequest("GET", fmt.Sprintf("https://sessionserver.mojang.com/session/minecraft/profile/%s", uuid), nil)
8180
request.Header.Set("User-Agent", "MyMCUUID-API")
8281
resp, err := client.Do(request)
@@ -92,6 +91,10 @@ func GetHeadFromUUID(uuid string) (*image2.Image, error) {
9291
if err != nil {
9392
return nil, err
9493
}
94+
return &profile, nil
95+
}
96+
97+
func GetHeadFromProfile(profile ProfileResponse) (*image2.Image, error) {
9598
var texture *TextureInformation
9699
for _, val := range profile.Properties {
97100
if val.Name == "textures" {
@@ -122,6 +125,18 @@ func GetHeadFromUUID(uuid string) (*image2.Image, error) {
122125
return nil, fmt.Errorf("something went wrong")
123126
}
124127

128+
func GetHeadFromUUID(uuid string) (*image2.Image, error) {
129+
profile, err := GetProfileFromUUID(uuid)
130+
if err != nil {
131+
return nil, err
132+
}
133+
image, err := GetHeadFromProfile(*profile)
134+
if err != nil {
135+
return nil, err
136+
}
137+
return image, nil
138+
}
139+
125140
func GetImage(imageURL string) (io.ReadCloser, error) {
126141
request, err := http.NewRequest("GET", imageURL, nil)
127142
request.Header.Set("User-Agent", "MyMCUUID-API")

0 commit comments

Comments
 (0)