helpers.go 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103
  1. package gocql
  2. import "reflect"
  3. type rowData struct {
  4. Columns []string
  5. Values []interface{}
  6. }
  7. func (t *TypeInfo) New() interface{} {
  8. return reflect.New(goType(t)).Interface()
  9. }
  10. func goType(t *TypeInfo) reflect.Type {
  11. switch t.Type {
  12. case TypeVarchar, TypeAscii:
  13. return reflect.TypeOf(*new(string))
  14. case TypeBigInt, TypeCounter, TypeTimestamp:
  15. return reflect.TypeOf(*new(int64))
  16. case TypeBlob:
  17. return reflect.TypeOf(*new([]byte))
  18. case TypeBoolean:
  19. return reflect.TypeOf(*new(bool))
  20. case TypeFloat:
  21. return reflect.TypeOf(*new(float32))
  22. case TypeDouble:
  23. return reflect.TypeOf(*new(float64))
  24. case TypeInt:
  25. return reflect.TypeOf(*new(int))
  26. case TypeUUID, TypeTimeUUID:
  27. return reflect.TypeOf(*new(UUID))
  28. case TypeList, TypeSet:
  29. return reflect.SliceOf(goType(t.Elem))
  30. case TypeMap:
  31. return reflect.MapOf(goType(t.Key), goType(t.Elem))
  32. default:
  33. return nil
  34. }
  35. }
  36. func dereference(i interface{}) interface{} {
  37. return reflect.Indirect(reflect.ValueOf(i)).Interface()
  38. }
  39. func (r *rowData) Map(m map[string]interface{}) {
  40. for i, column := range r.Columns {
  41. m[column] = dereference(r.Values[i])
  42. }
  43. }
  44. func (iter *Iter) rowData() (rowData, error) {
  45. if iter.err != nil {
  46. return rowData{}, iter.err
  47. }
  48. columns := make([]string, 0)
  49. values := make([]interface{}, 0)
  50. for _, column := range iter.Columns() {
  51. val := column.TypeInfo.New()
  52. columns = append(columns, column.Name)
  53. values = append(values, val)
  54. }
  55. rowData := rowData{
  56. Columns: columns,
  57. Values: values,
  58. }
  59. return rowData, nil
  60. }
  61. // SliceMap is a helper function to make the API easier to use
  62. // returns the data from the query in the form of []map[string]interface{}
  63. func (iter *Iter) SliceMap() ([]map[string]interface{}, error) {
  64. if iter.err != nil {
  65. return nil, iter.err
  66. }
  67. // Not checking for the error because we just did
  68. rowData, _ := iter.rowData()
  69. dataToReturn := make([]map[string]interface{}, 0)
  70. for iter.Scan(rowData.Values...) {
  71. m := make(map[string]interface{})
  72. rowData.Map(m)
  73. dataToReturn = append(dataToReturn, m)
  74. }
  75. if iter.err != nil {
  76. return nil, iter.err
  77. }
  78. return dataToReturn, nil
  79. }
  80. func (iter *Iter) MapScan(m map[string]interface{}) bool {
  81. if iter.err != nil {
  82. return false
  83. }
  84. // Not checking for the error because we just did
  85. rowData, _ := iter.rowData()
  86. if iter.Scan(rowData.Values...) {
  87. rowData.Map(m)
  88. return true
  89. }
  90. return false
  91. }