(b []byte)
| 16 | } |
| 17 | |
| 18 | func parseFuncDef(b []byte) (*funcType, error) { |
| 19 | defStr := string(b) |
| 20 | |
| 21 | // extract func name |
| 22 | n := strings.Index(defStr, "(") |
| 23 | if n < 0 { |
| 24 | return nil, fmt.Errorf("cannot find '(' in function definition") |
| 25 | } |
| 26 | name := defStr[:n] |
| 27 | defStr = defStr[n+1:] |
| 28 | defPrefix := "" |
| 29 | callPrefix := "" |
| 30 | if len(name) == 0 { |
| 31 | // Either empty func name or valid method definition. Let's check. |
| 32 | |
| 33 | // parse method receiver |
| 34 | n = strings.Index(defStr, ")") |
| 35 | if n < 0 { |
| 36 | return nil, fmt.Errorf("cannot find ')' in func") |
| 37 | } |
| 38 | recvStr := defStr[:n] |
| 39 | defStr = defStr[n+1:] |
| 40 | exprStr := fmt.Sprintf("func (%s)", recvStr) |
| 41 | expr, err := goparser.ParseExpr(exprStr) |
| 42 | if err != nil { |
| 43 | return nil, fmt.Errorf("invalid method definition: %s", err) |
| 44 | } |
| 45 | ft := expr.(*ast.FuncType) |
| 46 | if len(ft.Params.List) != 1 || len(ft.Params.List[0].Names) != 1 { |
| 47 | // method receiver must contain only one param |
| 48 | return nil, fmt.Errorf("missing func or method name") |
| 49 | } |
| 50 | recvName := ft.Params.List[0].Names[0].Name |
| 51 | defPrefix = fmt.Sprintf("(%s) ", recvStr) |
| 52 | callPrefix = recvName + "." |
| 53 | |
| 54 | // extract method name |
| 55 | n = strings.Index(defStr, "(") |
| 56 | if n < 0 { |
| 57 | return nil, fmt.Errorf("missing func name") |
| 58 | } |
| 59 | name = string(stripLeadingSpace([]byte(defStr[:n]))) |
| 60 | if len(name) == 0 { |
| 61 | return nil, fmt.Errorf("missing method name") |
| 62 | } |
| 63 | defStr = defStr[n+1:] |
| 64 | } |
| 65 | |
| 66 | // validate and collect func args |
| 67 | if len(defStr) == 0 || defStr[len(defStr)-1] != ')' { |
| 68 | return nil, fmt.Errorf("missing ')' at the end of func") |
| 69 | } |
| 70 | args := defStr[:len(defStr)-1] |
| 71 | exprStr := fmt.Sprintf("func (%s)", args) |
| 72 | expr, err := goparser.ParseExpr(exprStr) |
| 73 | if err != nil { |
| 74 | return nil, fmt.Errorf("invalid func args: %s", err) |
| 75 | } |
searching dependent graphs…