// Add imports for each of the methods of the interface, but not the interface // itself. func addImportsForInterfaceMethods(imports importMap, it reflect.Type) { // Handle each method. for i := 0; i < it.NumMethod(); i++ { m := it.Method(i) addImportsForType(imports, m.Type) } }
func newControllerInfo(namespace string, t reflect.Type, defaultAction string) *controllerInfo { typeName := t.String() if strings.HasPrefix(typeName, "*") { panic(errInvalidCtrlType(typeName)) } numMethod := t.NumMethod() if numMethod < 1 { panic(errCtrlNoAction(typeName)) } methods := make([]string, 0, numMethod) for i := 0; i < numMethod; i++ { methodInfo := t.Method(i) numIn := methodInfo.Type.NumIn() numOut := methodInfo.Type.NumOut() if numIn != 1 || numOut != 1 { continue } methodName := methodInfo.Name methods = append(methods, methodName) } if len(methods) < 1 { panic(errCtrlNoAction(typeName)) } actions := make(map[string]string, len(methods)) for _, m := range methods { actions[strings.ToLower(m)] = m } return &controllerInfo{ NsName: namespace, CtrlName: getControllerName(t), CtrlType: t, Actions: actions, DefaultAction: defaultAction, } }
func createEventHandlersForType(sourceType reflect.Type) handlersMap { handlers := make(handlersMap) // Loop through all the methods of the source methodCount := sourceType.NumMethod() for i := 0; i < methodCount; i++ { method := sourceType.Method(i) // Only match methods that satisfy prefix if strings.HasPrefix(method.Name, methodHandlerPrefix) { // Handling methods are defined in code by: // func (source *MySource) HandleMyEvent(e MyEvent). // When getting the type of this methods by reflection the signature // is as following: // func HandleMyEvent(source *MySource, e MyEvent). if method.Type.NumIn() == 2 { eventType := method.Type.In(1) handler := createEventHandler(method) handlers[eventType] = handler } } } return handlers }
func deepFieldsImpl(ifaceType reflect.Type) []string { fields := []string{} if ifaceType.Kind() != reflect.Ptr && ifaceType.Kind() != reflect.Struct { return fields } methods := ifaceType.NumMethod() for i := 0; i < methods; i++ { var v reflect.Method v = ifaceType.Method(i) fields = append(fields, v.Name) } if ifaceType.Kind() == reflect.Ptr { return fields } elements := ifaceType.NumField() for i := 0; i < elements; i++ { var v reflect.StructField v = ifaceType.Field(i) fields = append(fields, v.Name) } return fields }
func (info *Info) addMethods(jt *Type, t reflect.Type) { // Add any methods. var vt reflect.Type if t.Kind() != reflect.Interface && !isWithoutReceiver(t) { t = reflect.PtrTo(t) vt = t.Elem() } for i := 0; i < t.NumMethod(); i++ { m := t.Method(i) if m.PkgPath != "" { continue } if t.Kind() != reflect.Interface { m.Type = withoutReceiverType{m.Type} } jm := Method{ Name: m.Name, Type: info.Ref(m.Type), } if vt != nil { _, hasValueMethod := vt.MethodByName(m.Name) jm.PtrReceiver = !hasValueMethod } if jt.Methods == nil { jt.Methods = make(map[string]*Method) } jt.Methods[jm.Name] = &jm } }
func (s *Service) findRPCMethods(typ reflect.Type) { for i := 0; i < typ.NumMethod(); i++ { m := typ.Method(i) // Don't register callbacks if m.Name == "Started" || m.Name == "Stopped" || m.Name == "Registered" || m.Name == "Unregistered" { continue } // Only register exported methods if m.PkgPath != "" { continue } if m.Type.NumOut() != 1 && m.Type.NumOut() != 2 { continue } s.methods[m.Name] = m.Func //s.Log.Println("Registered RPC Method: " + m.Name) s.Log.Item(RegisteredMethod{ Method: m.Name, }) } }
func generatemethodsEx(t reflect.Type, ignorefunc func(name string) bool, callobject string, name func(t reflect.Type, m reflect.Method) string) (methods string) { t2 := t if t.Kind() == reflect.Ptr { t2 = t.Elem() } for i := 0; i < t.NumMethod(); i++ { var ( m = t.Method(i) reason string ) if m.Name[0] != strings.ToUpper(m.Name[:1])[0] { reason = "unexported" goto skip } if ignorefunc != nil && ignorefunc(m.Name) { reason = "in skip list" goto skip } if m, err := generatemethod(m, t2, callobject, name(t2, m)); err != nil { reason = err.Error() goto skip } else { methods += m } continue skip: fmt.Printf("Skipping method %s.%s: %s\n", t2, m.Name, reason) } return }
// suitableMethods returns suitable Rpc methods of typ, it will report // error using log if reportErr is true. func suitableMethods(typ reflect.Type, reportErr bool) map[string]*methodType { methods := make(map[string]*methodType) OUTER: for m := 0; m < typ.NumMethod(); m++ { method := typ.Method(m) mtype := method.Type mname := method.Name // Method must be exported. if method.PkgPath != "" { continue } // Method needs at least one ins: receiver if mtype.NumIn() < 1 { if reportErr { log.Println("method", mname, "has wrong number of ins:", mtype.NumIn()) } continue } // check if all args are exported or built in types argTypes := make([]reflect.Type, mtype.NumIn()-1) for i := 1; i < mtype.NumIn(); i++ { // first is the receiver which we don't need if !isExportedOrBuiltinType(mtype.In(i)) { if reportErr { log.Printf("%s argument %d not an exported type - %v\n", mname, i, mtype.In(i)) } continue } argTypes[i-1] = mtype.In(i) } // check if all return values are exported or built in types var hasError bool outTypes := make([]reflect.Type, mtype.NumOut()) for i := 0; i < mtype.NumOut(); i++ { if mtype.Out(i) == typeOfError { if hasError { // verify if there is only a single error returned if reportErr { log.Printf("%s returns multiple errors\n", mname) continue OUTER } } hasError = true outTypes[i] = mtype.Out(i) } else if isExportedOrBuiltinType(mtype.Out(i)) { outTypes[i] = mtype.Out(i) continue } else { if reportErr { log.Printf("Returned argument #%d for %s is of invalid type %v\n", i, mname, mtype.Out(i)) } continue OUTER } } methods[mname] = &methodType{method: method, ArgTypes: argTypes, ReplyTypes: outTypes, CanRetErr: hasError} } return methods }
func methods(t reflect.Type) []string { res := []string{} for i := 0; i < t.NumMethod(); i++ { res = append(res, t.Method(i).Name) } return res }
func (c *structCache) Methods(typ reflect.Type) map[string]int { c.methodsl.RLock() indxs, ok := c.methods[typ] c.methodsl.RUnlock() if ok { return indxs } num := typ.NumMethod() indxs = make(map[string]int, num) for i := 0; i < num; i++ { m := typ.Method(i) if m.Type.NumIn() > 1 { continue } if m.Type.NumOut() != 1 { continue } indxs[m.Name] = m.Index } c.methodsl.Lock() c.methods[typ] = indxs c.methodsl.Unlock() return indxs }
// TODO: delete when reflect's own MethodByName is released. func methodByName(typ reflect.Type, name string) (reflect.Method, bool) { for i := 0; i < typ.NumMethod(); i++ { if typ.Method(i).Name == name { return typ.Method(i), true } } return reflect.Method{}, false }
func buildMethodData(t reflect.Type) map[string]reflect.Value { data := make(map[string]reflect.Value) for i, l := 0, t.NumMethod(); i < l; i++ { m := t.Method(i) data[strings.ToLower(m.Name)] = m.Func } return data }
func (e *Exchange) getMethodsForType(t reflect.Type) []string { r := []string{} for i := 0; i < t.NumMethod(); i++ { r = append(r, t.Method(i).Name) } return r }
// 合适的方法返回对应的Rpc方法,如果reportError设置为true的话,它会使用log来报告error。 func suitableMethods(typ reflect.Type, reportErr bool) map[string]*methodType { methods := make(map[string]*methodType) for m := 0; m < typ.NumMethod(); m++ { method := typ.Method(m) mtype := method.Type mname := method.Name // Method must be exported. if method.PkgPath != "" { continue } // Method needs three ins: receiver, *args, *reply. if mtype.NumIn() != 3 { if reportErr { log.Println("method", mname, "has wrong number of ins:", mtype.NumIn()) } continue } // First arg need not be a pointer. argType := mtype.In(1) if !isExportedOrBuiltinType(argType) { if reportErr { log.Println(mname, "argument type not exported:", argType) } continue } // Second arg must be a pointer. replyType := mtype.In(2) if replyType.Kind() != reflect.Ptr { if reportErr { log.Println("method", mname, "reply type not a pointer:", replyType) } continue } // Reply type must be exported. if !isExportedOrBuiltinType(replyType) { if reportErr { log.Println("method", mname, "reply type not exported:", replyType) } continue } // Method needs one out. if mtype.NumOut() != 1 { if reportErr { log.Println("method", mname, "has wrong number of outs:", mtype.NumOut()) } continue } // The return type of the method must be error. if returnType := mtype.Out(0); returnType != typeOfError { if reportErr { log.Println("method", mname, "returns", returnType.String(), "not error") } continue } methods[mname] = &methodType{method: method, ArgType: argType, ReplyType: replyType} } return methods }
func FindMethod(recvType reflect.Type, funcVal reflect.Value) *reflect.Method { for i := 0; i < recvType.NumMethod(); i++ { method := recvType.Method(i) if method.Func.Pointer() == funcVal.Pointer() { return &method } } return nil }
// methodIndex returns which method of rt implements the method. func methodIndex(rt reflect.Type, method string) int { for i := 0; i < rt.NumMethod(); i++ { if rt.Method(i).Name == method { return i } } errorf("internal error: can't find method %s", method) return 0 }
// ForeachMethod 遍历instance的所有方法 func ForeachMethod(instance reflect.Type, solve func(method reflect.Method) error) error { for i := 0; i < instance.NumMethod(); i++ { var err = solve(instance.Method(i)) if err != nil { return err } } return nil }
func FindMethod(cType reflect.Type, methodName string) *reflect.Method { for i := 0; i < cType.NumMethod(); i++ { method := cType.Method(i) if strings.ToLower(method.Name) == strings.ToLower(methodName) { return &method } } return nil }
func (h *Handler) findHandleFunc(t reflect.Type) *reflect.Method { for i := 0; i < t.NumMethod(); i++ { method := t.Method(i) if method.Name == flaglyHandle { return &method } } return nil }
func lookupMethod(t reflect.Type, name string) *reflect.Method { for i := 0; i < t.NumMethod(); i++ { m := t.Method(i) // fmt.Printf("%v: %d: %s\n", t, i, m.Name) if name == m.Name { return &m } } return nil }
func getMethods(it reflect.Type) []reflect.Method { numMethods := it.NumMethod() methods := make([]reflect.Method, numMethods) for i := 0; i < numMethods; i++ { methods[i] = it.Method(i) } return methods }
func missingMethod(iT, xT reflect.Type) (method string) { numMethod := iT.NumMethod() for i := 0; i < numMethod; i += 1 { method = iT.Method(i).Name if _, ok := xT.MethodByName(method); !ok { return } } return "" }
// payloadMethods loosly bases around suitableMethods from $GOROOT/src/net/rpc/server.go. func payloadMethods(typ reflect.Type) map[string]reflect.Method { methods := make(map[string]reflect.Method) LoopMethods: for i := 0; i < typ.NumMethod(); i++ { method := typ.Method(i) mtype := method.Type mname := method.Name if method.PkgPath != "" { continue LoopMethods } switch mtype.NumIn() { case 2: eventType := mtype.In(1) if eventType.Kind() != reflect.Ptr { log.Println("method", mname, "takes wrong type of event:", eventType) continue LoopMethods } event, ok := payloads.Name(eventType.Elem()) if !ok { log.Println("method", mname, "takes wrong type of event:", eventType) continue LoopMethods } if _, ok = methods[event]; ok { panic(fmt.Sprintf("there is more than one method handling %v event", eventType)) } methods[event] = method case 3: if mtype.In(1).Implements(contextType) && mtype.In(2).Kind() == reflect.Ptr { eventType := mtype.In(2) event, ok := payloads.Name(eventType.Elem()) if !ok { log.Println("method", mname, "takes wrong type of event:", eventType) continue LoopMethods } if _, ok = methods[event]; ok { panic(fmt.Sprintf("there is more than one method handling %v event", eventType)) } methods[event] = method continue } if mtype.In(1).Kind() != reflect.String || mtype.In(2) != empty { log.Println("wildcard method", mname, "takes wrong types of arguments") continue LoopMethods } if _, ok := methods["*"]; ok { panic("there is more than one method handling all events") } methods["*"] = method default: log.Println("method", mname, "takes wrong number of arguments:", mtype.NumIn()) continue LoopMethods } } return methods }
// Return the reflect.Method, given a Receiver type and Func value. func FindMethod(recvType reflect.Type, funcVal reflect.Value) *reflect.Method { // It is not possible to get the name of the method from the Func. // Instead, compare it to each method of the Controller. for i := 0; i < recvType.NumMethod(); i++ { method := recvType.Method(i) if method.Func.Pointer() == funcVal.Pointer() { return &method } } return nil }
// Given a type t, return all of the methods of t sorted such that source file // order is preserved. Order across files is undefined. Order within lines is // undefined. func getMethodsInSourceOrder(t reflect.Type) []reflect.Method { // Build the list of methods. methods := sortableMethodSet{} for i := 0; i < t.NumMethod(); i++ { methods = append(methods, t.Method(i)) } // Sort it. sort.Sort(methods) return methods }
func init() { var opcode Opcode var opcodeType reflect.Type = reflect.TypeOf(opcode) var opcodeValue reflect.Value = reflect.ValueOf(opcode) numMethods := opcodeType.NumMethod() for i := 0; i < numMethods; i++ { funcName := opcodeType.Method(i).Name funcValue := opcodeValue.Method(i) funcTable[funcName] = funcValue } }
func (s *Server) RegisterWithConfig(c interface{}, prefix string, cfg *ResponseConfig) error { var t reflect.Type v := reflect.ValueOf(c) if v.Kind() != reflect.Ptr { return fmt.Errorf("Invalid controller object passed (%s). Controller object should be a pointer", v.Kind()) } t = reflect.TypeOf(c) controllerName := reflect.Indirect(v).Type().Name() s.Log().Info(fmt.Sprintf("Registering %s", controllerName)) path := prefix fixUrlPath(&path, true, true) controllerName = strings.ToLower(controllerName) if strings.HasSuffix(controllerName, "controller") { controllerName = controllerName[0 : len(controllerName)-len("controller")] } path += controllerName + "/" if t == nil { } methodCount := t.NumMethod() for mi := 0; mi < methodCount; mi++ { method := t.Method(mi) // validate if this method match FnContent isFnContent := false tm := method.Type if tm.NumIn() == 2 && tm.In(1).String() == "*knot.Request" { if tm.NumOut() == 1 && tm.Out(0).Kind() == reflect.Interface { isFnContent = true } } if isFnContent { var fnc FnContent fnc = v.MethodByName(method.Name).Interface().(func(*Request) interface{}) methodName := method.Name handlerPath := path + strings.ToLower(methodName) s.Log().Info(fmt.Sprintf("Registering handler for %s", handlerPath)) newcfg := NewResponseConfig() *newcfg = *cfg if newcfg.OutputType == OutputTemplate && newcfg.ViewName == "" { newcfg.ViewName = strings.Join([]string{ strings.ToLower(controllerName), strings.ToLower(methodName)}, "/") + ".html" } s.RouteWithConfig(handlerPath, fnc, newcfg) } } return nil }
func ScanMethod(t reflect.Type) map[string]int { var ( methods map[string]int = make(map[string]int, t.NumMethod()) name string ) for i := 0; i < t.NumMethod(); i++ { name = t.Method(i).Name if len(name) > 5 && name[0:4] == "Act_" { methods[strings.ToLower(name[4:])] = i } } return methods }
func (ctx *Context) pushStructMethods(obj int, t reflect.Type, v reflect.Value) { mCount := t.NumMethod() for i := 0; i < mCount; i++ { methodName := t.Method(i).Name if !isExported(methodName) { continue } ctx.PushGoFunction(v.Method(i).Interface()) ctx.PutPropString(obj, nameToJavaScript(methodName)) } }
func typeString_Interface( t reflect.Type, pkgPath string) (s string) { var methods []string for i := 0; i < t.NumMethod(); i++ { m := t.Method(i) mString := typeString_FuncOrMethod(m.Name, m.Type, pkgPath) methods = append(methods, mString) } s = fmt.Sprintf("interface { %s }", strings.Join(methods, "; ")) return }