github.com/mavryk-network/mvgo@v1.19.9/internal/generate/golang.go (about)

     1  package generate
     2  
     3  import (
     4  	"fmt"
     5  	"strings"
     6  	"text/template"
     7  
     8  	"github.com/mavryk-network/mvgo/contract/ast"
     9  
    10  	"github.com/iancoleman/strcase"
    11  )
    12  
    13  var funcMap = template.FuncMap{
    14  	"receiver":    receiver,
    15  	"pascal":      strcase.ToCamel,
    16  	"camel":       strcase.ToLowerCamel,
    17  	"sub":         func(a, b int) int { return a - b },
    18  	"type":        goType,
    19  	"mkprim":      marshalPrimMethod,
    20  	"pathFromIdx": pathFromIndex,
    21  }
    22  
    23  func receiver(typeName string) string {
    24  	if typeName == "" {
    25  		return "_r"
    26  	}
    27  	return "_" + strings.ToLower(string(typeName[0]))
    28  }
    29  
    30  func goType(typ *ast.Struct) string {
    31  	switch typ.MichelineType {
    32  	case "nat", "mumav", "int":
    33  		return "*big.Int"
    34  	case "string":
    35  		return "string"
    36  	case "bool":
    37  		return "bool"
    38  	case "bytes", "key_hash":
    39  		return "[]byte"
    40  	case "timestamp":
    41  		return "time.Time"
    42  	case "address":
    43  		return "mavryk.Address"
    44  	case "key":
    45  		return "mavryk.Key"
    46  	case "unit":
    47  		return "struct{}"
    48  	case "chain_id":
    49  		return "mavryk.ChainIdHash"
    50  	case "signature":
    51  		return "mavryk.Signature"
    52  	case "struct":
    53  		return "*" + strcase.ToCamel(typ.Name)
    54  	case "big_map":
    55  		return fmt.Sprintf("bind.Bigmap[%s, %s]", goType(typ.Key), goType(typ.Value))
    56  	case "lambda":
    57  		return "bind.Lambda"
    58  	case "list", "set":
    59  		return "[]" + goType(typ.Type)
    60  	case "map":
    61  		return fmt.Sprintf("bind.Map[%s, %s]", goType(typ.Key), goType(typ.Value))
    62  	case "option":
    63  		return fmt.Sprintf("bind.Option[%s]", goType(typ.Type))
    64  	case "union":
    65  		return fmt.Sprintf("bind.Or[%s, %s]", goType(typ.LeftType), goType(typ.RightType))
    66  	case "operation", "contract":
    67  		return "any"
    68  		// skip
    69  	}
    70  
    71  	return "any"
    72  }
    73  
    74  func marshalPrimMethod(typ *ast.Struct) string {
    75  	switch typ.MichelineType {
    76  	case "nat", "int", "mumav":
    77  		return "micheline.NewBig(%s)"
    78  	case "string":
    79  		return "micheline.NewString(%s)"
    80  	case "bool":
    81  		return "mvgoext.MarshalPrimBool(%s)"
    82  	case "bytes", "keyhash":
    83  		return "micheline.NewBytes(%s)"
    84  	case "timestamp":
    85  		return "mvgoext.MarshalPrimTimestamp(%s)"
    86  	case "address":
    87  		return "micheline.NewString(%s.String())"
    88  	case "signature", "key", "chain_id":
    89  		return "micheline.NewBytes(%s.Bytes())"
    90  	case "list":
    91  		return "mvgoext.MarshalPrimSeq[" + goType(typ) + "](%s, mvgoext.MarshalAny)"
    92  	case "lambda", "struct":
    93  		return "%s.Prim"
    94  	default:
    95  		// case *types.Operation:
    96  		// case *types.Contract:
    97  		return "micheline.Prim{}/* %s */"
    98  	}
    99  }
   100  
   101  // pathFromIndex returns a path to a right-comb nested Pairs, from the index of a struct's field
   102  // and the total number of fields.
   103  func pathFromIndex(i, n int) string {
   104  	if n == 1 {
   105  		panic("pathFromIndex should not be called when a struct has 1 field")
   106  	}
   107  	if i == n-1 {
   108  		return strings.TrimSuffix(strings.Repeat("r/", n-1), "/")
   109  	}
   110  	return strings.Repeat("r/", i) + "l"
   111  }