diff --git a/orm/db.go b/orm/db.go index b62c165b..314c3535 100644 --- a/orm/db.go +++ b/orm/db.go @@ -113,7 +113,7 @@ func (d *dbBase) collectFieldValue(mi *modelInfo, fi *fieldInfo, ind reflect.Val if fi.pk { _, value, _ = getExistPk(mi, ind) } else { - field := ind.Field(fi.fieldIndex) + field := ind.FieldByIndex(fi.fieldIndex) if fi.isFielder { f := field.Addr().Interface().(Fielder) value = f.RawValue() @@ -517,9 +517,9 @@ func (d *dbBase) Delete(q dbQuerier, mi *modelInfo, ind reflect.Value, tz *time. if num > 0 { if mi.fields.pk.auto { if mi.fields.pk.fieldType&IsPostiveIntegerField > 0 { - ind.Field(mi.fields.pk.fieldIndex).SetUint(0) + ind.FieldByIndex(mi.fields.pk.fieldIndex).SetUint(0) } else { - ind.Field(mi.fields.pk.fieldIndex).SetInt(0) + ind.FieldByIndex(mi.fields.pk.fieldIndex).SetInt(0) } } err := d.deleteRels(q, mi, []interface{}{pkValue}, tz) @@ -859,13 +859,13 @@ func (d *dbBase) ReadBatch(q dbQuerier, qs *querySet, mi *modelInfo, cond *Condi mmi = fi.relModelInfo field := last if last.Kind() != reflect.Invalid { - field = reflect.Indirect(last.Field(fi.fieldIndex)) + field = reflect.Indirect(last.FieldByIndex(fi.fieldIndex)) if field.IsValid() { d.setColsValues(mmi, &field, mmi.fields.dbcols, trefs[:len(mmi.fields.dbcols)], tz) for _, fi := range mmi.fields.fieldsReverse { if fi.inModel && fi.reverseFieldInfo.mi == lastm { if fi.reverseFieldInfo != nil { - f := field.Field(fi.fieldIndex) + f := field.FieldByIndex(fi.fieldIndex) if f.Kind() == reflect.Ptr { f.Set(last.Addr()) } @@ -1014,7 +1014,7 @@ func (d *dbBase) setColsValues(mi *modelInfo, ind *reflect.Value, cols []string, fi := mi.fields.GetByColumn(column) - field := ind.Field(fi.fieldIndex) + field := ind.FieldByIndex(fi.fieldIndex) value, err := d.convertValueFromDB(fi, val, tz) if err != nil { @@ -1350,7 +1350,7 @@ setValue: fieldType = fi.relModelInfo.fields.pk.fieldType mf := reflect.New(fi.relModelInfo.addrField.Elem().Type()) field.Set(mf) - f := mf.Elem().Field(fi.relModelInfo.fields.pk.fieldIndex) + f := mf.Elem().FieldByIndex(fi.relModelInfo.fields.pk.fieldIndex) field = f goto setValue } diff --git a/orm/db_utils.go b/orm/db_utils.go index ae9b1625..c97caf36 100644 --- a/orm/db_utils.go +++ b/orm/db_utils.go @@ -32,7 +32,7 @@ func getDbAlias(name string) *alias { func getExistPk(mi *modelInfo, ind reflect.Value) (column string, value interface{}, exist bool) { fi := mi.fields.pk - v := ind.Field(fi.fieldIndex) + v := ind.FieldByIndex(fi.fieldIndex) if fi.fieldType&IsPostiveIntegerField > 0 { vu := v.Uint() exist = vu > 0 diff --git a/orm/models_info_f.go b/orm/models_info_f.go index 14e1f2c6..996a2f40 100644 --- a/orm/models_info_f.go +++ b/orm/models_info_f.go @@ -102,7 +102,7 @@ func newFields() *fields { // single field info type fieldInfo struct { mi *modelInfo - fieldIndex int + fieldIndex []int fieldType int dbcol bool inModel bool @@ -138,7 +138,7 @@ type fieldInfo struct { } // new field info -func newFieldInfo(mi *modelInfo, field reflect.Value, sf reflect.StructField) (fi *fieldInfo, err error) { +func newFieldInfo(mi *modelInfo, field reflect.Value, sf reflect.StructField, mName string) (fi *fieldInfo, err error) { var ( tag string tagValue string @@ -278,7 +278,7 @@ checkType: fi.column = getColumnName(fieldType, addrField, sf, tags["column"]) fi.addrValue = addrField fi.sf = sf - fi.fullName = mi.fullName + "." + sf.Name + fi.fullName = mi.fullName + mName + "." + sf.Name fi.null = attrs["null"] fi.index = attrs["index"] diff --git a/orm/models_info_m.go b/orm/models_info_m.go index 2654cdb5..bbb82444 100644 --- a/orm/models_info_m.go +++ b/orm/models_info_m.go @@ -36,11 +36,6 @@ type modelInfo struct { // new model info func newModelInfo(val reflect.Value) (info *modelInfo) { - var ( - err error - fi *fieldInfo - sf reflect.StructField - ) info = &modelInfo{} info.fields = newFields() @@ -53,13 +48,31 @@ func newModelInfo(val reflect.Value) (info *modelInfo) { info.name = typ.Name() info.fullName = getFullName(typ) + addModelFields(info, ind, "", []int{}) + + return +} + +func addModelFields(info *modelInfo, ind reflect.Value, mName string, index []int) { + var ( + err error + fi *fieldInfo + sf reflect.StructField + ) + for i := 0; i < ind.NumField(); i++ { field := ind.Field(i) sf = ind.Type().Field(i) if sf.PkgPath != "" { continue } - fi, err = newFieldInfo(info, field, sf) + // add anonymous struct fields + if sf.Anonymous { + addModelFields(info, field, mName+"."+sf.Name, append(index, i)) + continue + } + + fi, err = newFieldInfo(info, field, sf, mName) if err != nil { if err == errSkipField { @@ -84,7 +97,7 @@ func newModelInfo(val reflect.Value) (info *modelInfo) { } } - fi.fieldIndex = i + fi.fieldIndex = append(index, i) fi.mi = info fi.inModel = true } @@ -93,8 +106,6 @@ func newModelInfo(val reflect.Value) (info *modelInfo) { fmt.Println(fmt.Errorf("field: %s.%s, %s", ind.Type(), sf.Name, err)) os.Exit(2) } - - return } // combine related model info to new model info. diff --git a/orm/orm.go b/orm/orm.go index d00d6d03..0ffb6b86 100644 --- a/orm/orm.go +++ b/orm/orm.go @@ -140,7 +140,7 @@ func (o *orm) ReadOrCreate(md interface{}, col1 string, cols ...string) (bool, i return (err == nil), id, err } - return false, ind.Field(mi.fields.pk.fieldIndex).Int(), err + return false, ind.FieldByIndex(mi.fields.pk.fieldIndex).Int(), err } // insert model data to database @@ -160,9 +160,9 @@ func (o *orm) Insert(md interface{}) (int64, error) { func (o *orm) setPk(mi *modelInfo, ind reflect.Value, id int64) { if mi.fields.pk.auto { if mi.fields.pk.fieldType&IsPostiveIntegerField > 0 { - ind.Field(mi.fields.pk.fieldIndex).SetUint(uint64(id)) + ind.FieldByIndex(mi.fields.pk.fieldIndex).SetUint(uint64(id)) } else { - ind.Field(mi.fields.pk.fieldIndex).SetInt(id) + ind.FieldByIndex(mi.fields.pk.fieldIndex).SetInt(id) } } } @@ -290,7 +290,7 @@ func (o *orm) LoadRelated(md interface{}, name string, args ...interface{}) (int qs.orders = []string{order} } - find := ind.Field(fi.fieldIndex) + find := ind.FieldByIndex(fi.fieldIndex) var nums int64 var err error diff --git a/orm/orm_object.go b/orm/orm_object.go index df5a6600..8a5d85e2 100644 --- a/orm/orm_object.go +++ b/orm/orm_object.go @@ -51,9 +51,9 @@ func (o *insertSet) Insert(md interface{}) (int64, error) { if id > 0 { if o.mi.fields.pk.auto { if o.mi.fields.pk.fieldType&IsPostiveIntegerField > 0 { - ind.Field(o.mi.fields.pk.fieldIndex).SetUint(uint64(id)) + ind.FieldByIndex(o.mi.fields.pk.fieldIndex).SetUint(uint64(id)) } else { - ind.Field(o.mi.fields.pk.fieldIndex).SetInt(id) + ind.FieldByIndex(o.mi.fields.pk.fieldIndex).SetInt(id) } } } diff --git a/orm/orm_raw.go b/orm/orm_raw.go index cbb18064..5f88121c 100644 --- a/orm/orm_raw.go +++ b/orm/orm_raw.go @@ -342,7 +342,7 @@ func (o *rawSet) QueryRow(containers ...interface{}) error { for _, col := range columns { if fi := sMi.fields.GetByColumn(col); fi != nil { value := reflect.ValueOf(columnsMp[col]).Elem().Interface() - o.setFieldValue(ind.FieldByIndex([]int{fi.fieldIndex}), value) + o.setFieldValue(ind.FieldByIndex(fi.fieldIndex), value) } } } else { @@ -480,7 +480,7 @@ func (o *rawSet) QueryRows(containers ...interface{}) (int64, error) { for _, col := range columns { if fi := sMi.fields.GetByColumn(col); fi != nil { value := reflect.ValueOf(columnsMp[col]).Elem().Interface() - o.setFieldValue(ind.FieldByIndex([]int{fi.fieldIndex}), value) + o.setFieldValue(ind.FieldByIndex(fi.fieldIndex), value) } } } else {