dialect_sqlite3.go 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108
  1. package gorm
  2. import (
  3. "fmt"
  4. "reflect"
  5. "strings"
  6. "time"
  7. )
  8. type sqlite3 struct {
  9. commonDialect
  10. }
  11. func init() {
  12. RegisterDialect("sqlite", &sqlite3{})
  13. RegisterDialect("sqlite3", &sqlite3{})
  14. }
  15. func (sqlite3) GetName() string {
  16. return "sqlite3"
  17. }
  18. // Get Data Type for Sqlite Dialect
  19. func (s *sqlite3) DataTypeOf(field *StructField) string {
  20. var dataValue, sqlType, size, additionalType = ParseFieldStructForDialect(field, s)
  21. if sqlType == "" {
  22. switch dataValue.Kind() {
  23. case reflect.Bool:
  24. sqlType = "bool"
  25. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uintptr:
  26. if field.IsPrimaryKey {
  27. field.TagSettings["AUTO_INCREMENT"] = "AUTO_INCREMENT"
  28. sqlType = "integer primary key autoincrement"
  29. } else {
  30. sqlType = "integer"
  31. }
  32. case reflect.Int64, reflect.Uint64:
  33. if field.IsPrimaryKey {
  34. field.TagSettings["AUTO_INCREMENT"] = "AUTO_INCREMENT"
  35. sqlType = "integer primary key autoincrement"
  36. } else {
  37. sqlType = "bigint"
  38. }
  39. case reflect.Float32, reflect.Float64:
  40. sqlType = "real"
  41. case reflect.String:
  42. if size > 0 && size < 65532 {
  43. sqlType = fmt.Sprintf("varchar(%d)", size)
  44. } else {
  45. sqlType = "text"
  46. }
  47. case reflect.Struct:
  48. if _, ok := dataValue.Interface().(time.Time); ok {
  49. sqlType = "datetime"
  50. }
  51. default:
  52. if _, ok := dataValue.Interface().([]byte); ok {
  53. sqlType = "blob"
  54. }
  55. }
  56. }
  57. if sqlType == "" {
  58. panic(fmt.Sprintf("invalid sql type %s (%s) for sqlite3", dataValue.Type().Name(), dataValue.Kind().String()))
  59. }
  60. if strings.TrimSpace(additionalType) == "" {
  61. return sqlType
  62. }
  63. return fmt.Sprintf("%v %v", sqlType, additionalType)
  64. }
  65. func (s sqlite3) HasIndex(tableName string, indexName string) bool {
  66. var count int
  67. s.db.QueryRow(fmt.Sprintf("SELECT count(*) FROM sqlite_master WHERE tbl_name = ? AND sql LIKE '%%INDEX %v ON%%'", indexName), tableName).Scan(&count)
  68. return count > 0
  69. }
  70. func (s sqlite3) HasTable(tableName string) bool {
  71. var count int
  72. s.db.QueryRow("SELECT count(*) FROM sqlite_master WHERE type='table' AND name=?", tableName).Scan(&count)
  73. return count > 0
  74. }
  75. func (s sqlite3) HasColumn(tableName string, columnName string) bool {
  76. var count int
  77. s.db.QueryRow(fmt.Sprintf("SELECT count(*) FROM sqlite_master WHERE tbl_name = ? AND (sql LIKE '%%\"%v\" %%' OR sql LIKE '%%%v %%');\n", columnName, columnName), tableName).Scan(&count)
  78. return count > 0
  79. }
  80. func (s sqlite3) CurrentDatabase() (name string) {
  81. var (
  82. ifaces = make([]interface{}, 3)
  83. pointers = make([]*string, 3)
  84. i int
  85. )
  86. for i = 0; i < 3; i++ {
  87. ifaces[i] = &pointers[i]
  88. }
  89. if err := s.db.QueryRow("PRAGMA database_list").Scan(ifaces...); err != nil {
  90. return
  91. }
  92. if pointers[1] != nil {
  93. name = *pointers[1]
  94. }
  95. return
  96. }