caller. handler's args are optional.

This commit is contained in:
Gennadii Kovalev 2016-05-22 20:04:25 +02:00
parent b811737225
commit 79023de6ce
5 changed files with 49 additions and 23 deletions

View File

@ -18,7 +18,7 @@ Examples directory contains simple client and server.
server := gosocketio.NewServer(transport.GetDefaultWebsocketTransport())
//handle connected
server.On(gosocketio.OnConnection, func(c *gosocketio.Channel, args interface{}) {
server.On(gosocketio.OnConnection, func(c *gosocketio.Channel) {
log.Println("New client connected")
//join them to room
c.Join("chat")
@ -89,7 +89,9 @@ var socket = io('ws://yourdomain.com', {transports: ['websocket']});
log.Println(len(channels), "clients in room")
})
//on disconnection handler, if client hangs connection unexpectedly, it will still occurs
server.On(gosocketio.OnDisconnection, func(c *gosocketio.Channel, args interface{}) {
//you can omit function args if you do not need them
//you can return string value for ack, or return nothing for emit
server.On(gosocketio.OnDisconnection, func(c *gosocketio.Channel) {
//this is not necessary, client will be removed from rooms
//automatically on disconnect
//but you can remove client from room whenever you need to
@ -98,7 +100,7 @@ var socket = io('ws://yourdomain.com', {transports: ['websocket']});
log.Println("Disconnected")
})
//error catching handler
server.On(gosocketio.OnError, func(c *gosocketio.Channel, args interface{}) {
server.On(gosocketio.OnError, func(c *gosocketio.Channel) {
log.Println("Error occurs")
})

View File

@ -6,14 +6,15 @@ import (
)
type caller struct {
Func reflect.Value
Args reflect.Type
Out bool
Func reflect.Value
Args reflect.Type
ArgsPresent bool
Out bool
}
var (
ErrorCallerNotFunc = errors.New("f is not function")
ErrorCallerNot2Args = errors.New("f should have 2 args")
ErrorCallerNot2Args = errors.New("f should have 1 or 2 args")
ErrorCallerMaxOneValue = errors.New("f should return not more than one value")
)
@ -28,19 +29,25 @@ func newCaller(f interface{}) (*caller, error) {
}
fType := fVal.Type()
if fType.NumIn() != 2 {
return nil, ErrorCallerNot2Args
}
if fType.NumOut() > 1 {
return nil, ErrorCallerMaxOneValue
}
return &caller{
curCaller := &caller{
Func: fVal,
Args: fType.In(1),
Out: fType.NumOut() == 1,
}, nil
}
if fType.NumIn() == 1 {
curCaller.Args = nil
curCaller.ArgsPresent = false
} else if fType.NumIn() == 2 {
curCaller.Args = fType.In(1)
curCaller.ArgsPresent = true
} else {
return nil, ErrorCallerNot2Args
}
return curCaller, nil
}
/**
@ -55,6 +62,9 @@ calls function with given arguments from its representation using reflection
*/
func (c *caller) callFunc(h *Channel, args interface{}) []reflect.Value {
a := []reflect.Value{reflect.ValueOf(h), reflect.ValueOf(args).Elem()}
if !c.ArgsPresent {
a = a[0:1]
}
return c.Func.Call(a)
}

View File

@ -45,14 +45,14 @@ func main() {
log.Fatal(err)
}
err = c.On(gosocketio.OnDisconnection, func(h *gosocketio.Channel, args interface{}) {
err = c.On(gosocketio.OnDisconnection, func(h *gosocketio.Channel) {
log.Fatal("Disconnected")
})
if err != nil {
log.Fatal(err)
}
err = c.On(gosocketio.OnConnection, func(h *gosocketio.Channel, args interface{}) {
err = c.On(gosocketio.OnConnection, func(h *gosocketio.Channel) {
log.Println("Connected")
})
if err != nil {

View File

@ -21,7 +21,7 @@ type Message struct {
func main() {
server := gosocketio.NewServer(transport.GetDefaultWebsocketTransport())
server.On(gosocketio.OnConnection, func(c *gosocketio.Channel, args interface{}) {
server.On(gosocketio.OnConnection, func(c *gosocketio.Channel) {
log.Println("Connected")
c.Emit("/message", Message{10, "main", "using emit"})
@ -29,12 +29,13 @@ func main() {
c.Join("test")
c.BroadcastTo("test", "/message", Message{10, "main", "using broadcast"})
})
server.On(gosocketio.OnDisconnection, func(c *gosocketio.Channel, args interface{}) {
server.On(gosocketio.OnDisconnection, func(c *gosocketio.Channel) {
log.Println("Disconnected")
})
server.On("/join", func(c *gosocketio.Channel, channel Channel) string {
time.Sleep(2 * time.Second)
log.Println("Client joined to ", channel.Channel)
return "joined to " + channel.Channel
})

View File

@ -4,6 +4,7 @@ import (
"encoding/json"
"github.com/graarh/golang-socketio/protocol"
"sync"
"reflect"
)
const (
@ -92,6 +93,11 @@ func (m *methods) processIncomingMessage(c *Channel, msg *protocol.Message) {
return
}
if !f.ArgsPresent {
f.callFunc(c, &struct{}{})
return
}
data := f.getArgs()
err := json.Unmarshal([]byte(msg.Args), &data)
if err != nil {
@ -106,13 +112,20 @@ func (m *methods) processIncomingMessage(c *Channel, msg *protocol.Message) {
return
}
data := f.getArgs()
err := json.Unmarshal([]byte(msg.Args), &data)
if err != nil {
return
var result []reflect.Value
if f.ArgsPresent {
//data type should be defined for unmarshall
data := f.getArgs()
err := json.Unmarshal([]byte(msg.Args), &data)
if err != nil {
return
}
result = f.callFunc(c, data)
} else {
result = f.callFunc(c, &struct{}{})
}
result := f.callFunc(c, data)
ack := &protocol.Message{
Type: protocol.MessageTypeAckResponse,
AckId: msg.AckId,