mirror of
https://github.com/originalmk/archat-server.git
synced 2025-01-18 16:29:17 +00:00
Finished implementation for B, C, D stages of initiation
This commit is contained in:
parent
d5b891e4f5
commit
62e3ee780b
@ -1,5 +1,6 @@
|
|||||||
# 🔀 Archat
|
# 🔀 Archat
|
||||||
*It is not working application yet, work in progress!*
|
*It is not working application yet, work in progress!*
|
||||||
|
|
||||||
Simple P2P server (and client - for testing purposes only, client for end user will be written in NodeJS using Electron, soon).
|
Simple P2P server (and client - for testing purposes only, client for end user will be written in NodeJS using Electron, soon).
|
||||||
|
|
||||||
## Starting
|
## Starting
|
||||||
|
124
client/client.go
124
client/client.go
@ -7,8 +7,10 @@ import (
|
|||||||
"golang.org/x/sync/errgroup"
|
"golang.org/x/sync/errgroup"
|
||||||
"net/url"
|
"net/url"
|
||||||
"os"
|
"os"
|
||||||
|
"slices"
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
|
"sync"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/charmbracelet/log"
|
"github.com/charmbracelet/log"
|
||||||
@ -23,6 +25,8 @@ type Context struct {
|
|||||||
resFromServer chan cm.RFrame
|
resFromServer chan cm.RFrame
|
||||||
reqFromServer chan cm.RFrame
|
reqFromServer chan cm.RFrame
|
||||||
rToServer chan cm.RFrame
|
rToServer chan cm.RFrame
|
||||||
|
initiations []*cm.Initiation
|
||||||
|
initiationsLock sync.RWMutex
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewClientContext(conn *websocket.Conn) *Context {
|
func NewClientContext(conn *websocket.Conn) *Context {
|
||||||
@ -37,6 +41,7 @@ func NewClientContext(conn *websocket.Conn) *Context {
|
|||||||
func (cliCtx *Context) serverHandler(syncCtx context.Context) error {
|
func (cliCtx *Context) serverHandler(syncCtx context.Context) error {
|
||||||
defer logger.Debug("server handler last line...")
|
defer logger.Debug("server handler last line...")
|
||||||
|
|
||||||
|
handleNext:
|
||||||
for {
|
for {
|
||||||
select {
|
select {
|
||||||
case <-syncCtx.Done():
|
case <-syncCtx.Done():
|
||||||
@ -44,23 +49,81 @@ func (cliCtx *Context) serverHandler(syncCtx context.Context) error {
|
|||||||
case reqFrame := <-cliCtx.reqFromServer:
|
case reqFrame := <-cliCtx.reqFromServer:
|
||||||
logger.Debug("got request from server", "id", reqFrame.ID)
|
logger.Debug("got request from server", "id", reqFrame.ID)
|
||||||
|
|
||||||
|
var res cm.Response
|
||||||
|
var err error
|
||||||
|
|
||||||
if reqFrame.ID == cm.EchoReqID {
|
if reqFrame.ID == cm.EchoReqID {
|
||||||
echoReq, err := cm.RequestFromFrame[cm.EchoRequest](reqFrame)
|
res, err = cliCtx.handleEcho(reqFrame)
|
||||||
|
} else if reqFrame.ID == cm.StartChatBReqID {
|
||||||
|
res, err = cliCtx.handleStartChatB(reqFrame)
|
||||||
|
} else if reqFrame.ID == cm.StartChatDReqID {
|
||||||
|
res, err = cliCtx.handleStartChatD(reqFrame)
|
||||||
|
} else {
|
||||||
|
logger.Warn("can't handle it!")
|
||||||
|
}
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
logger.Errorf("could not handle request ID=%d", reqFrame.ID)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
resFrame, err := cm.ResponseFrameFrom(cm.EchoResponse(echoReq))
|
if res == nil {
|
||||||
|
logger.Debugf("request without response ID=%d", reqFrame.ID)
|
||||||
|
continue handleNext
|
||||||
|
}
|
||||||
|
|
||||||
|
resFrame, err := cm.ResponseFrameFrom(res)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
logger.Errorf("could not create frame from response")
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
cliCtx.rToServer <- resFrame
|
cliCtx.rToServer <- resFrame
|
||||||
} else {
|
|
||||||
logger.Warn("can't handle it!")
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (cliCtx *Context) handleEcho(reqFrame cm.RFrame) (res cm.Response, err error) {
|
||||||
|
echoReq, err := cm.RequestFromFrame[cm.EchoRequest](reqFrame)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return cm.EchoResponse(echoReq), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (cliCtx *Context) handleStartChatB(reqFrame cm.RFrame) (res cm.Response, err error) {
|
||||||
|
startChatBReq, err := cm.RequestFromFrame[cm.StartChatBRequest](reqFrame)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
logger.Infof("got start chat, %s wants to contact. use startchatc command to "+
|
||||||
|
"decide if you want to accept the chat", startChatBReq.Nickname)
|
||||||
|
|
||||||
|
cliCtx.initiationsLock.Lock()
|
||||||
|
cliCtx.initiations = append(cliCtx.initiations, &cm.Initiation{
|
||||||
|
AbANick: startChatBReq.Nickname,
|
||||||
|
AbBNick: "",
|
||||||
|
Stage: cm.InitiationStageB,
|
||||||
|
})
|
||||||
|
cliCtx.initiationsLock.Unlock()
|
||||||
|
|
||||||
|
return nil, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (cliCtx *Context) handleStartChatD(reqFrame cm.RFrame) (res cm.Response, err error) {
|
||||||
|
startChatDReq, err := cm.RequestFromFrame[cm.StartChatDRequest](reqFrame)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
logger.Infof("servers wants to be punched, got start chat d request for %s with code %s",
|
||||||
|
startChatDReq.Nickname, startChatDReq.PunchCode)
|
||||||
|
logger.Warn("handleStartChatD not implemented yet")
|
||||||
|
|
||||||
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cliCtx *Context) serverWriter(syncCtx context.Context) error {
|
func (cliCtx *Context) serverWriter(syncCtx context.Context) error {
|
||||||
@ -133,7 +196,7 @@ func init() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func sendAuth(ctx *Context, nick, pass string) {
|
func sendAuth(ctx *Context, nick, pass string) {
|
||||||
logger.Info("Trying to authenticate as krzmaciek...")
|
logger.Info("trying to authenticate as krzmaciek...")
|
||||||
err := ctx.sendRequest(cm.AuthRequest{Nickname: nick, Password: pass})
|
err := ctx.sendRequest(cm.AuthRequest{Nickname: nick, Password: pass})
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -141,7 +204,7 @@ func sendAuth(ctx *Context, nick, pass string) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
logger.Debug("Request sent, waiting for response...")
|
logger.Debug("request sent, waiting for response...")
|
||||||
arf := ctx.getResponseFrame()
|
arf := ctx.getResponseFrame()
|
||||||
ar, err := cm.ResponseFromFrame[cm.AuthResponse](arf)
|
ar, err := cm.ResponseFromFrame[cm.AuthResponse](arf)
|
||||||
|
|
||||||
@ -154,7 +217,7 @@ func sendAuth(ctx *Context, nick, pass string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func sendEcho(ctx *Context, echoByte byte) {
|
func sendEcho(ctx *Context, echoByte byte) {
|
||||||
logger.Info("Testing echo...", "echoByte", echoByte)
|
logger.Info("testing echo...", "echoByte", echoByte)
|
||||||
err := ctx.sendRequest(cm.EchoRequest{EchoByte: echoByte})
|
err := ctx.sendRequest(cm.EchoRequest{EchoByte: echoByte})
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -162,7 +225,7 @@ func sendEcho(ctx *Context, echoByte byte) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
logger.Debug("Request sent, waiting for response...")
|
logger.Debug("request sent, waiting for response...")
|
||||||
ereqf := ctx.getResponseFrame()
|
ereqf := ctx.getResponseFrame()
|
||||||
ereq, err := cm.ResponseFromFrame[cm.EchoResponse](ereqf)
|
ereq, err := cm.ResponseFromFrame[cm.EchoResponse](ereqf)
|
||||||
|
|
||||||
@ -171,11 +234,11 @@ func sendEcho(ctx *Context, echoByte byte) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
logger.Info("Got response", "echoByte", ereq.EchoByte)
|
logger.Info("got response", "echoByte", ereq.EchoByte)
|
||||||
}
|
}
|
||||||
|
|
||||||
func sendListPeers(ctx *Context) {
|
func sendListPeers(ctx *Context) {
|
||||||
logger.Info("Trying to get list of peers...")
|
logger.Info("trying to get list of peers...")
|
||||||
err := ctx.sendRequest(cm.ListPeersRequest{})
|
err := ctx.sendRequest(cm.ListPeersRequest{})
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -183,7 +246,7 @@ func sendListPeers(ctx *Context) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
logger.Debug("Request sent, waiting for response...")
|
logger.Debug("request sent, waiting for response...")
|
||||||
lpreqf := ctx.getResponseFrame()
|
lpreqf := ctx.getResponseFrame()
|
||||||
lpreq, err := cm.ResponseFromFrame[cm.ListPeersResponse](lpreqf)
|
lpreq, err := cm.ResponseFromFrame[cm.ListPeersResponse](lpreqf)
|
||||||
|
|
||||||
@ -196,7 +259,7 @@ func sendListPeers(ctx *Context) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func sendStartChatA(ctx *Context, nick string) {
|
func sendStartChatA(ctx *Context, nick string) {
|
||||||
logger.Info("Doing chat start A...")
|
logger.Info("doing chat start A...")
|
||||||
err := ctx.sendRequest(cm.StartChatARequest{Nickname: nick})
|
err := ctx.sendRequest(cm.StartChatARequest{Nickname: nick})
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -204,7 +267,27 @@ func sendStartChatA(ctx *Context, nick string) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
logger.Debug("Request sent, no wait for response")
|
logger.Debug("request sent, no wait for response")
|
||||||
|
}
|
||||||
|
|
||||||
|
func sendStartChatC(ctx *Context, nick string) {
|
||||||
|
idx := slices.IndexFunc(ctx.initiations, func(i *cm.Initiation) bool {
|
||||||
|
return i.AbANick == nick
|
||||||
|
})
|
||||||
|
|
||||||
|
if idx == -1 {
|
||||||
|
logger.Warn("user of that nick did not initiate connection, ignoring")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
err := ctx.sendRequest(cm.StartChatCRequest{Nickname: nick})
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
logger.Error(err)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
logger.Debug("request sent, no wait for response")
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunClient() {
|
func RunClient() {
|
||||||
@ -297,6 +380,21 @@ func RunClient() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
sendStartChatA(cliCtx, cmdArgs[0])
|
sendStartChatA(cliCtx, cmdArgs[0])
|
||||||
|
} else if cmdName == "initations" {
|
||||||
|
logger.Info("displaying all initations...")
|
||||||
|
|
||||||
|
cliCtx.initiationsLock.RLock()
|
||||||
|
for _, i := range cliCtx.initiations {
|
||||||
|
logger.Debugf("from %s, stage: %d", i.AbANick, i.Stage)
|
||||||
|
}
|
||||||
|
cliCtx.initiationsLock.RUnlock()
|
||||||
|
} else if cmdName == "startchatc" {
|
||||||
|
if len(cmdArgs) != 1 {
|
||||||
|
logger.Errorf("startchatc command requires 1 argument, but %d was provided", len(cmdArgs))
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
sendStartChatC(cliCtx, cmdArgs[0])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}()
|
}()
|
||||||
|
@ -174,9 +174,24 @@ func (StartChatCRequest) ID() int {
|
|||||||
|
|
||||||
type StartChatDRequest struct {
|
type StartChatDRequest struct {
|
||||||
Nickname string `json:"nickname"`
|
Nickname string `json:"nickname"`
|
||||||
Accept bool `json:"accept"`
|
PunchCode string `json:"punchCode"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (StartChatDRequest) ID() int {
|
func (StartChatDRequest) ID() int {
|
||||||
return StartChatDReqID
|
return StartChatDReqID
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type Initiation struct {
|
||||||
|
AbANick string
|
||||||
|
AbBNick string
|
||||||
|
Stage int
|
||||||
|
AbAPunchCode string
|
||||||
|
AbBPunchCode string
|
||||||
|
}
|
||||||
|
|
||||||
|
const (
|
||||||
|
InitiationStageA = 1
|
||||||
|
InitiationStageB = 2
|
||||||
|
InitiationStageC = 3
|
||||||
|
InitiationStageD = 4
|
||||||
|
)
|
||||||
|
133
server/server.go
133
server/server.go
@ -2,6 +2,7 @@ package server
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"crypto/rand"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"errors"
|
"errors"
|
||||||
"net/http"
|
"net/http"
|
||||||
@ -30,26 +31,21 @@ func NewPeer(conn *websocket.Conn) *Peer {
|
|||||||
return &Peer{-1, conn, false, nil}
|
return &Peer{-1, conn, false, nil}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (p *Peer) NicknameOrEmpty() string {
|
||||||
|
if p.hasAccount {
|
||||||
|
return p.account.nickname
|
||||||
|
} else {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
type Account struct {
|
type Account struct {
|
||||||
nickname string
|
nickname string
|
||||||
passHash []byte
|
passHash []byte
|
||||||
}
|
}
|
||||||
|
|
||||||
const (
|
func NewInitiation(abA string, abB string) *common.Initiation {
|
||||||
InitiationStageA = 1
|
return &common.Initiation{AbANick: abA, AbBNick: abB, Stage: common.InitiationStageA}
|
||||||
InitiationStageB = 2
|
|
||||||
InitiationStageC = 3
|
|
||||||
InitiationStageD = 4
|
|
||||||
)
|
|
||||||
|
|
||||||
type Initiation struct {
|
|
||||||
abANick string
|
|
||||||
abBNick string
|
|
||||||
stage int
|
|
||||||
}
|
|
||||||
|
|
||||||
func NewInitiation(abA string, abB string) *Initiation {
|
|
||||||
return &Initiation{abA, abB, InitiationStageA}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
type Context struct {
|
type Context struct {
|
||||||
@ -59,7 +55,7 @@ type Context struct {
|
|||||||
peersListLock sync.RWMutex
|
peersListLock sync.RWMutex
|
||||||
accounts map[string]*Account
|
accounts map[string]*Account
|
||||||
accountsLock sync.RWMutex
|
accountsLock sync.RWMutex
|
||||||
initiations []*Initiation
|
initiations []*common.Initiation
|
||||||
initiationsLock sync.RWMutex
|
initiationsLock sync.RWMutex
|
||||||
handlerContexts []*HandlerContext
|
handlerContexts []*HandlerContext
|
||||||
handlerContextsLock sync.RWMutex
|
handlerContextsLock sync.RWMutex
|
||||||
@ -69,7 +65,7 @@ func NewContext() *Context {
|
|||||||
return &Context{
|
return &Context{
|
||||||
peersList: make([]*Peer, 0),
|
peersList: make([]*Peer, 0),
|
||||||
accounts: make(map[string]*Account),
|
accounts: make(map[string]*Account),
|
||||||
initiations: make([]*Initiation, 0),
|
initiations: make([]*common.Initiation, 0),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -134,6 +130,11 @@ handleNext:
|
|||||||
res, err = hdlCtx.handleEcho(&reqFrame)
|
res, err = hdlCtx.handleEcho(&reqFrame)
|
||||||
} else if reqFrame.ID == common.StartChatAReqID {
|
} else if reqFrame.ID == common.StartChatAReqID {
|
||||||
res, err = hdlCtx.handleChatStartA(&reqFrame)
|
res, err = hdlCtx.handleChatStartA(&reqFrame)
|
||||||
|
} else if reqFrame.ID == common.StartChatCReqID {
|
||||||
|
res, err = hdlCtx.handleChatStartC(&reqFrame)
|
||||||
|
} else {
|
||||||
|
logger.Warnf("can't handle request of ID=%d", reqFrame.ID)
|
||||||
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -271,10 +272,10 @@ func (ctx *Context) removePeer(peer *Peer) {
|
|||||||
return p.id == peer.id
|
return p.id == peer.id
|
||||||
})
|
})
|
||||||
|
|
||||||
ctx.initiations = slices.DeleteFunc[[]*Initiation, *Initiation](
|
ctx.initiations = slices.DeleteFunc[[]*common.Initiation, *common.Initiation](
|
||||||
ctx.initiations,
|
ctx.initiations,
|
||||||
func(i *Initiation) bool {
|
func(i *common.Initiation) bool {
|
||||||
return peer.hasAccount && (peer.account.nickname == i.abANick || peer.account.nickname == i.abBNick)
|
return peer.hasAccount && (peer.account.nickname == i.AbANick || peer.account.nickname == i.AbBNick)
|
||||||
})
|
})
|
||||||
|
|
||||||
// TODO: Inform the other side about peer leaving
|
// TODO: Inform the other side about peer leaving
|
||||||
@ -317,21 +318,13 @@ func (hdlCtx *HandlerContext) handleListPeers(reqFrame *common.RFrame) (res comm
|
|||||||
listPeersRes := common.ListPeersResponse{PeersInfo: make([]common.PeerInfo, 0)}
|
listPeersRes := common.ListPeersResponse{PeersInfo: make([]common.PeerInfo, 0)}
|
||||||
|
|
||||||
for _, peer := range peersFreeze {
|
for _, peer := range peersFreeze {
|
||||||
var nickname string
|
|
||||||
|
|
||||||
if peer.hasAccount {
|
|
||||||
nickname = peer.account.nickname
|
|
||||||
} else {
|
|
||||||
nickname = ""
|
|
||||||
}
|
|
||||||
|
|
||||||
listPeersRes.PeersInfo = append(
|
listPeersRes.PeersInfo = append(
|
||||||
listPeersRes.PeersInfo,
|
listPeersRes.PeersInfo,
|
||||||
common.PeerInfo{
|
common.PeerInfo{
|
||||||
ID: peer.id,
|
ID: peer.id,
|
||||||
Addr: peer.conn.RemoteAddr().String(),
|
Addr: peer.conn.RemoteAddr().String(),
|
||||||
HasNickname: peer.hasAccount,
|
HasNickname: peer.hasAccount,
|
||||||
Nickname: nickname,
|
Nickname: peer.NicknameOrEmpty(),
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
@ -418,47 +411,101 @@ func (hdlCtx *HandlerContext) handleChatStartA(reqFrame *common.RFrame) (res com
|
|||||||
receiverPeerCtx.rToClient <- chatStartBReqF
|
receiverPeerCtx.rToClient <- chatStartBReqF
|
||||||
|
|
||||||
hdlCtx.initiationsLock.Lock()
|
hdlCtx.initiationsLock.Lock()
|
||||||
//
|
idx := slices.IndexFunc(hdlCtx.initiations, func(i *common.Initiation) bool {
|
||||||
|
return i.AbANick == hdlCtx.peer.account.nickname && i.AbBNick == startChatAReq.Nickname
|
||||||
|
})
|
||||||
|
hdlCtx.initiations[idx].Stage = common.InitiationStageB
|
||||||
hdlCtx.initiationsLock.Unlock()
|
hdlCtx.initiationsLock.Unlock()
|
||||||
|
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (hdlCtx *HandlerContext) handleChatStartC(reqFrame *common.RFrame) (res common.Response, err error) {
|
func (hdlCtx *HandlerContext) handleChatStartC(reqFrame *common.RFrame) (res common.Response, err error) {
|
||||||
startChatAReq, err := common.RequestFromFrame[common.StartChatARequest](*reqFrame)
|
hdlCtx.initiationsLock.Lock()
|
||||||
|
startChatCReq, err := common.RequestFromFrame[common.StartChatCRequest](*reqFrame)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
receiverPeerCtx, err := hdlCtx.getCtxByNick(startChatAReq.Nickname)
|
logger.Debugf("got chat start c for %s", startChatCReq.Nickname)
|
||||||
|
|
||||||
|
receiverPeerCtx, err := hdlCtx.getCtxByNick(startChatCReq.Nickname)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logger.Debug("receiver peer not found")
|
logger.Debug("receiver peer not found")
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// initation started
|
idx := slices.IndexFunc(hdlCtx.initiations, func(i *common.Initiation) bool {
|
||||||
hdlCtx.initiationsLock.Lock()
|
return i.AbBNick == hdlCtx.peer.account.nickname && i.AbANick == startChatCReq.Nickname
|
||||||
hdlCtx.initiations = append(hdlCtx.initiations, NewInitiation(hdlCtx.peer.account.nickname, startChatAReq.Nickname))
|
})
|
||||||
hdlCtx.initiationsLock.Unlock()
|
|
||||||
|
|
||||||
chatStartB := common.StartChatBRequest{
|
if idx == -1 {
|
||||||
Nickname: hdlCtx.peer.account.nickname,
|
logger.Debug("initation not found, won't handle")
|
||||||
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
chatStartBReqF, err := common.RequestFrameFrom(chatStartB)
|
if hdlCtx.initiations[idx].Stage != common.InitiationStageB {
|
||||||
|
logger.Debug("initation found, but is not in stage B, won't handle")
|
||||||
|
return nil, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
hdlCtx.initiations[idx].Stage = common.InitiationStageC
|
||||||
|
|
||||||
|
aCode, err := generatePunchCode()
|
||||||
|
if err != nil {
|
||||||
|
logger.Error("failed generating punch code for a")
|
||||||
|
return nil, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
bCode, err := generatePunchCode()
|
||||||
|
if err != nil {
|
||||||
|
logger.Error("failed generating punch code for b")
|
||||||
|
return nil, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
hdlCtx.initiations[idx].AbAPunchCode = aCode
|
||||||
|
hdlCtx.initiations[idx].AbBPunchCode = bCode
|
||||||
|
|
||||||
|
dReqToA := common.StartChatDRequest{Nickname: hdlCtx.peer.account.nickname, PunchCode: aCode}
|
||||||
|
dReqToB := common.StartChatDRequest{Nickname: startChatCReq.Nickname, PunchCode: bCode}
|
||||||
|
|
||||||
|
err = hdlCtx.sendRequest(dReqToB)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logger.Debug("chat start B req frame creation failed")
|
logger.Errorf("could not send chatstartd to B=%s", hdlCtx.peer.account.nickname)
|
||||||
return nil, err
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
receiverPeerCtx.rToClient <- chatStartBReqF
|
err = receiverPeerCtx.sendRequest(dReqToA)
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
logger.Errorf("could not send chatstartd to A=%s", startChatCReq.Nickname)
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
hdlCtx.initiations[idx].Stage = common.InitiationStageD
|
||||||
|
|
||||||
|
hdlCtx.initiationsLock.Unlock()
|
||||||
|
return nil, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func generatePunchCode() (string, error) {
|
||||||
|
codeBytes := make([]byte, 8)
|
||||||
|
_, err := rand.Read(codeBytes)
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
|
||||||
|
for idx, cb := range codeBytes {
|
||||||
|
codeBytes[idx] = 65 + (cb % 26)
|
||||||
|
}
|
||||||
|
|
||||||
|
return string(codeBytes), nil
|
||||||
|
}
|
||||||
|
|
||||||
func (ctx *Context) printDebugInfo() {
|
func (ctx *Context) printDebugInfo() {
|
||||||
ctx.peersListLock.RLock()
|
ctx.peersListLock.RLock()
|
||||||
logger.Debug("================================ server state")
|
logger.Debug("================================ server state")
|
||||||
@ -477,7 +524,7 @@ func (ctx *Context) printDebugInfo() {
|
|||||||
logger.Debug("displaying all initiations:")
|
logger.Debug("displaying all initiations:")
|
||||||
|
|
||||||
for _, i := range ctx.initiations {
|
for _, i := range ctx.initiations {
|
||||||
logger.Debugf("from %s to %s, stage: %d", i.abBNick, i.abBNick, i.stage)
|
logger.Debugf("from %s to %s, stage: %d", i.AbANick, i.AbBNick, i.Stage)
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx.peersListLock.RUnlock()
|
ctx.peersListLock.RUnlock()
|
||||||
|
Loading…
x
Reference in New Issue
Block a user