2016-06-23 08:09:56 +02:00
|
|
|
package bdb
|
|
|
|
|
|
|
|
import (
|
|
|
|
"fmt"
|
|
|
|
"regexp"
|
2016-09-14 10:08:30 +02:00
|
|
|
"strings"
|
2016-06-23 08:09:56 +02:00
|
|
|
)
|
|
|
|
|
|
|
|
var rgxAutoIncColumn = regexp.MustCompile(`^nextval\(.*\)`)
|
|
|
|
|
|
|
|
// PrimaryKey represents a primary key constraint in a database
|
|
|
|
type PrimaryKey struct {
|
|
|
|
Name string
|
|
|
|
Columns []string
|
|
|
|
}
|
|
|
|
|
|
|
|
// ForeignKey represents a foreign key constraint in a database
|
|
|
|
type ForeignKey struct {
|
2016-08-24 08:20:41 +02:00
|
|
|
Table string
|
2016-07-09 18:53:21 +02:00
|
|
|
Name string
|
|
|
|
Column string
|
|
|
|
Nullable bool
|
2016-07-15 21:09:32 +02:00
|
|
|
Unique bool
|
2016-06-23 08:09:56 +02:00
|
|
|
|
2016-07-12 17:09:26 +02:00
|
|
|
ForeignTable string
|
|
|
|
ForeignColumn string
|
|
|
|
ForeignColumnNullable bool
|
2016-07-15 21:09:32 +02:00
|
|
|
ForeignColumnUnique bool
|
2016-06-23 08:09:56 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
// SQLColumnDef formats a column name and type like an SQL column definition.
|
|
|
|
type SQLColumnDef struct {
|
|
|
|
Name string
|
|
|
|
Type string
|
|
|
|
}
|
|
|
|
|
2016-06-23 08:48:49 +02:00
|
|
|
// String for fmt.Stringer
|
2016-06-23 08:09:56 +02:00
|
|
|
func (s SQLColumnDef) String() string {
|
|
|
|
return fmt.Sprintf("%s %s", s.Name, s.Type)
|
|
|
|
}
|
|
|
|
|
2016-06-27 08:54:23 +02:00
|
|
|
// SQLColumnDefs has small helper functions
|
|
|
|
type SQLColumnDefs []SQLColumnDef
|
|
|
|
|
|
|
|
// Names returns all the names
|
|
|
|
func (s SQLColumnDefs) Names() []string {
|
|
|
|
names := make([]string, len(s))
|
|
|
|
|
|
|
|
for i, sqlDef := range s {
|
|
|
|
names[i] = sqlDef.Name
|
|
|
|
}
|
|
|
|
|
|
|
|
return names
|
|
|
|
}
|
|
|
|
|
|
|
|
// Types returns all the types
|
|
|
|
func (s SQLColumnDefs) Types() []string {
|
|
|
|
types := make([]string, len(s))
|
|
|
|
|
|
|
|
for i, sqlDef := range s {
|
|
|
|
types[i] = sqlDef.Type
|
|
|
|
}
|
|
|
|
|
|
|
|
return types
|
|
|
|
}
|
|
|
|
|
2016-06-23 08:09:56 +02:00
|
|
|
// SQLColDefinitions creates a definition in sql format for a column
|
2016-06-27 08:54:23 +02:00
|
|
|
func SQLColDefinitions(cols []Column, names []string) SQLColumnDefs {
|
2016-06-23 08:09:56 +02:00
|
|
|
ret := make([]SQLColumnDef, len(names))
|
|
|
|
|
|
|
|
for i, n := range names {
|
|
|
|
for _, c := range cols {
|
|
|
|
if n != c.Name {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
ret[i] = SQLColumnDef{Name: n, Type: c.Type}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return ret
|
|
|
|
}
|
2016-09-14 10:08:30 +02:00
|
|
|
|
|
|
|
// AutoIncPrimaryKey returns the auto-increment primary key column name or an
|
|
|
|
// empty string. Primary key columns with default values are presumed
|
|
|
|
// to be auto-increment, because pkeys need to be unique and a static
|
|
|
|
// default value would cause collisions.
|
|
|
|
func AutoIncPrimaryKey(cols []Column, pkey *PrimaryKey) *Column {
|
|
|
|
if pkey == nil {
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
for _, pkeyColumn := range pkey.Columns {
|
|
|
|
for _, c := range cols {
|
|
|
|
if c.Name != pkeyColumn {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
if c.Default != "auto_increment" || c.Nullable ||
|
|
|
|
!(strings.HasPrefix(c.Type, "int") || strings.HasPrefix(c.Type, "uint")) {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
return &c
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|