diff --git a/conn.go b/conn.go index 9ab59c4..9de994a 100644 --- a/conn.go +++ b/conn.go @@ -69,10 +69,10 @@ func (c *Conn) Close() error { return c.close(nil) } -// Call initiates a JSON-RPC call using the specified method and -// params, and waits for the response. If the response is successful, -// its result is stored in result (a pointer to a value that can be -// JSON-unmarshaled into); otherwise, a non-nil error is returned. +// Call initiates a JSON-RPC call using the specified method and params, and +// waits for the response. If the response is successful, its result is stored +// in result (a pointer to a value that can be JSON-unmarshaled into); +// otherwise, a non-nil error is returned. See DispatchCall for more details. func (c *Conn) Call(ctx context.Context, method string, params, result interface{}, opts ...CallOption) error { call, err := c.DispatchCall(ctx, method, params, opts...) if err != nil { @@ -87,11 +87,14 @@ func (c *Conn) DisconnectNotify() <-chan struct{} { return c.disconnect } -// DispatchCall dispatches a JSON-RPC call using the specified method -// and params, and returns a call proxy or an error. Call Wait() -// on the returned proxy to receive the response. Only use this -// function if you need to do work after dispatching the request, -// otherwise use Call. +// DispatchCall dispatches a JSON-RPC call using the specified method and +// params, and returns a call proxy or an error. Call Wait() on the returned +// proxy to receive the response. Only use this function if you need to do work +// after dispatching the request, otherwise use Call. +// +// The params member is omitted from the JSON-RPC request if the given params is +// nil. Use json.RawMessage("null") to send a JSON-RPC request with its params +// member set to null. func (c *Conn) DispatchCall(ctx context.Context, method string, params interface{}, opts ...CallOption) (Waiter, error) { req := &Request{Method: method} for _, opt := range opts { @@ -114,9 +117,13 @@ func (c *Conn) DispatchCall(ctx context.Context, method string, params interface return Waiter{call: call}, nil } -// Notify is like Call, but it returns when the notification request -// is sent (without waiting for a response, because JSON-RPC -// notifications do not have responses). +// Notify is like Call, but it returns when the notification request is sent +// (without waiting for a response, because JSON-RPC notifications do not have +// responses). +// +// The params member is omitted from the JSON-RPC request if the given params is +// nil. Use json.RawMessage("null") to send a JSON-RPC request with its params +// member set to null. func (c *Conn) Notify(ctx context.Context, method string, params interface{}, opts ...CallOption) error { req := &Request{Method: method, Notif: true} for _, opt := range opts { diff --git a/example_test.go b/example_test.go new file mode 100644 index 0000000..9b2b75a --- /dev/null +++ b/example_test.go @@ -0,0 +1,78 @@ +package jsonrpc2_test + +import ( + "context" + "encoding/json" + "fmt" + "net" + "os" + + "github.com/sourcegraph/jsonrpc2" +) + +// Send a JSON-RPC notification with its params member omitted. +func ExampleConn_Notify_paramsOmitted() { + ctx := context.Background() + + connA, connB := net.Pipe() + defer connA.Close() + defer connB.Close() + + rpcConn := jsonrpc2.NewConn(ctx, jsonrpc2.NewPlainObjectStream(connA), nil) + + // Send the JSON-RPC notification. + go func() { + // Set params to nil. + if err := rpcConn.Notify(ctx, "foo", nil); err != nil { + fmt.Fprintln(os.Stderr, "notify:", err) + } + }() + + // Read the raw JSON-RPC notification on connB. + // + // Reading the raw JSON-RPC request is for the purpose of this example only. + // Use a jsonrpc2.Handler to read parsed requests. + buf := make([]byte, 64) + n, err := connB.Read(buf) + if err != nil { + fmt.Fprintln(os.Stderr, "read:", err) + } + + fmt.Printf("%s\n", buf[:n]) + + // Output: {"jsonrpc":"2.0","method":"foo"} +} + +// Send a JSON-RPC notification with its params member set to null. +func ExampleConn_Notify_nullParams() { + ctx := context.Background() + + connA, connB := net.Pipe() + defer connA.Close() + defer connB.Close() + + rpcConn := jsonrpc2.NewConn(ctx, jsonrpc2.NewPlainObjectStream(connA), nil) + + // Send the JSON-RPC notification. + go func() { + // Set params to the JSON null value. + params := json.RawMessage("null") + if err := rpcConn.Notify(ctx, "foo", params); err != nil { + fmt.Fprintln(os.Stderr, "notify:", err) + } + }() + + // Read the raw JSON-RPC notification on connB. + // + // Reading the raw JSON-RPC request is for the purpose of this example only. + // Use a jsonrpc2.Handler to read parsed requests. + buf := make([]byte, 64) + n, err := connB.Read(buf) + if err != nil { + fmt.Fprintln(os.Stderr, "read:", err) + } + + fmt.Printf("%s\n", buf[:n]) + + // Output: {"jsonrpc":"2.0","method":"foo","params":null} +}