A package for assertions without dependency hell
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

166 lines
4.1 KiB

  1. package assert
  2. import (
  3. "reflect"
  4. "runtime"
  5. )
  6. // Assert is a helper for tests
  7. type Assert func(bool, ...interface{})
  8. // New returns a new Assert
  9. func New(t T) Assert {
  10. a := func(ok bool, msg ...interface{}) {
  11. if !ok {
  12. if msg == nil {
  13. msg = []interface{}{`Assertion failed`}
  14. }
  15. msg = append(append([]interface{}{shell(1) + shell(97) + shell(41) + `FAIL!` + shell(0) + shell(1)}, msg...), shell(0), "\n")
  16. t.Helper()
  17. t.Error(msg...)
  18. }
  19. }
  20. f := runtime.FuncForPC(reflect.ValueOf(a).Pointer())
  21. ts[f] = t
  22. return a
  23. }
  24. // TODO: Panics, Len
  25. ///// Boolean /////
  26. // True asserts the given value is true
  27. func (a Assert) True(actual bool, msg ...interface{}) {
  28. t(a).Helper()
  29. msg = prepMsg(msg, `Should be true, but it isn't`)
  30. a(actual, msg...)
  31. }
  32. // False sserts the given value is false
  33. func (a Assert) False(actual bool, msg ...interface{}) {
  34. t(a).Helper()
  35. msg = prepMsg(msg, `Should be false, but it isn't`)
  36. a(!actual, msg...)
  37. }
  38. ///// Nil /////
  39. func isNil(val interface{}) bool {
  40. if val == nil {
  41. return true
  42. }
  43. v := reflect.ValueOf(val)
  44. switch v.Kind() {
  45. case reflect.Chan, reflect.Func, reflect.Interface, reflect.Map, reflect.Ptr, reflect.Slice:
  46. return v.IsNil()
  47. }
  48. return false
  49. }
  50. // Nil asserts the given value is nil
  51. func (a Assert) Nil(actual interface{}, msg ...interface{}) {
  52. t(a).Helper()
  53. msg = prepMsg(msg, `Should be nil, but got %#v`, actual)
  54. a(isNil(actual), msg...)
  55. }
  56. // NotNil sserts the given value is not nil
  57. func (a Assert) NotNil(actual interface{}, msg ...interface{}) {
  58. t(a).Helper()
  59. msg = prepMsg(msg, `Should not be nil, but it is`)
  60. a(!isNil(actual), msg...)
  61. }
  62. ///// Errors /////
  63. // Error asserts the given error is not nil
  64. func (a Assert) Error(actual error, msg ...interface{}) {
  65. t(a).Helper()
  66. msg = prepMsg(msg, `Expected an error, but got nil`)
  67. a(actual != nil, msg...)
  68. }
  69. // NoError asserts the given error is not nil
  70. func (a Assert) NoError(actual error, msg ...interface{}) {
  71. t(a).Helper()
  72. msg = prepMsg(msg, `Expected no error, but got %#v`, actual)
  73. a(actual == nil, msg...)
  74. }
  75. ///// Comparisons /////
  76. // Eq asserts the given values match
  77. func (a Assert) Eq(expected, actual interface{}, msg ...interface{}) {
  78. t(a).Helper()
  79. if reflect.TypeOf(expected) != reflect.TypeOf(actual) {
  80. msg = prepMsg(msg, `Expected %T(%#v), but got %T(%#v)`, expected, expected, actual, actual)
  81. a(false, msg...)
  82. return
  83. }
  84. msg = prepMsg(msg, `Expected %#v, but got %#v`, expected, actual)
  85. a(expected == actual, msg...)
  86. }
  87. // Ne asserts the given values don't match
  88. func (a Assert) Ne(expected, actual interface{}, msg ...interface{}) {
  89. t(a).Helper()
  90. msg = prepMsg(msg, `Should not be %#v, but it is`, expected)
  91. a(expected != actual, msg...)
  92. }
  93. ///// Lists /////
  94. // Contains asserts the expected value is in the given list
  95. func (a Assert) Contains(expected, list interface{}, msg ...interface{}) {
  96. t(a).Helper()
  97. rlist := reflect.ValueOf(list)
  98. a(rlist.Kind() == reflect.Slice || rlist.Kind() == reflect.Array, `Can only call assert.Contains on a slice or array`)
  99. for i := 0; i < rlist.Len(); i++ {
  100. if rlist.Index(i).Interface() == expected {
  101. return
  102. }
  103. }
  104. msg = prepMsg(msg, `Expected %#v to be in %#v, but it isn't`, expected, list)
  105. a(false, msg...)
  106. }
  107. // SameElements asserts the values have the same elements. It ignores the order of the elements
  108. func (a Assert) SameElements(expected, actual interface{}, msg ...interface{}) {
  109. t(a).Helper()
  110. rexpected, ractual := reflect.ValueOf(expected), reflect.ValueOf(actual)
  111. a(rexpected.Kind() == reflect.Slice || rexpected.Kind() == reflect.Array, `Can only call assert.SameElements on a slice or array`)
  112. a(ractual.Kind() == reflect.Slice || ractual.Kind() == reflect.Array, `Can only call assert.SameElements on a slice or array`)
  113. msg = prepMsg(msg, `Expected elements of %#v to match %#v, but they don't`, expected, actual)
  114. if rexpected.Len() != ractual.Len() {
  115. a(false, msg...)
  116. return
  117. }
  118. var same int
  119. for i := 0; i < rexpected.Len(); i++ {
  120. for j := 0; j < ractual.Len(); j++ {
  121. if rexpected.Index(i).Interface() == ractual.Index(j).Interface() {
  122. same++
  123. break
  124. }
  125. }
  126. }
  127. if same == rexpected.Len() {
  128. return
  129. }
  130. a(false, msg...)
  131. }