2018-04-04 13:28:35 +00:00
|
|
|
package server
|
|
|
|
|
|
|
|
import (
|
|
|
|
"sync"
|
|
|
|
|
|
|
|
logging "git.loafle.net/commons/logging-go"
|
|
|
|
)
|
|
|
|
|
2018-04-04 13:50:34 +00:00
|
|
|
type ServerReadWriter struct {
|
2018-04-04 13:28:35 +00:00
|
|
|
connections sync.Map
|
|
|
|
|
|
|
|
ReadwriteHandler ReadWriteHandler
|
|
|
|
ServerStopChan <-chan struct{}
|
|
|
|
ServerStopWg *sync.WaitGroup
|
|
|
|
}
|
|
|
|
|
2018-04-04 13:50:34 +00:00
|
|
|
func (srw *ServerReadWriter) ConnectionSize() int {
|
2018-04-04 13:28:35 +00:00
|
|
|
var sz int
|
2018-04-04 13:50:34 +00:00
|
|
|
srw.connections.Range(func(k, v interface{}) bool {
|
2018-04-04 13:28:35 +00:00
|
|
|
sz++
|
|
|
|
return true
|
|
|
|
})
|
|
|
|
return sz
|
|
|
|
}
|
|
|
|
|
2018-04-04 13:50:34 +00:00
|
|
|
func (srw *ServerReadWriter) HandleConnection(servlet Servlet, servletCtx ServletCtx, conn *Conn) {
|
2018-04-04 13:28:35 +00:00
|
|
|
addr := conn.RemoteAddr()
|
|
|
|
|
|
|
|
defer func() {
|
|
|
|
if nil != conn {
|
|
|
|
conn.Close()
|
|
|
|
}
|
|
|
|
servlet.OnDisconnect(servletCtx)
|
|
|
|
logging.Logger().Infof("Client[%s] has been disconnected", addr)
|
2018-04-04 13:50:34 +00:00
|
|
|
srw.ServerStopWg.Done()
|
2018-04-04 13:28:35 +00:00
|
|
|
}()
|
|
|
|
|
|
|
|
logging.Logger().Infof("Client[%s] has been connected", addr)
|
|
|
|
|
2018-04-04 13:50:34 +00:00
|
|
|
srw.connections.Store(conn, true)
|
|
|
|
defer srw.connections.Delete(conn)
|
2018-04-04 13:28:35 +00:00
|
|
|
|
|
|
|
servlet.OnConnect(servletCtx, conn)
|
|
|
|
conn.SetCloseHandler(func(code int, text string) error {
|
|
|
|
logging.Logger().Debugf("close")
|
|
|
|
return nil
|
|
|
|
})
|
|
|
|
|
|
|
|
stopChan := make(chan struct{})
|
|
|
|
servletDoneChan := make(chan struct{})
|
|
|
|
|
|
|
|
readChan := make(chan []byte)
|
|
|
|
writeChan := make(chan []byte)
|
|
|
|
|
|
|
|
readerDoneChan := make(chan error)
|
|
|
|
writerDoneChan := make(chan error)
|
|
|
|
|
|
|
|
go servlet.Handle(servletCtx, stopChan, servletDoneChan, readChan, writeChan)
|
2018-04-04 13:50:34 +00:00
|
|
|
go connReadHandler(srw.ReadwriteHandler, conn, stopChan, readerDoneChan, readChan)
|
|
|
|
go connWriteHandler(srw.ReadwriteHandler, conn, stopChan, writerDoneChan, writeChan)
|
2018-04-04 13:28:35 +00:00
|
|
|
|
|
|
|
select {
|
|
|
|
case <-readerDoneChan:
|
|
|
|
close(stopChan)
|
|
|
|
<-writerDoneChan
|
|
|
|
<-servletDoneChan
|
|
|
|
case <-writerDoneChan:
|
|
|
|
close(stopChan)
|
|
|
|
<-readerDoneChan
|
|
|
|
<-servletDoneChan
|
|
|
|
case <-servletDoneChan:
|
|
|
|
close(stopChan)
|
|
|
|
<-readerDoneChan
|
|
|
|
<-writerDoneChan
|
2018-04-04 13:50:34 +00:00
|
|
|
case <-srw.ServerStopChan:
|
2018-04-04 13:28:35 +00:00
|
|
|
close(stopChan)
|
|
|
|
<-readerDoneChan
|
|
|
|
<-writerDoneChan
|
|
|
|
<-servletDoneChan
|
|
|
|
}
|
|
|
|
}
|