Skip to content

Commit

Permalink
server: Simplify the API for static and single-run services.
Browse files Browse the repository at this point in the history
- Rework NewStatic as "Static", which returns a plain constructor.
- Remove the "Simple" type and move its Run method to a top-level function.
- Update usage examples.

#46 (comment)
  • Loading branch information
creachadair committed May 6, 2021
1 parent b11415d commit 4bb7b22
Show file tree
Hide file tree
Showing 7 changed files with 35 additions and 58 deletions.
2 changes: 1 addition & 1 deletion cmd/examples/server/server.go
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ func main() {
log.Fatalln("Listen:", err)
}
log.Printf("Listening at %v...", lst.Addr())
server.Loop(lst, server.NewStatic(mux), &server.LoopOptions{
server.Loop(lst, server.Static(mux), &server.LoopOptions{
ServerOptions: &jrpc2.ServerOptions{
Logger: log.New(os.Stderr, "[jrpc2.Server] ", log.LstdFlags|log.Lshortfile),
Concurrency: *maxTasks,
Expand Down
4 changes: 2 additions & 2 deletions server/example_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -46,10 +46,10 @@ func (s Service) Finish(stat jrpc2.ServerStatus) {
close(s.done)
}

func ExampleNewSimple() {
func ExampleRun() {
done := make(chan struct{})
cch, sch := channel.Direct()
go server.NewSimple(Service{done}, nil).Run(sch)
go server.Run(sch, Service{done}, nil)

cli := jrpc2.NewClient(cch, nil)
if _, err := cli.Call(context.Background(), "Hello", nil); err != nil {
Expand Down
14 changes: 6 additions & 8 deletions server/loop.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,16 +19,14 @@ type Service interface {
Finish(jrpc2.ServerStatus)
}

type singleton struct{ assigner jrpc2.Assigner }
// Static wraps a jrpc2.Assigner to trivially implement the Service interface.
func Static(m jrpc2.Assigner) func() Service { return static{methods: m}.New }

func (s singleton) Assigner() (jrpc2.Assigner, error) { return s.assigner, nil }
func (singleton) Finish(jrpc2.ServerStatus) {}
type static struct{ methods jrpc2.Assigner }

// NewStatic creates a static (singleton) service from the given assigner.
func NewStatic(assigner jrpc2.Assigner) func() Service {
svc := singleton{assigner}
return func() Service { return svc }
}
func (s static) New() Service { return s }
func (s static) Assigner() (jrpc2.Assigner, error) { return s.methods, nil }
func (static) Finish(jrpc2.ServerStatus) {}

// Loop obtains connections from lst and starts a server for each with the
// given service constructor and options, running in a new goroutine. If accept
Expand Down
2 changes: 1 addition & 1 deletion server/loop_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ import (
var newChan = channel.Line

// A static test service that returns the same thing each time.
var testService = NewStatic(handler.Map{
var testService = Static(handler.Map{
"Test": handler.New(func(context.Context) (string, error) {
return "OK", nil
}),
Expand Down
23 changes: 23 additions & 0 deletions server/run.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package server

import (
"github.com/creachadair/jrpc2"
"github.com/creachadair/jrpc2/channel"
)

// Run starts a server for svc on the given channel, and blocks until it
// returns. The server exit status is reported to the service, and the error
// value is returned.
//
// If the caller does not need the error value and does not want to wait for
// the server to complete, call Run in a goroutine.
func Run(ch channel.Channel, svc Service, opts *jrpc2.ServerOptions) error {
assigner, err := svc.Assigner()
if err != nil {
return err
}
srv := jrpc2.NewServer(assigner, opts).Start(ch)
stat := srv.WaitStatus()
svc.Finish(stat)
return stat.Err
}
5 changes: 2 additions & 3 deletions server/simple_test.go → server/run_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ func (t *testService) Finish(stat jrpc2.ServerStatus) {
t.stat = stat
}

func TestSimple(t *testing.T) {
func TestRun(t *testing.T) {
svc := &testService{assigner: handler.Map{
"Test": handler.New(func(ctx context.Context) string {
return "OK"
Expand All @@ -44,8 +44,7 @@ func TestSimple(t *testing.T) {
}
}()

srv := server.NewSimple(svc, nil)
if err := srv.Run(spipe); err != nil {
if err := server.Run(spipe, svc, nil); err != nil {
t.Errorf("Server failed: %v", err)
}
if result != "OK" {
Expand Down
43 changes: 0 additions & 43 deletions server/simple.go

This file was deleted.

0 comments on commit 4bb7b22

Please sign in to comment.