Skip to content

Commit

Permalink
#129 bug(rpc): duplicated error from the uber.multierr
Browse files Browse the repository at this point in the history
#129 bug(rpc): duplicated error from the `uber.multierr`
  • Loading branch information
rustatian authored Jun 14, 2021
2 parents b67b3b1 + 24b2036 commit efae571
Show file tree
Hide file tree
Showing 3 changed files with 53 additions and 14 deletions.
9 changes: 9 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,15 @@
CHANGELOG
=========

v3.1.4 (14.06.2021)
-------------------

## 🩹 Fixes:

- 🐛 Fix: Duplicated RPC error message: [PR](https://github.com/spiral/goridge/pull/129)

---

v3.1.3 (11.06.2021)
-------------------

Expand Down
31 changes: 31 additions & 0 deletions pkg/rpc/client_server_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -197,6 +197,37 @@ func TestClientServerJSON(t *testing.T) {
assert.Equal(t, "key", rp.Keys["value"])
}

func TestClientServerError(t *testing.T) {
ln, err := net.Listen("tcp", "127.0.0.1:12336")
assert.NoError(t, err)

go func() {
for {
conn, err2 := ln.Accept()
assert.NoError(t, err2)
rpc.ServeCodec(NewCodec(conn))
}
}()

err = rpc.RegisterName("testError2", new(testService))
assert.NoError(t, err)

conn, err := net.Dial("tcp", "127.0.0.1:12336")
assert.NoError(t, err)

client := rpc.NewClientWithCodec(NewClientCodec(conn))
defer func() {
err := client.Close()
if err != nil {
t.Fatal(err)
}
}()

err = client.Call("unknown", nil, nil)
assert.Error(t, err)
assert.Equal(t, "rpc: service/method request ill-formed: unknown", err.Error())
}

func TestClientServerConcurrent(t *testing.T) {
ln, err := net.Listen("tcp", "127.0.0.1:22385")
if err != nil {
Expand Down
27 changes: 13 additions & 14 deletions pkg/rpc/codec.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ import (
"github.com/spiral/goridge/v3/pkg/frame"
"github.com/spiral/goridge/v3/pkg/relay"
"github.com/spiral/goridge/v3/pkg/socket"
"go.uber.org/multierr"
)

// Codec represent net/rpc bridge over Goridge socket relay.
Expand Down Expand Up @@ -98,7 +97,7 @@ func (c *Codec) WriteResponse(r *rpc.Response, body interface{}) error { //nolin
// if error returned, we sending it via relay and return error from WriteResponse
if r.Error != "" {
// Append error flag
return c.handleError(r, fr, buf, errors.Str(r.Error))
return c.handleError(r, fr, r.Error)
}

// read flag previously written
Expand All @@ -109,40 +108,40 @@ func (c *Codec) WriteResponse(r *rpc.Response, body interface{}) error { //nolin
case flags&frame.CODEC_RAW != 0:
err := encodeRaw(buf, body)
if err != nil {
return c.handleError(r, fr, buf, err)
return c.handleError(r, fr, err.Error())
}
// send buffer
return c.sendBuf(fr, buf)
case flags&frame.CODEC_PROTO != 0:
err := encodeProto(buf, body)
if err != nil {
return c.handleError(r, fr, buf, err)
return c.handleError(r, fr, err.Error())
}
// send buffer
return c.sendBuf(fr, buf)
case flags&frame.CODEC_JSON != 0:
err := encodeJSON(buf, body)
if err != nil {
return c.handleError(r, fr, buf, err)
return c.handleError(r, fr, err.Error())
}
// send buffer
return c.sendBuf(fr, buf)
case flags&frame.CODEC_MSGPACK != 0:
err := encodeMsgPack(buf, body)
if err != nil {
return c.handleError(r, fr, buf, err)
return c.handleError(r, fr, err.Error())
}
// send buffer
return c.sendBuf(fr, buf)
case flags&frame.CODEC_GOB != 0:
err := encodeGob(buf, body)
if err != nil {
return c.handleError(r, fr, buf, err)
return c.handleError(r, fr, err.Error())
}
// send buffer
return c.sendBuf(fr, buf)
default:
return c.handleError(r, fr, buf, errors.E(op, errors.Str("unknown codec")))
return c.handleError(r, fr, errors.E(op, errors.Str("unknown codec")).Error())
}
}

Expand All @@ -155,18 +154,18 @@ func (c *Codec) sendBuf(frame *frame.Frame, buf *bytes.Buffer) error {
return c.relay.Send(frame)
}

func (c *Codec) handleError(r *rpc.Response, fr *frame.Frame, buf *bytes.Buffer, err error) error {
// just to be sure, remove all data from buffer and write new
buf.Truncate(0)
func (c *Codec) handleError(r *rpc.Response, fr *frame.Frame, err string) error {
buf := c.get()
defer c.put(buf)

// write all possible errors
err = multierr.Append(err, errors.Str(r.Error))
buf.WriteString(r.ServiceMethod)

const op = errors.Op("handle codec error")
fr.WriteFlags(frame.ERROR)
// error should be here
if err != nil {
buf.WriteString(err.Error())
if err != "" {
buf.WriteString(err)
}
fr.WritePayloadLen(uint32(buf.Len()))
fr.WritePayload(buf.Bytes())
Expand Down

0 comments on commit efae571

Please sign in to comment.