111 lines
3.5 KiB
Go
111 lines
3.5 KiB
Go
package goricochet
|
|
|
|
import (
|
|
"errors"
|
|
"github.com/golang/protobuf/proto"
|
|
"github.com/s-rah/go-ricochet/auth"
|
|
"github.com/s-rah/go-ricochet/chat"
|
|
"github.com/s-rah/go-ricochet/control"
|
|
)
|
|
|
|
type MessageDecoder struct {
|
|
}
|
|
|
|
// Conceptual Chat Message - we construct this to avoid polluting the
|
|
// the main ricochet code with protobuf cruft - and enable us to minimise the
|
|
// code that may break in the future.
|
|
type RicochetChatMessage struct {
|
|
Ack bool
|
|
MessageID int32
|
|
Message string
|
|
Accepted bool
|
|
}
|
|
|
|
// Conceptual Control Message - we construct this to avoid polluting the
|
|
// the main ricochet code with protobuf cruft - and enable us to minimise the
|
|
// code that may break in the future.
|
|
type RicochetControlMessage struct {
|
|
Ack bool
|
|
Type string
|
|
ChannelID int32
|
|
Accepted bool
|
|
ClientCookie [16]byte
|
|
ServerCookie [16]byte
|
|
}
|
|
|
|
// DecodeAuthMessage
|
|
func (md *MessageDecoder) DecodeAuthMessage(data []byte) (bool, error) {
|
|
res := new(Protocol_Data_AuthHiddenService.Packet)
|
|
err := proto.Unmarshal(data[:], res)
|
|
if err != nil {
|
|
return false, errors.New("error unmarshalling control message type")
|
|
}
|
|
return res.GetResult().GetAccepted(), nil
|
|
}
|
|
|
|
// DecodeControlMessage
|
|
func (md *MessageDecoder) DecodeControlMessage(data []byte) (*RicochetControlMessage, error) {
|
|
res := new(Protocol_Data_Control.Packet)
|
|
err := proto.Unmarshal(data[:], res)
|
|
|
|
if err != nil {
|
|
return nil, errors.New("error unmarshalling control message type")
|
|
}
|
|
|
|
if res.GetOpenChannel() != nil {
|
|
ricochetControlMessage := new(RicochetControlMessage)
|
|
ricochetControlMessage.Ack = false
|
|
|
|
if res.GetOpenChannel().GetChannelType() == "im.ricochet.auth.hidden-service" {
|
|
ricochetControlMessage.Type = "openauthchannel"
|
|
}
|
|
|
|
ricochetControlMessage.Type = "openchannel"
|
|
ricochetControlMessage.ChannelID = int32(res.GetOpenChannel().GetChannelIdentifier())
|
|
return ricochetControlMessage, nil
|
|
} else if res.GetChannelResult() != nil {
|
|
ricochetControlMessage := new(RicochetControlMessage)
|
|
ricochetControlMessage.Ack = true
|
|
ricochetControlMessage.ChannelID = int32(res.GetOpenChannel().GetChannelIdentifier())
|
|
|
|
serverCookie, err := proto.GetExtension(res.GetChannelResult(), Protocol_Data_AuthHiddenService.E_ServerCookie)
|
|
|
|
if err == nil {
|
|
ricochetControlMessage.Type = "openauthchannel"
|
|
copy(ricochetControlMessage.ServerCookie[:], serverCookie.([]byte))
|
|
} else {
|
|
ricochetControlMessage.Type = "openchannel"
|
|
|
|
}
|
|
|
|
return ricochetControlMessage, nil
|
|
}
|
|
return nil, errors.New("unknown control message type")
|
|
}
|
|
|
|
// DecodeChatMessage takes a byte representing a data packet and returns a
|
|
// constructed RicochetControlMessage
|
|
func (md *MessageDecoder) DecodeChatMessage(data []byte) (*RicochetChatMessage, error) {
|
|
res := new(Protocol_Data_Chat.Packet)
|
|
err := proto.Unmarshal(data[:], res)
|
|
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
if res.GetChatMessage() != nil {
|
|
ricochetChatMessage := new(RicochetChatMessage)
|
|
ricochetChatMessage.Ack = false
|
|
ricochetChatMessage.MessageID = int32(res.GetChatMessage().GetMessageId())
|
|
ricochetChatMessage.Message = res.GetChatMessage().GetMessageText()
|
|
return ricochetChatMessage, nil
|
|
} else if res.GetChatAcknowledge != nil {
|
|
ricochetChatMessage := new(RicochetChatMessage)
|
|
ricochetChatMessage.Ack = true
|
|
ricochetChatMessage.MessageID = int32(res.GetChatAcknowledge().GetMessageId())
|
|
ricochetChatMessage.Accepted = res.GetChatAcknowledge().GetAccepted()
|
|
return ricochetChatMessage, nil
|
|
}
|
|
return nil, errors.New("chat message type not supported")
|
|
}
|