diff --git a/mxrouter.go b/mxrouter.go index c218d65..1944276 100644 --- a/mxrouter.go +++ b/mxrouter.go @@ -27,7 +27,7 @@ import ( ) const ( - version = "0.9.3" + version = "0.9.4" ) var ( @@ -43,6 +43,28 @@ var ( defDomain *string ) + +func ldapSearch(conLdap *ldap.Conn, searchReq *ldap.SearchRequest, attempt int) (*ldap.SearchResult, error) { + mutex.Lock() + result, err := conLdap.Search(searchReq) + mutex.Unlock() + // Let's just manage connection errors here + if err != nil && strings.HasSuffix(err.Error(), "ldap: connection closed") { + logstream.Err("LDAP connection closed, retrying") + conLdap.Close() + conLdap, err = connectLdap() + if err != nil { + return result, err + } else { + attempt = attempt + 1 + return ldapSearch(conLdap, searchReq, attempt) + } + } + + return result, err +} + + func handleConnection(connClt net.Conn, conLdap *ldap.Conn) { var s string var mxdom string @@ -89,14 +111,8 @@ func handleConnection(connClt net.Conn, conLdap *ldap.Conn) { searchReq := ldap.NewSearchRequest(*ldapBaseDN, ldap.ScopeWholeSubtree, 0, 0, 0, false, filter, []string{*ldapAttr}, []ldap.Control{}) - mutex.Lock() - result, err := conLdap.Search(searchReq) - mutex.Unlock() + result, err := ldapSearch(conLdap, searchReq, 0) if err != nil { - if err.Error == "ldap: connection closed" { - // TODO : Reconnect to LDAP - return - } logstream.Err(fmt.Sprintln("Error searching into LDAP: ", err)) s := strings.Replace(err.Error(), " ", "%20", -1) response := fmt.Sprintf("500 %s\n", s) @@ -142,6 +158,21 @@ func handleConnection(connClt net.Conn, conLdap *ldap.Conn) { } } +func connectLdap() (*ldap.Conn, error) { + conLdap, err := ldap.DialURL(*ldapURL) + if err != nil { + logstream.Err(fmt.Sprintln("Error dialing LDAP: ", err)) + return conLdap, err + } + + err = conLdap.Bind(*ldapUser, *ldapPass) + if err != nil { + logstream.Err(fmt.Sprintln("Error binding LDAP: ", err)) + return conLdap, err + } + return conLdap, err +} + func run() { logstream.Info("start") defer logstream.Info("exit") @@ -150,12 +181,8 @@ func run() { log.Fatal(fmt.Sprintln("Error listening: ", err)) } - conLdap, err := ldap.DialURL(*ldapURL) - defer conLdap.Close() - - err = conLdap.Bind(*ldapUser, *ldapPass) + conLdap, err := connectLdap() if err != nil { - logstream.Err(fmt.Sprintln("Error binding LDAP: ", err)) return } @@ -166,6 +193,7 @@ func run() { } go handleConnection(connClt, conLdap) } + conLdap.Close() } func main() {