Search code examples
gosmpp

How I can close the connection by timeout if the client doesn't respond in 10 seconds?


I have code (I use https://github.com/fiorix/go-smpp):

// -----------------------------------------------
// handleConnection new clients.
// -----------------------------------------------
func (_srv *ServerSmpp) handleConnection(_cfg *ConfigSmpp, c *conn) {
    defer c.Close()

    if err := _srv.auth(_cfg, c); err != nil {
        if err != io.EOF {
            log.Printf("smpp_server: server auth failed: %s\n", err)
        }
        return
    }

    notify := make(chan error)

    go func() {
        for {
            pb, err := c.Read()
            if err != nil {
                notify <- err
                return
            }

            err = _srv.Handler(_srv.RemoteProvider, c, pb)
            if err != nil {
                fmt.Printf("%s\n", err)
                notify <- err
                return
            }
        }
    }()


    for {
        select {
        case err:= <-notify:
            if io.EOF == err {
                fmt.Printf("Smpp server (read): %s\n", err)
                return
            }
      case <-time.After(time.Second * 10):
            fmt.Printf("Client disconnected by timeout.\n")
            return
        }
    }
}

Code for invoked handleConnection:

func (_srv *ServerSmpp) Serve(_cfg *ConfigSmpp) {
    for {
        client, err := _srv.NetListener.Accept()
        if err != nil {
            break 
        }
        c := newConn(client)

        go _srv.handleConnection(_cfg, c)
    }
}

When this code work, the server disconnects all clients by timeout 10 sec, but how I can disconnect the client when it's doesn't work 10 sec?


Solution

  • Your client object seems to be a net.Conn,
    choose a way to call client.SetReadDeadline() with the appropriate time.Time value before blocking on client.Read() :

    c.client.SetDeadline( time.Now().Add(10 * time.Second )
    pb, err := c.Read() { ...