error.go 1.4 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485
  1. package internal
  2. import (
  3. "io"
  4. "net"
  5. "strings"
  6. "github.com/go-redis/redis/internal/proto"
  7. )
  8. func IsRetryableError(err error, retryNetError bool) bool {
  9. if IsNetworkError(err) {
  10. return retryNetError
  11. }
  12. s := err.Error()
  13. if s == "ERR max number of clients reached" {
  14. return true
  15. }
  16. if strings.HasPrefix(s, "LOADING ") {
  17. return true
  18. }
  19. if strings.HasPrefix(s, "CLUSTERDOWN ") {
  20. return true
  21. }
  22. return false
  23. }
  24. func IsRedisError(err error) bool {
  25. _, ok := err.(proto.RedisError)
  26. return ok
  27. }
  28. func IsNetworkError(err error) bool {
  29. if err == io.EOF {
  30. return true
  31. }
  32. _, ok := err.(net.Error)
  33. return ok
  34. }
  35. func IsReadOnlyError(err error) bool {
  36. return strings.HasPrefix(err.Error(), "READONLY ")
  37. }
  38. func IsBadConn(err error, allowTimeout bool) bool {
  39. if err == nil {
  40. return false
  41. }
  42. if IsRedisError(err) {
  43. return false
  44. }
  45. if allowTimeout {
  46. if netErr, ok := err.(net.Error); ok && netErr.Timeout() {
  47. return false
  48. }
  49. }
  50. return true
  51. }
  52. func IsMovedError(err error) (moved bool, ask bool, addr string) {
  53. if !IsRedisError(err) {
  54. return
  55. }
  56. s := err.Error()
  57. if strings.HasPrefix(s, "MOVED ") {
  58. moved = true
  59. } else if strings.HasPrefix(s, "ASK ") {
  60. ask = true
  61. } else {
  62. return
  63. }
  64. ind := strings.LastIndex(s, " ")
  65. if ind == -1 {
  66. return false, false, ""
  67. }
  68. addr = s[ind+1:]
  69. return
  70. }
  71. func IsLoadingError(err error) bool {
  72. return strings.HasPrefix(err.Error(), "LOADING ")
  73. }