package json import ( "encoding/json" "fmt" "sync" "git.loafle.net/commons_go/rpc/codec" "git.loafle.net/commons_go/rpc/protocol" ) // ---------------------------------------------------------------------------- // ClientResponseCodec // ---------------------------------------------------------------------------- // 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"` } // newClientResponseCodec returns a new ClientResponseCodec. func newClientResponseCodec(raw *json.RawMessage, codec codec.Codec) (protocol.ClientResponseCodec, error) { // Decode the request body and check if RPC method is valid. ccr := retainClientResponseCodec() err := json.Unmarshal(*raw, &ccr.res) if err != nil { releaseClientResponseCodec(ccr) return nil, err } if nil == ccr.res.Result && nil == ccr.res.Error { releaseClientResponseCodec(ccr) return nil, fmt.Errorf("This is not Response") } return ccr, nil } // ClientResponseCodec decodes and encodes a single request. type ClientResponseCodec struct { res clientResponse err error } func (ccr *ClientResponseCodec) ID() interface{} { return ccr.res.ID } 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 { params := [1]interface{}{result} if err = json.Unmarshal(*ccr.res.Result, ¶ms); err != nil { ccr.err = err } } } return ccr.err } func (ccr *ClientResponseCodec) Error() error { return ccr.res.Error } func (ccr *ClientResponseCodec) Close() { releaseClientResponseCodec(ccr) } var clientResponseCodecPool sync.Pool func retainClientResponseCodec() *ClientResponseCodec { v := clientResponseCodecPool.Get() if v == nil { return &ClientResponseCodec{} } return v.(*ClientResponseCodec) } func releaseClientResponseCodec(ccr *ClientResponseCodec) { ccr.res.Result = nil ccr.res.Error = nil ccr.res.ID = 0 clientResponseCodecPool.Put(ccr) }