rows_test.go 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220
  1. // +build go1.8
  2. package pq
  3. import (
  4. "math"
  5. "reflect"
  6. "testing"
  7. "github.com/lib/pq/oid"
  8. )
  9. func TestDataTypeName(t *testing.T) {
  10. tts := []struct {
  11. typ oid.Oid
  12. name string
  13. }{
  14. {oid.T_int8, "INT8"},
  15. {oid.T_int4, "INT4"},
  16. {oid.T_int2, "INT2"},
  17. {oid.T_varchar, "VARCHAR"},
  18. {oid.T_text, "TEXT"},
  19. {oid.T_bool, "BOOL"},
  20. {oid.T_numeric, "NUMERIC"},
  21. {oid.T_date, "DATE"},
  22. {oid.T_time, "TIME"},
  23. {oid.T_timetz, "TIMETZ"},
  24. {oid.T_timestamp, "TIMESTAMP"},
  25. {oid.T_timestamptz, "TIMESTAMPTZ"},
  26. {oid.T_bytea, "BYTEA"},
  27. }
  28. for i, tt := range tts {
  29. dt := fieldDesc{OID: tt.typ}
  30. if name := dt.Name(); name != tt.name {
  31. t.Errorf("(%d) got: %s want: %s", i, name, tt.name)
  32. }
  33. }
  34. }
  35. func TestDataType(t *testing.T) {
  36. tts := []struct {
  37. typ oid.Oid
  38. kind reflect.Kind
  39. }{
  40. {oid.T_int8, reflect.Int64},
  41. {oid.T_int4, reflect.Int32},
  42. {oid.T_int2, reflect.Int16},
  43. {oid.T_varchar, reflect.String},
  44. {oid.T_text, reflect.String},
  45. {oid.T_bool, reflect.Bool},
  46. {oid.T_date, reflect.Struct},
  47. {oid.T_time, reflect.Struct},
  48. {oid.T_timetz, reflect.Struct},
  49. {oid.T_timestamp, reflect.Struct},
  50. {oid.T_timestamptz, reflect.Struct},
  51. {oid.T_bytea, reflect.Slice},
  52. }
  53. for i, tt := range tts {
  54. dt := fieldDesc{OID: tt.typ}
  55. if kind := dt.Type().Kind(); kind != tt.kind {
  56. t.Errorf("(%d) got: %s want: %s", i, kind, tt.kind)
  57. }
  58. }
  59. }
  60. func TestDataTypeLength(t *testing.T) {
  61. tts := []struct {
  62. typ oid.Oid
  63. len int
  64. mod int
  65. length int64
  66. ok bool
  67. }{
  68. {oid.T_int4, 0, -1, 0, false},
  69. {oid.T_varchar, 65535, 9, 5, true},
  70. {oid.T_text, 65535, -1, math.MaxInt64, true},
  71. {oid.T_bytea, 65535, -1, math.MaxInt64, true},
  72. }
  73. for i, tt := range tts {
  74. dt := fieldDesc{OID: tt.typ, Len: tt.len, Mod: tt.mod}
  75. if l, k := dt.Length(); k != tt.ok || l != tt.length {
  76. t.Errorf("(%d) got: %d, %t want: %d, %t", i, l, k, tt.length, tt.ok)
  77. }
  78. }
  79. }
  80. func TestDataTypePrecisionScale(t *testing.T) {
  81. tts := []struct {
  82. typ oid.Oid
  83. mod int
  84. precision, scale int64
  85. ok bool
  86. }{
  87. {oid.T_int4, -1, 0, 0, false},
  88. {oid.T_numeric, 589830, 9, 2, true},
  89. {oid.T_text, -1, 0, 0, false},
  90. }
  91. for i, tt := range tts {
  92. dt := fieldDesc{OID: tt.typ, Mod: tt.mod}
  93. p, s, k := dt.PrecisionScale()
  94. if k != tt.ok {
  95. t.Errorf("(%d) got: %t want: %t", i, k, tt.ok)
  96. }
  97. if p != tt.precision {
  98. t.Errorf("(%d) wrong precision got: %d want: %d", i, p, tt.precision)
  99. }
  100. if s != tt.scale {
  101. t.Errorf("(%d) wrong scale got: %d want: %d", i, s, tt.scale)
  102. }
  103. }
  104. }
  105. func TestRowsColumnTypes(t *testing.T) {
  106. columnTypesTests := []struct {
  107. Name string
  108. TypeName string
  109. Length struct {
  110. Len int64
  111. OK bool
  112. }
  113. DecimalSize struct {
  114. Precision int64
  115. Scale int64
  116. OK bool
  117. }
  118. ScanType reflect.Type
  119. }{
  120. {
  121. Name: "a",
  122. TypeName: "INT4",
  123. Length: struct {
  124. Len int64
  125. OK bool
  126. }{
  127. Len: 0,
  128. OK: false,
  129. },
  130. DecimalSize: struct {
  131. Precision int64
  132. Scale int64
  133. OK bool
  134. }{
  135. Precision: 0,
  136. Scale: 0,
  137. OK: false,
  138. },
  139. ScanType: reflect.TypeOf(int32(0)),
  140. }, {
  141. Name: "bar",
  142. TypeName: "TEXT",
  143. Length: struct {
  144. Len int64
  145. OK bool
  146. }{
  147. Len: math.MaxInt64,
  148. OK: true,
  149. },
  150. DecimalSize: struct {
  151. Precision int64
  152. Scale int64
  153. OK bool
  154. }{
  155. Precision: 0,
  156. Scale: 0,
  157. OK: false,
  158. },
  159. ScanType: reflect.TypeOf(""),
  160. },
  161. }
  162. db := openTestConn(t)
  163. defer db.Close()
  164. rows, err := db.Query("SELECT 1 AS a, text 'bar' AS bar, 1.28::numeric(9, 2) AS dec")
  165. if err != nil {
  166. t.Fatal(err)
  167. }
  168. columns, err := rows.ColumnTypes()
  169. if err != nil {
  170. t.Fatal(err)
  171. }
  172. if len(columns) != 3 {
  173. t.Errorf("expected 3 columns found %d", len(columns))
  174. }
  175. for i, tt := range columnTypesTests {
  176. c := columns[i]
  177. if c.Name() != tt.Name {
  178. t.Errorf("(%d) got: %s, want: %s", i, c.Name(), tt.Name)
  179. }
  180. if c.DatabaseTypeName() != tt.TypeName {
  181. t.Errorf("(%d) got: %s, want: %s", i, c.DatabaseTypeName(), tt.TypeName)
  182. }
  183. l, ok := c.Length()
  184. if l != tt.Length.Len {
  185. t.Errorf("(%d) got: %d, want: %d", i, l, tt.Length.Len)
  186. }
  187. if ok != tt.Length.OK {
  188. t.Errorf("(%d) got: %t, want: %t", i, ok, tt.Length.OK)
  189. }
  190. p, s, ok := c.DecimalSize()
  191. if p != tt.DecimalSize.Precision {
  192. t.Errorf("(%d) got: %d, want: %d", i, p, tt.DecimalSize.Precision)
  193. }
  194. if s != tt.DecimalSize.Scale {
  195. t.Errorf("(%d) got: %d, want: %d", i, s, tt.DecimalSize.Scale)
  196. }
  197. if ok != tt.DecimalSize.OK {
  198. t.Errorf("(%d) got: %t, want: %t", i, ok, tt.DecimalSize.OK)
  199. }
  200. if c.ScanType() != tt.ScanType {
  201. t.Errorf("(%d) got: %v, want: %v", i, c.ScanType(), tt.ScanType)
  202. }
  203. }
  204. }