func (nn *NNet) SendBytesDirectReply(replyToID, data []byte, remoteNode *node.RemoteNode) error {
	msg, err := nn.NewDirectBytesMessage(data)
	if err != nil {
		return err
	}
	msg.ReplyToId = replyToID
	return remoteNode.SendMessageAsync(msg)
}
SendBytesDirectReply is the same as SendBytesDirectAsync but with the
replyToId field of the message set
package nnet
import (
	"time"
	"github.com/gogo/protobuf/proto"
	"github.com/nknorg/nnet/message"
	"github.com/nknorg/nnet/node"
	"github.com/nknorg/nnet/protobuf"
)
func (nn *NNet) NewDirectBytesMessage(data []byte) (*protobuf.Message, error) {
	id, err := message.GenID(nn.GetLocalNode().MessageIDBytes)
	if err != nil {
		return nil, err
	}
	msgBody := &protobuf.Bytes{
		Data: data,
	}
	buf, err := proto.Marshal(msgBody)
	if err != nil {
		return nil, err
	}
	msg := &protobuf.Message{
		MessageType: protobuf.BYTES,
		RoutingType: protobuf.DIRECT,
		MessageId:   id,
		Message:     buf,
	}
	return msg, nil
}
func (nn *NNet) NewRelayBytesMessage(data, srcID, key []byte) (*protobuf.Message, error) {
	id, err := message.GenID(nn.GetLocalNode().MessageIDBytes)
	if err != nil {
		return nil, err
	}
	msgBody := &protobuf.Bytes{
		Data: data,
	}
	buf, err := proto.Marshal(msgBody)
	if err != nil {
		return nil, err
	}
	msg := &protobuf.Message{
		MessageType: protobuf.BYTES,
		RoutingType: protobuf.RELAY,
		MessageId:   id,
		Message:     buf,
		SrcId:       srcID,
		DestId:      key,
	}
	return msg, nil
}
func (nn *NNet) NewBroadcastBytesMessage(data, srcID []byte, routingType protobuf.RoutingType) (*protobuf.Message, error) {
	id, err := message.GenID(nn.GetLocalNode().MessageIDBytes)
	if err != nil {
		return nil, err
	}
	msgBody := &protobuf.Bytes{
		Data: data,
	}
	buf, err := proto.Marshal(msgBody)
	if err != nil {
		return nil, err
	}
	msg := &protobuf.Message{
		MessageType: protobuf.BYTES,
		RoutingType: routingType,
		MessageId:   id,
		Message:     buf,
		SrcId:       srcID,
	}
	return msg, nil
}
func (nn *NNet) SendBytesDirectAsync(data []byte, remoteNode *node.RemoteNode) error {
	msg, err := nn.NewDirectBytesMessage(data)
	if err != nil {
		return err
	}
	return remoteNode.SendMessageAsync(msg)
}
func (nn *NNet) SendBytesDirectSync(data []byte, remoteNode *node.RemoteNode) ([]byte, *node.RemoteNode, error) {
	return nn.SendBytesDirectSyncWithTimeout(data, remoteNode, 0)
}
func (nn *NNet) SendBytesDirectSyncWithTimeout(data []byte, remoteNode *node.RemoteNode, replyTimeout time.Duration) ([]byte, *node.RemoteNode, error) {
	msg, err := nn.NewDirectBytesMessage(data)
	if err != nil {
		return nil, nil, err
	}
	reply, err := remoteNode.SendMessageSync(msg, replyTimeout)
	if err != nil {
		return nil, nil, err
	}
	replyBody := &protobuf.Bytes{}
	err = proto.Unmarshal(reply.Msg.Message, replyBody)
	if err != nil {
		return nil, reply.RemoteNode, err
	}
	return replyBody.Data, reply.RemoteNode, nil
}