github.com/informationsea/shellflow@v0.1.3/flowscript/flowscript_builtin.go (about) 1 package flowscript 2 3 import ( 4 "fmt" 5 "path" 6 "strings" 7 ) 8 9 type ScriptFunction struct { 10 call ScriptFunctionCall 11 name string 12 maxArgNum int 13 minArgNum int 14 } 15 16 func (s ScriptFunction) String() string { 17 return s.name 18 } 19 20 var BuiltinFunctions = map[string]*ScriptFunction{ 21 "basename": &ScriptFunction{ScriptFunctionCallBasename, "basename", 1, 2}, 22 "dirname": &ScriptFunction{ScriptFunctionCallDirname, "dirname", 1, 1}, 23 "prefix": &ScriptFunction{ScriptFunctionCallPrefix, "prefix", 2, 2}, 24 "zip": &ScriptFunction{ScriptFunctionCallZip, "zip", 2, 2}, 25 } 26 27 type ScriptFunctionCall func(args []Value) (Value, error) 28 29 func ScriptFunctionCallBasename(args []Value) (Value, error) { 30 if len(args) >= 3 { 31 return nil, fmt.Errorf("Too many arguments for basename") 32 } 33 if len(args) == 0 { 34 return nil, fmt.Errorf("one or two arguments are required for basename") 35 } 36 37 str, err := args[0].AsString() 38 if err != nil { 39 return nil, err 40 } 41 42 base := path.Base(str) 43 44 if len(args) == 2 { 45 str2, err2 := args[1].AsString() 46 if err2 != nil { 47 return nil, err2 48 } 49 if strings.HasSuffix(base, str2) { 50 return StringValue{base[:len(base)-len(str2)]}, nil 51 } 52 } 53 return StringValue{base}, nil 54 } 55 56 func ScriptFunctionCallDirname(args []Value) (Value, error) { 57 if len(args) >= 2 { 58 return nil, fmt.Errorf("Too many arguments for dirname") 59 } 60 if len(args) == 0 { 61 return nil, fmt.Errorf("one argument are required for dirname") 62 } 63 64 str, err := args[0].AsString() 65 if err != nil { 66 return nil, err 67 } 68 69 dir := path.Dir(str) 70 71 return StringValue{dir}, nil 72 } 73 74 func ScriptFunctionCallPrefix(args []Value) (Value, error) { 75 if len(args) != 2 { 76 return nil, fmt.Errorf("two arguments are required for prefix") 77 } 78 79 prefix, err := args[0].AsString() 80 if err != nil { 81 return nil, err 82 } 83 84 array, ok := args[1].(ArrayValue) 85 if !ok { 86 return nil, fmt.Errorf("%s is not array", args[1]) 87 } 88 89 values := make([]Value, len(array.value)) 90 for i, v := range args { 91 s, e := v.AsString() 92 if e != nil { 93 return nil, e 94 } 95 values[i] = StringValue{prefix + s} 96 } 97 98 return ArrayValue{values}, nil 99 } 100 101 func ScriptFunctionCallZip(args []Value) (Value, error) { 102 if len(args) != 2 { 103 return nil, fmt.Errorf("two arguments are required for zip") 104 } 105 106 array1, ok := args[0].(ArrayValue) 107 if !ok { 108 return nil, fmt.Errorf("%s is not array", args[0]) 109 } 110 111 array2, ok := args[1].(ArrayValue) 112 if !ok { 113 return nil, fmt.Errorf("%s is not array", args[1]) 114 } 115 116 var newLength int 117 if len(array1.Value()) > len(array2.Value()) { 118 newLength = len(array2.Value()) 119 } else { 120 newLength = len(array1.Value()) 121 } 122 123 values := make([]Value, newLength) 124 for i := 0; i < newLength; i++ { 125 pair := [...]Value{array1.Value()[i], array2.Value()[i]} 126 values[i] = ArrayValue{pair[:]} 127 } 128 129 return ArrayValue{values}, nil 130 }