rpc/protocol/json/client_response.go

87 lines
2.1 KiB
Go
Raw Normal View History

2017-10-31 09:25:44 +00:00
package json
import (
"encoding/json"
"fmt"
"sync"
2017-11-26 10:15:51 +00:00
"git.loafle.net/commons_go/rpc/codec"
2017-10-31 09:25:44 +00:00
"git.loafle.net/commons_go/rpc/protocol"
)
// ----------------------------------------------------------------------------
2017-11-26 10:15:51 +00:00
// ClientResponseCodec
2017-10-31 09:25:44 +00:00
// ----------------------------------------------------------------------------
2017-11-26 10:15:51 +00:00
// clientResponse represents a JSON-RPC response returned to a client.
type clientResponse struct {
Result *json.RawMessage `json:"result,omitempty"`
Error error `json:"error,omitempty"`
ID interface{} `json:"id,omitempty"`
}
2017-10-31 09:25:44 +00:00
2017-11-26 10:15:51 +00:00
// newClientResponseCodec returns a new ClientResponseCodec.
func newClientResponseCodec(raw *json.RawMessage, codec codec.Codec) (protocol.ClientResponseCodec, error) {
2017-10-31 09:25:44 +00:00
// Decode the request body and check if RPC method is valid.
2017-11-26 10:15:51 +00:00
ccr := retainClientResponseCodec()
err := json.Unmarshal(*raw, &ccr.res)
2017-10-31 09:25:44 +00:00
if err != nil {
2017-11-26 10:15:51 +00:00
releaseClientResponseCodec(ccr)
2017-10-31 09:25:44 +00:00
return nil, err
}
2017-11-26 10:15:51 +00:00
if nil == ccr.res.Result && nil == ccr.res.Error {
releaseClientResponseCodec(ccr)
2017-10-31 09:25:44 +00:00
return nil, fmt.Errorf("This is not Response")
}
return ccr, nil
}
2017-11-26 10:15:51 +00:00
// ClientResponseCodec decodes and encodes a single request.
type ClientResponseCodec struct {
res clientResponse
err error
2017-10-31 09:25:44 +00:00
}
2017-11-26 10:15:51 +00:00
func (ccr *ClientResponseCodec) ID() interface{} {
return ccr.res.ID
2017-10-31 09:25:44 +00:00
}
2017-11-26 10:15:51 +00:00
func (ccr *ClientResponseCodec) Result(result interface{}) error {
if ccr.err == nil && ccr.res.Result != nil {
if err := json.Unmarshal(*ccr.res.Result, &result); err != nil {
2017-11-01 09:58:16 +00:00
params := [1]interface{}{result}
2017-11-26 10:15:51 +00:00
if err = json.Unmarshal(*ccr.res.Result, &params); err != nil {
2017-11-01 09:58:16 +00:00
ccr.err = err
}
}
}
return ccr.err
2017-10-31 09:25:44 +00:00
}
2017-11-26 10:15:51 +00:00
func (ccr *ClientResponseCodec) Error() error {
return ccr.res.Error
2017-10-31 09:25:44 +00:00
}
2017-11-26 10:15:51 +00:00
func (ccr *ClientResponseCodec) Close() {
releaseClientResponseCodec(ccr)
2017-10-31 09:25:44 +00:00
}
2017-11-26 10:15:51 +00:00
var clientResponseCodecPool sync.Pool
2017-10-31 09:25:44 +00:00
2017-11-26 10:15:51 +00:00
func retainClientResponseCodec() *ClientResponseCodec {
v := clientResponseCodecPool.Get()
2017-10-31 09:25:44 +00:00
if v == nil {
2017-11-26 10:15:51 +00:00
return &ClientResponseCodec{}
2017-10-31 09:25:44 +00:00
}
2017-11-26 10:15:51 +00:00
return v.(*ClientResponseCodec)
2017-10-31 09:25:44 +00:00
}
2017-11-26 10:15:51 +00:00
func releaseClientResponseCodec(ccr *ClientResponseCodec) {
ccr.res.Result = nil
ccr.res.Error = nil
ccr.res.ID = 0
2017-10-31 09:25:44 +00:00
2017-11-26 10:15:51 +00:00
clientResponseCodecPool.Put(ccr)
2017-10-31 09:25:44 +00:00
}