This commit is contained in:
crusader 2018-04-10 21:30:57 +09:00
parent 05707fb828
commit 8c5c5b0311
4 changed files with 51 additions and 56 deletions

View File

@ -67,7 +67,7 @@ type Annotation interface {
// @Inject(name? string) // @Inject(name? string)
// @Resource(name? string) // @Resource(name? string)
func ParseAnnotation(tag reflect.StructTag) (map[string]Annotation, error) { func ParseAnnotation(tag reflect.StructTag) (map[reflect.Type]Annotation, error) {
s := strings.Trim(tag.Get(AnnotationTag), " ") s := strings.Trim(tag.Get(AnnotationTag), " ")
if "" == s { if "" == s {
return nil, nil return nil, nil
@ -82,13 +82,13 @@ func ParseAnnotation(tag reflect.StructTag) (map[string]Annotation, error) {
return nil, nil return nil, nil
} }
rKVs := make(map[string]Annotation, 0) rKVs := make(map[reflect.Type]Annotation, 0)
for name, attributes := range annotations { for name, attributes := range annotations {
annotation, err := newAnnotation(name, attributes) t, annotation, err := newAnnotation(name, attributes)
if nil != err { if nil != err {
return nil, err return nil, err
} }
rKVs[name] = annotation rKVs[t] = annotation
} }
return rKVs, nil return rKVs, nil
@ -155,10 +155,10 @@ func splitAnnotationAttribute(s string) (map[string]string, error) {
return ss, nil return ss, nil
} }
func newAnnotation(name string, attributes map[string]string) (Annotation, error) { func newAnnotation(name string, attributes map[string]string) (reflect.Type, Annotation, error) {
def, ok := annotationRegistry[name] def, ok := annotationRegistry[name]
if !ok { if !ok {
return nil, fmt.Errorf("There is no annotation[%s]", name) return nil, nil, fmt.Errorf("There is no annotation[%s]", name)
} }
v := reflect.New(def.rt) v := reflect.New(def.rt)
@ -167,7 +167,7 @@ func newAnnotation(name string, attributes map[string]string) (Annotation, error
if nil != attributes { if nil != attributes {
setMetaAttributes(def, v.Elem(), attributes) setMetaAttributes(def, v.Elem(), attributes)
} }
return i, nil return def.t, i, nil
} }
// func parseAnnotationItem(a string) (name string, attributes map[string]string, err error) { // func parseAnnotationItem(a string) (name string, attributes map[string]string, err error) {

View File

@ -15,24 +15,20 @@ type TypeDefinition struct {
Type reflect.Type Type reflect.Type
RealType reflect.Type RealType reflect.Type
TypeAnnotations map[string]cda.Annotation TypeAnnotations map[reflect.Type]cda.Annotation
MethodAnnotations map[string]map[string]cda.Annotation MethodAnnotations map[string]map[reflect.Type]cda.Annotation
Fields []*FieldDefinition Fields []*FieldDefinition
} }
func (td *TypeDefinition) GetAnnotation(name string) cda.Annotation {
if nil == td.TypeAnnotations {
return nil
}
return td.TypeAnnotations[name]
}
func (td *TypeDefinition) GetTypeAnnotationByType(at reflect.Type, includeEmbedding bool) cda.Annotation { func (td *TypeDefinition) GetTypeAnnotationByType(at reflect.Type, includeEmbedding bool) cda.Annotation {
if nil == td.TypeAnnotations { if nil == td.TypeAnnotations {
return nil return nil
} }
if !includeEmbedding {
return td.TypeAnnotations[at]
}
for _, v := range td.TypeAnnotations { for _, v := range td.TypeAnnotations {
if at == reflect.TypeOf(v) { if at == reflect.TypeOf(v) {
return v return v
@ -58,15 +54,26 @@ func (td *TypeDefinition) GetMethodAnnotationByType(at reflect.Type, methodName
return nil return nil
} }
for _, v := range ms { return ms[at]
if at == reflect.TypeOf(v) {
return v
}
} }
func (td *TypeDefinition) GetMethodAnnotationsByType(at reflect.Type) map[string]cda.Annotation {
if nil == td.MethodAnnotations {
return nil return nil
} }
mas := make(map[string]cda.Annotation)
for k, v := range td.MethodAnnotations {
a, ok := v[at]
if !ok {
continue
}
mas[k] = a
}
return mas
}
func checkAnnotation(t reflect.Type, st reflect.Type) bool { func checkAnnotation(t reflect.Type, st reflect.Type) bool {
rt, _, _ := cur.GetTypeInfo(t) rt, _, _ := cur.GetTypeInfo(t)
if reflect.Struct != rt.Kind() { if reflect.Struct != rt.Kind() {
@ -96,14 +103,7 @@ type FieldDefinition struct {
Type reflect.Type Type reflect.Type
RealType reflect.Type RealType reflect.Type
Annotations map[string]cda.Annotation Annotations map[reflect.Type]cda.Annotation
}
func (fd *FieldDefinition) GetAnnotation(name string) cda.Annotation {
if nil == fd.Annotations {
return nil
}
return fd.Annotations[name]
} }
func (fd *FieldDefinition) GetAnnotationByType(at reflect.Type, includeEmbedding bool) cda.Annotation { func (fd *FieldDefinition) GetAnnotationByType(at reflect.Type, includeEmbedding bool) cda.Annotation {
@ -111,6 +111,10 @@ func (fd *FieldDefinition) GetAnnotationByType(at reflect.Type, includeEmbedding
return nil return nil
} }
if !includeEmbedding {
return fd.Annotations[at]
}
for _, v := range fd.Annotations { for _, v := range fd.Annotations {
if at == reflect.TypeOf(v) { if at == reflect.TypeOf(v) {
return v return v

View File

@ -29,6 +29,7 @@ type ComponentRegistry interface {
GetTypeAnnotation(instanceType reflect.Type, annotationType reflect.Type) cda.Annotation GetTypeAnnotation(instanceType reflect.Type, annotationType reflect.Type) cda.Annotation
GetMethodAnnotation(instanceType reflect.Type, annotationType reflect.Type, methodName string) cda.Annotation GetMethodAnnotation(instanceType reflect.Type, annotationType reflect.Type, methodName string) cda.Annotation
GetMethodAnnotations(instanceType reflect.Type, annotationType reflect.Type) map[string]cda.Annotation
} }
func newRegistry() ComponentRegistry { func newRegistry() ComponentRegistry {
@ -215,30 +216,6 @@ func (cr *defaultComponentRegistry) GetInstances(ts []reflect.Type) ([]interface
return instances, nil return instances, nil
} }
// GetInstancesByAnnotationName returns instance of annotated
// n must be name of registered annotation
// func GetInstancesByAnnotationName(n string) ([]interface{}, error) {
// return registry.GetInstancesByAnnotationName(n)
// }
// func (cr *defaultComponentRegistry) GetInstancesByAnnotationName(n string) ([]interface{}, error) {
// var (
// i interface{}
// err error
// )
// instances := make([]interface{}, 0)
// for _, td := range cr.definitionByType {
// if nil != td.GetAnnotation(n) {
// if i, err = cr.GetInstance(td.Type); nil != err {
// return nil, err
// }
// instances = append(instances, i)
// }
// }
// return instances, nil
// }
func GetInstancesByAnnotationType(t reflect.Type) ([]interface{}, error) { func GetInstancesByAnnotationType(t reflect.Type) ([]interface{}, error) {
return registry.GetInstancesByAnnotationType(t) return registry.GetInstancesByAnnotationType(t)
} }
@ -286,6 +263,20 @@ func (cr *defaultComponentRegistry) GetMethodAnnotation(instanceType reflect.Typ
return def.GetMethodAnnotationByType(annotationType, methodName) return def.GetMethodAnnotationByType(annotationType, methodName)
} }
func GetMethodAnnotations(instanceType reflect.Type, annotationType reflect.Type) map[string]cda.Annotation {
return registry.GetMethodAnnotations(instanceType, annotationType)
}
func (cr *defaultComponentRegistry) GetMethodAnnotations(instanceType reflect.Type, annotationType reflect.Type) map[string]cda.Annotation {
rt, _, _ := cur.GetTypeInfo(instanceType)
def, ok := cr.definitionByType[rt]
if !ok {
return nil
}
return def.GetMethodAnnotationsByType(annotationType)
}
func (cr *defaultComponentRegistry) buildDefinition(t reflect.Type) (*TypeDefinition, error) { func (cr *defaultComponentRegistry) buildDefinition(t reflect.Type) (*TypeDefinition, error) {
if nil == t { if nil == t {
return nil, fmt.Errorf("t[reflect.Type] is nil") return nil, fmt.Errorf("t[reflect.Type] is nil")
@ -384,7 +375,7 @@ func parseMethodAnnotation(f *reflect.StructField, td *TypeDefinition) bool {
if nil != as && 0 < len(as) { if nil != as && 0 < len(as) {
if nil == td.MethodAnnotations { if nil == td.MethodAnnotations {
td.MethodAnnotations = make(map[string]map[string]cda.Annotation, 0) td.MethodAnnotations = make(map[string]map[reflect.Type]cda.Annotation, 0)
} }
td.MethodAnnotations[f.Name[1:]] = as td.MethodAnnotations[f.Name[1:]] = as
return true return true

View File

@ -50,7 +50,7 @@ func TestRegisterType(t *testing.T) {
} }
type AService struct { type AService struct {
annotation.TypeAnnotation `annotation:"@Component(name='dkdkdf', methods='[1, 2]')"` annotation.TypeAnnotation `annotation:"@Component(name='dkdkdf')"`
NameA string NameA string
} }