gitee.com/eden-framework/sqlx@v0.0.3/er/er.go (about)

     1  package er
     2  
     3  import (
     4  	"reflect"
     5  	"strings"
     6  
     7  	"gitee.com/eden-framework/enumeration"
     8  	"gitee.com/eden-framework/sqlx"
     9  	"gitee.com/eden-framework/sqlx/builder"
    10  )
    11  
    12  func DatabaseERFromDB(database *sqlx.Database, dialect builder.Dialect) *ERDatabase {
    13  	erd := &ERDatabase{Name: database.Name, Tables: map[string]*ERTable{}}
    14  
    15  	database.Tables.Range(func(table *builder.Table, idx int) {
    16  		t := &ERTable{Name: table.Name, Cols: map[string]*ERCol{}, Keys: map[string]*ERKey{}}
    17  
    18  		if len(table.Description) > 0 {
    19  			t.Summary = table.Description[0]
    20  
    21  			if len(table.Description) > 1 {
    22  				t.Desc = strings.Join(table.Description[1:], "\n")
    23  			}
    24  		}
    25  
    26  		erd.Tables[t.Name] = t
    27  
    28  		table.Columns.Range(func(col *builder.Column, idx int) {
    29  			if col.DeprecatedActions != nil {
    30  				return
    31  			}
    32  
    33  			c := &ERCol{
    34  				Name:     col.Name,
    35  				DataType: builder.ResolveExpr(dialect.DataType(col.ColumnType)).String(),
    36  			}
    37  
    38  			if len(col.Description) > 0 {
    39  				c.Summary = col.Description[0]
    40  
    41  				if len(col.Description) > 1 {
    42  					c.Desc = strings.Join(col.Description[1:], "\n")
    43  				}
    44  			}
    45  
    46  			rv := reflect.New(col.ColumnType.Type)
    47  
    48  			if rv.CanInterface() {
    49  				if emum, ok := rv.Interface().(enumeration.Enum); ok {
    50  
    51  					c.Enum = map[string]EREnum{}
    52  
    53  					for _, e := range emum {
    54  						em := EREnum{}
    55  						em.Value = e.Val
    56  						em.Name = e.Label
    57  						em.Label = e.Label
    58  
    59  						c.Enum[em.Name] = em
    60  					}
    61  				}
    62  			}
    63  
    64  			if len(col.Relation) == 2 {
    65  				relTable := database.Tables.Model(col.Relation[0])
    66  				if relTable != nil && relTable != table {
    67  					relCol := relTable.F(col.Relation[1])
    68  					if relCol != nil {
    69  						c.Rel = []string{
    70  							relTable.Name,
    71  							relCol.Name,
    72  						}
    73  					}
    74  				}
    75  			}
    76  
    77  			t.Cols[c.Name] = c
    78  		})
    79  
    80  		table.Keys.Range(func(key *builder.Key, idx int) {
    81  			k := &ERKey{
    82  				Name:      key.Name,
    83  				Method:    key.Method,
    84  				IsUnique:  key.IsUnique,
    85  				IsPrimary: key.Name == "primary",
    86  			}
    87  
    88  			key.Columns.Range(func(col *builder.Column, idx int) {
    89  				k.Cols = append(k.Cols, col.Name)
    90  			})
    91  
    92  			t.Keys[k.Name] = k
    93  		})
    94  	})
    95  
    96  	return erd
    97  }
    98  
    99  type ERDatabase struct {
   100  	Name   string              `json:"name"`
   101  	Tables map[string]*ERTable `json:"tables"`
   102  }
   103  
   104  type ERTable struct {
   105  	Name    string            `json:"name"`
   106  	Summary string            `json:"summary"`
   107  	Desc    string            `json:"desc"`
   108  	Cols    map[string]*ERCol `json:"cols"`
   109  	Keys    map[string]*ERKey `json:"keys"`
   110  }
   111  
   112  type ERCol struct {
   113  	Name     string            `json:"name"`
   114  	DataType string            `json:"dataType"`
   115  	Enum     map[string]EREnum `json:"enum"`
   116  	Summary  string            `json:"summary"`
   117  	Desc     string            `json:"desc"`
   118  	Rel      []string          `json:"rel"`
   119  }
   120  
   121  type EREnum struct {
   122  	Value int    `json:"value"`
   123  	Name  string `json:"name"`
   124  	Label string `json:"label"`
   125  }
   126  
   127  type ERKey struct {
   128  	Name      string   `json:"name"`
   129  	Method    string   `json:"method"`
   130  	IsUnique  bool     `json:"isUnique"`
   131  	IsPrimary bool     `json:"isPrimary"`
   132  	Cols      []string `json:"cols"`
   133  }