From e8ea58cea084bb9aa0dd8a923d60af3976b9b523 Mon Sep 17 00:00:00 2001 From: mountain Date: Fri, 10 Nov 2023 16:41:40 +0900 Subject: [PATCH] =?UTF-8?q?=ED=8C=8C=ED=8B=B0=20=EC=9E=AC=EC=B0=B8?= =?UTF-8?q?=EC=97=AC=20=EB=A1=9C=EC=A7=81=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- core/group_party.go | 126 +++++++++++++++++++++++++++++--------------- 1 file changed, 84 insertions(+), 42 deletions(-) diff --git a/core/group_party.go b/core/group_party.go index c286c6f..efbea50 100644 --- a/core/group_party.go +++ b/core/group_party.go @@ -9,7 +9,6 @@ import ( "time" "github.com/go-redis/redis/v8" - "github.com/gorilla/websocket" "repositories.action2quare.com/ayo/gocommon" "repositories.action2quare.com/ayo/gocommon/logger" "repositories.action2quare.com/ayo/gocommon/wshandler" @@ -311,48 +310,89 @@ func (gp *groupParty) JoinParty(w http.ResponseWriter, r *http.Request) { } // 내 정보 업데이트할 때에도 사용됨 - if data.First { - if memdoc, err := gd.addMember(mid, character); err == nil { - // 기존 유저에게 새 유저 알림 - gp.sendUpstreamMessage(&wshandler.UpstreamMessage{ - Target: "#" + gid.Hex(), - Body: map[string]any{ - gd.tid(mid): memdoc, - }, - Tag: []string{"MemberDocFull"}, - }) - - gp.enterRoom(gid, mid) - - // 최초 입장이라면 새 멤버에 그룹 전체를 알림 - gp.sendUpstreamMessage(&wshandler.UpstreamMessage{ - Target: mid.Hex(), - Body: gd.loadFull(), - Tag: []string{"GroupDocFull"}, - }) - } else if err != nil { - logger.Error("JoinParty failed :", err) - w.WriteHeader(http.StatusInternalServerError) - } - } else { + if !data.First { + // 이미 멤버여야 재입장 가능 path := "$._members." + gd.tid(mid) + "._body" if _, err := gd.rh.JSONSet(gd.strid(), path, character, gocommon.RedisonSetOptionXX); err != nil { + // 멤버가 아니네? logger.Error("JoinParty failed :", err) w.WriteHeader(http.StatusInternalServerError) return } + } + + gp.rh.JSONSet(mid.Hex(), "$.party", bson.M{"id": gid.Hex()}) + memdoc, err := gd.addMember(mid, character) + if err != nil { + logger.Error("JoinParty failed :", err) + w.WriteHeader(http.StatusInternalServerError) + return + } + + // 기존 유저에게 새 유저 알림 + gp.sendUpstreamMessage(&wshandler.UpstreamMessage{ + Target: "#" + gid.Hex(), + Body: map[string]any{ + gd.tid(mid): memdoc, + }, + Tag: []string{"MemberDocFull"}, + }) + + gp.enterRoom(gid, mid) + + gp.sendUpstreamMessage(&wshandler.UpstreamMessage{ + Target: mid.Hex(), + Body: gd.loadFull(), + Tag: []string{"GroupDocFull"}, + }) +} + +func (gp *groupParty) ConditionalClearPartyMember(w http.ResponseWriter, r *http.Request) { + var doc struct { + Gid string + Mid string + } + + // accid가 접속해 있지 않으면 파티에서 나간 걸로 간주하고 + // accid가 접속해 있으면 아무것도 하지 않는다. + if err := gocommon.MakeDecoder(r).Decode(&doc); err != nil { + logger.Println("ConditionalClearPartyMember failed. DecodeGob returns err :", err) + w.WriteHeader(http.StatusInternalServerError) + return + } + + pids, err := gp.rh.JSONGetString(doc.Mid, "$.party.id") + if err != nil { + logger.Error("ConditionalClearPartyMember failed. gp.rh.JSONGetString returns err :", err) + w.WriteHeader(http.StatusInternalServerError) + return + } + + removeMember := func() { + gid, _ := primitive.ObjectIDFromHex(doc.Gid) + mid, _ := primitive.ObjectIDFromHex(doc.Mid) + gd := partyDoc{ + id: gid, + rh: gp.rh, + } + gd.removeMember(mid) - // 기존 유저에게 캐릭터 알림 gp.sendUpstreamMessage(&wshandler.UpstreamMessage{ - Target: "#" + gid.Hex(), - Body: map[string]any{ - gd.tid(mid): bson.M{ - "_body": character, - }, + Target: "#" + doc.Gid, + Body: bson.M{ + gd.tid(mid): bson.M{}, }, - Tag: []string{"MemberDocFragment"}, + Tag: []string{"MemberDocFull"}, }) + } + if len(pids) == 0 { + // 없다. + // doc.Gid에서 제거 + removeMember() + } else if pids[0] != doc.Gid { + // 다른 파티? 기존 파티에서 제거 + removeMember() } } @@ -716,7 +756,8 @@ func (gp *groupParty) find(id groupID) (*partyDoc, error) { id: id, }, nil } -func (gp *groupParty) ClientDisconnected(conn *websocket.Conn, callby *wshandler.Sender) { + +func (gp *groupParty) ClientDisconnected(msg string, callby *wshandler.Sender) { gids, _ := gp.rh.JSONGetString(callby.Accid.Hex(), "$.party.id") if len(gids) > 0 && len(gids[0]) > 0 { @@ -727,15 +768,16 @@ func (gp *groupParty) ClientDisconnected(conn *websocket.Conn, callby *wshandler // 나를 먼저 룸에서 빼야 나한테 메시지가 안감 gp.leaveRoom(gid, callby.Accid) - // gid에는 제거 메시지 보냄 - gp.sendUpstreamMessage(&wshandler.UpstreamMessage{ - Target: "#" + gidstr, - Body: bson.M{ - makeTid(gid, callby.Accid): bson.M{}, - }, - Tag: []string{"MemberDocFull"}, - }) - + if msg != "pending" { + // gid에는 제거 메시지 보냄 + gp.sendUpstreamMessage(&wshandler.UpstreamMessage{ + Target: "#" + gidstr, + Body: bson.M{ + makeTid(gid, callby.Accid): bson.M{}, + }, + Tag: []string{"MemberDocFull"}, + }) + } } }