Skip to content

Commit

Permalink
Merge pull request #4 from ilacorda/adjust-proto
Browse files Browse the repository at this point in the history
feat: add proto type changes
  • Loading branch information
hilaryRope authored Oct 28, 2023
2 parents 346960f + c5788a1 commit 7fc0ce2
Show file tree
Hide file tree
Showing 7 changed files with 84 additions and 70 deletions.
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -98,4 +98,5 @@ The task was time-boxed and this currently version was reached in approximately

### Subsequent PRs
- Added structured logging with [zerolog](https://github.com/rs/zerolog) whose basic setup for Console logging is defined in `logger.go` and called in `main.go`
- ADD linter to Github actions and include Makefile with targets
- ADD linter to Github actions and include Makefile with targets
- Move to proto definitions as opposed to JSON
1 change: 1 addition & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ module secure-messaging-system
go 1.21

require (
github.com/google/go-cmp v0.6.0
github.com/icrowley/fake v0.0.0-20221112152111-d7b7e2276db2
github.com/rs/zerolog v1.31.0
github.com/stretchr/testify v1.7.5
Expand Down
4 changes: 2 additions & 2 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,9 @@ github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA=
github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk=
github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU=
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
github.com/icrowley/fake v0.0.0-20221112152111-d7b7e2276db2 h1:qU3v73XG4QAqCPHA4HOpfC1EfUvtLIDvQK4mNQ0LvgI=
github.com/icrowley/fake v0.0.0-20221112152111-d7b7e2276db2/go.mod h1:dQ6TM/OGAe+cMws81eTe4Btv1dKxfPZ2CX+YaAFAPN4=
github.com/mattn/go-colorable v0.1.13 h1:fFA4WZxdEF4tXPZVKMLwD8oUnCTTo08duU7wxecdEvA=
Expand All @@ -30,7 +31,6 @@ golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBc
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.12.0 h1:CM0HF96J0hcLAwsHPJZjfdNzs0gftsLfgKt57wWHJ0o=
golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4=
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw=
google.golang.org/protobuf v1.31.0 h1:g0LDEJHgrBl9N9r17Ru3sqWhkIx2NB67okBHPwC7hs8=
Expand Down
41 changes: 22 additions & 19 deletions pkg/message.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import (
"encoding/json"
"errors"
"github.com/rs/zerolog/log"
"google.golang.org/protobuf/types/known/timestamppb"
pb "secure-messaging-system/proto"
"time"
"unicode/utf8"
Expand All @@ -23,7 +24,7 @@ func NewMessageBuilder() *MessageBuilder {
// WithSenderID sets the SenderID of the message.
func (b *MessageBuilder) WithSenderID(senderID string) *MessageBuilder {
if senderID == "" {
log.Warn().Msg("Provided empty SenderID")
log.Warn().Msg("Provided empty SenderId")
return b
}
b.message.SenderId = senderID
Expand All @@ -33,15 +34,15 @@ func (b *MessageBuilder) WithSenderID(senderID string) *MessageBuilder {
// WithReceiverID sets the ReceiverID of the message.
func (b *MessageBuilder) WithReceiverID(receiverID string) *MessageBuilder {
if receiverID == "" {
log.Warn().Msg("Provided empty ReceiverID")
log.Warn().Msg("Provided empty ReceiverId")
return b
}
b.message.ReceiverId = receiverID
return b
}

func (b *MessageBuilder) WithTimestamp(timestamp time.Time) *MessageBuilder {
b.message.Timestamp = timestamp.Unix()
func (b *MessageBuilder) WithTimestamp(timeStamp time.Time) *MessageBuilder {
b.message.Timestamp = timestamppb.New(timeStamp)
return b
}

Expand All @@ -57,27 +58,29 @@ func (b *MessageBuilder) WithEncryptedText(encryptedText string) *MessageBuilder

// Build finalizes the building process and returns the constructed Message.
func (b *MessageBuilder) Build() (*pb.Message, error) {
if b.message.SenderId == "" || b.message.ReceiverId == "" || b.message.EncryptedText == "" {
if b.message.SenderId == "" ||
b.message.ReceiverId == "" ||
b.message.EncryptedText == "" ||
b.message.Timestamp == nil {
return nil, errors.New("message is incomplete")
}

if b.message.Timestamp == 0 {
b.message.Timestamp = time.Now().Unix()
}

return b.message, nil
}

func NewMessage(senderID, receiverID, encryptedText string) *pb.Message {
if senderID == "" || receiverID == "" || encryptedText == "" {
func NewMessage(senderID, receiverID, encryptedText string, timestamp *time.Time) *pb.Message {
if senderID == "" ||
receiverID == "" ||
encryptedText == "" ||
timestamp == nil {
log.Error().Msg("Cannot create a new message with empty fields")
return nil
}

return &pb.Message{
SenderId: senderID,
ReceiverId: receiverID,
Timestamp: time.Now().Unix(),
Timestamp: timestamppb.New(*timestamp),
EncryptedText: encryptedText,
}
}
Expand All @@ -97,12 +100,12 @@ func ToJSON(msg *pb.Message) ([]byte, error) {
return jsonData, nil
}

// MessageFromJSON converts a JSON representation to a message.
func MessageFromJSON(data []byte) (*pb.Message, error) {
msg := &pb.Message{}
err := json.Unmarshal(data, msg)
if err != nil {
return nil, err
func FromJSON(data []byte) (*pb.Message, error) {
var msg pb.Message

if err := json.Unmarshal(data, &msg); err != nil {
return nil, errors.New("failed to unmarshal JSON into Message struct: " + err.Error())
}
return msg, nil

return &msg, nil
}
55 changes: 31 additions & 24 deletions proto/message.pb.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 3 additions & 1 deletion proto/message.proto
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,13 @@ syntax = "proto3";

package pkg;

import "google/protobuf/timestamp.proto";

option go_package = "secure-messaging-system/pkg";

message Message {
string sender_id = 1;
string receiver_id = 2;
int64 timestamp = 3;
google.protobuf.Timestamp timestamp = 3;
string encrypted_text = 4;
}
46 changes: 23 additions & 23 deletions test/message_test.go
Original file line number Diff line number Diff line change
@@ -1,11 +1,15 @@
package test

import (
"github.com/google/go-cmp/cmp"
"github.com/google/go-cmp/cmp/cmpopts"
"github.com/icrowley/fake"
"github.com/stretchr/testify/assert"
"google.golang.org/protobuf/types/known/timestamppb"
"secure-messaging-system/pkg"
pb "secure-messaging-system/proto"
"testing"
"time"
)

const (
Expand All @@ -19,8 +23,9 @@ func Test_NewMessage(t *testing.T) {
senderID := fake.CharactersN(10)
receiverID := fake.CharactersN(10)
encryptedText := fake.Sentence()
timestamp := time.Now()

message := pkg.NewMessage(senderID, receiverID, encryptedText)
message := pkg.NewMessage(senderID, receiverID, encryptedText, &timestamp)

assert.Equal(t, senderID, message.SenderId, senderIDMismatchErr)
assert.Equal(t, receiverID, message.ReceiverId, receiverIDMismatchErr)
Expand All @@ -35,21 +40,22 @@ func TestMessageBuilder(t *testing.T) {
senderID := fake.CharactersN(10)
receiverID := fake.CharactersN(10)
encryptedText := fake.Sentence()
timestamp := time.Now()

message, err := pkg.NewMessageBuilder().
WithSenderID(senderID).
WithReceiverID(receiverID).
WithEncryptedText(encryptedText).
WithTimestamp(timestamp).
Build()

assert.NoError(t, err, "Error building the message")

assert.Equal(t, senderID, message.SenderId, senderIDMismatchErr)
assert.Equal(t, receiverID, message.ReceiverId, receiverIDMismatchErr)
assert.Equal(t, encryptedText, message.EncryptedText, encryptedTextMismatchErr)
assert.Equal(t, senderID, message.SenderId, "Mismatched Sender ID")
assert.Equal(t, receiverID, message.ReceiverId, "Mismatched Receiver ID")
assert.Equal(t, encryptedText, message.EncryptedText, "Mismatched Encrypted Text")

// Make sure that the timestamp was set
assert.NotEqual(t, int64(0), message.Timestamp, "Timestamp was not set")
assert.Equal(t, timestamppb.New(timestamp), message.Timestamp, "Timestamp mismatch")
})
}

Expand All @@ -66,7 +72,7 @@ func TestMessageConversion(t *testing.T) {
message: &pb.Message{
SenderId: fake.CharactersN(10),
ReceiverId: fake.CharactersN(10),
Timestamp: int64(0),
Timestamp: timestamppb.New(time.Now()),
EncryptedText: fake.Paragraph(),
},
wantErr: false,
Expand All @@ -76,7 +82,7 @@ func TestMessageConversion(t *testing.T) {
message: &pb.Message{
SenderId: fake.CharactersN(10),
ReceiverId: fake.CharactersN(10),
Timestamp: int64(0),
Timestamp: timestamppb.New(time.Now()),
EncryptedText: string([]byte{0x80, 0x81, 0x82, 0x83}),
},
wantErr: true,
Expand All @@ -90,7 +96,7 @@ func TestMessageConversion(t *testing.T) {
name: "incomplete Message",
message: &pb.Message{
SenderId: fake.CharactersN(10),
Timestamp: int64(0),
Timestamp: timestamppb.New(time.Now()),
},
wantErr: false,
},
Expand All @@ -111,26 +117,20 @@ func TestMessageConversion(t *testing.T) {
return
}

msgFromJSON, err := pkg.MessageFromJSON(jsonData)
msgFromJSON, err := pkg.FromJSON(jsonData)
if (err != nil) != tt.wantErr {
t.Errorf("MessageFromJSON() error = %v, wantErr %v", err, tt.wantErr)
return
}

if !tt.wantErr {
assert.True(t, messagesAreEquivalent(tt.message, msgFromJSON))
diff := cmp.Diff(
tt.message,
msgFromJSON,
cmpopts.IgnoreUnexported(pb.Message{}, timestamppb.Timestamp{}),
)
if diff != "" {
t.Errorf("Mismatch (-Original +FromJSON):\n%s", diff)
}
})
}
}

// Helper function

// messagesAreEquivalent compares two pb.Message objects and determines if they are equivalent.
func messagesAreEquivalent(msg1, msg2 *pb.Message) bool {
// Compare individual fields of the messages.
return msg1.SenderId == msg2.SenderId &&
msg1.ReceiverId == msg2.ReceiverId &&
msg1.EncryptedText == msg2.EncryptedText &&
msg1.Timestamp == msg2.Timestamp
}

0 comments on commit 7fc0ce2

Please sign in to comment.