convert.go (8941B)
1 package runtime 2 3 import ( 4 "encoding/base64" 5 "fmt" 6 "strconv" 7 "strings" 8 9 "google.golang.org/protobuf/encoding/protojson" 10 "google.golang.org/protobuf/types/known/durationpb" 11 "google.golang.org/protobuf/types/known/timestamppb" 12 "google.golang.org/protobuf/types/known/wrapperspb" 13 ) 14 15 // String just returns the given string. 16 // It is just for compatibility to other types. 17 func String(val string) (string, error) { 18 return val, nil 19 } 20 21 // StringSlice converts 'val' where individual strings are separated by 22 // 'sep' into a string slice. 23 func StringSlice(val, sep string) ([]string, error) { 24 return strings.Split(val, sep), nil 25 } 26 27 // Bool converts the given string representation of a boolean value into bool. 28 func Bool(val string) (bool, error) { 29 return strconv.ParseBool(val) 30 } 31 32 // BoolSlice converts 'val' where individual booleans are separated by 33 // 'sep' into a bool slice. 34 func BoolSlice(val, sep string) ([]bool, error) { 35 s := strings.Split(val, sep) 36 values := make([]bool, len(s)) 37 for i, v := range s { 38 value, err := Bool(v) 39 if err != nil { 40 return values, err 41 } 42 values[i] = value 43 } 44 return values, nil 45 } 46 47 // Float64 converts the given string representation into representation of a floating point number into float64. 48 func Float64(val string) (float64, error) { 49 return strconv.ParseFloat(val, 64) 50 } 51 52 // Float64Slice converts 'val' where individual floating point numbers are separated by 53 // 'sep' into a float64 slice. 54 func Float64Slice(val, sep string) ([]float64, error) { 55 s := strings.Split(val, sep) 56 values := make([]float64, len(s)) 57 for i, v := range s { 58 value, err := Float64(v) 59 if err != nil { 60 return values, err 61 } 62 values[i] = value 63 } 64 return values, nil 65 } 66 67 // Float32 converts the given string representation of a floating point number into float32. 68 func Float32(val string) (float32, error) { 69 f, err := strconv.ParseFloat(val, 32) 70 if err != nil { 71 return 0, err 72 } 73 return float32(f), nil 74 } 75 76 // Float32Slice converts 'val' where individual floating point numbers are separated by 77 // 'sep' into a float32 slice. 78 func Float32Slice(val, sep string) ([]float32, error) { 79 s := strings.Split(val, sep) 80 values := make([]float32, len(s)) 81 for i, v := range s { 82 value, err := Float32(v) 83 if err != nil { 84 return values, err 85 } 86 values[i] = value 87 } 88 return values, nil 89 } 90 91 // Int64 converts the given string representation of an integer into int64. 92 func Int64(val string) (int64, error) { 93 return strconv.ParseInt(val, 0, 64) 94 } 95 96 // Int64Slice converts 'val' where individual integers are separated by 97 // 'sep' into a int64 slice. 98 func Int64Slice(val, sep string) ([]int64, error) { 99 s := strings.Split(val, sep) 100 values := make([]int64, len(s)) 101 for i, v := range s { 102 value, err := Int64(v) 103 if err != nil { 104 return values, err 105 } 106 values[i] = value 107 } 108 return values, nil 109 } 110 111 // Int32 converts the given string representation of an integer into int32. 112 func Int32(val string) (int32, error) { 113 i, err := strconv.ParseInt(val, 0, 32) 114 if err != nil { 115 return 0, err 116 } 117 return int32(i), nil 118 } 119 120 // Int32Slice converts 'val' where individual integers are separated by 121 // 'sep' into a int32 slice. 122 func Int32Slice(val, sep string) ([]int32, error) { 123 s := strings.Split(val, sep) 124 values := make([]int32, len(s)) 125 for i, v := range s { 126 value, err := Int32(v) 127 if err != nil { 128 return values, err 129 } 130 values[i] = value 131 } 132 return values, nil 133 } 134 135 // Uint64 converts the given string representation of an integer into uint64. 136 func Uint64(val string) (uint64, error) { 137 return strconv.ParseUint(val, 0, 64) 138 } 139 140 // Uint64Slice converts 'val' where individual integers are separated by 141 // 'sep' into a uint64 slice. 142 func Uint64Slice(val, sep string) ([]uint64, error) { 143 s := strings.Split(val, sep) 144 values := make([]uint64, len(s)) 145 for i, v := range s { 146 value, err := Uint64(v) 147 if err != nil { 148 return values, err 149 } 150 values[i] = value 151 } 152 return values, nil 153 } 154 155 // Uint32 converts the given string representation of an integer into uint32. 156 func Uint32(val string) (uint32, error) { 157 i, err := strconv.ParseUint(val, 0, 32) 158 if err != nil { 159 return 0, err 160 } 161 return uint32(i), nil 162 } 163 164 // Uint32Slice converts 'val' where individual integers are separated by 165 // 'sep' into a uint32 slice. 166 func Uint32Slice(val, sep string) ([]uint32, error) { 167 s := strings.Split(val, sep) 168 values := make([]uint32, len(s)) 169 for i, v := range s { 170 value, err := Uint32(v) 171 if err != nil { 172 return values, err 173 } 174 values[i] = value 175 } 176 return values, nil 177 } 178 179 // Bytes converts the given string representation of a byte sequence into a slice of bytes 180 // A bytes sequence is encoded in URL-safe base64 without padding 181 func Bytes(val string) ([]byte, error) { 182 b, err := base64.StdEncoding.DecodeString(val) 183 if err != nil { 184 b, err = base64.URLEncoding.DecodeString(val) 185 if err != nil { 186 return nil, err 187 } 188 } 189 return b, nil 190 } 191 192 // BytesSlice converts 'val' where individual bytes sequences, encoded in URL-safe 193 // base64 without padding, are separated by 'sep' into a slice of bytes slices slice. 194 func BytesSlice(val, sep string) ([][]byte, error) { 195 s := strings.Split(val, sep) 196 values := make([][]byte, len(s)) 197 for i, v := range s { 198 value, err := Bytes(v) 199 if err != nil { 200 return values, err 201 } 202 values[i] = value 203 } 204 return values, nil 205 } 206 207 // Timestamp converts the given RFC3339 formatted string into a timestamp.Timestamp. 208 func Timestamp(val string) (*timestamppb.Timestamp, error) { 209 var r timestamppb.Timestamp 210 val = strconv.Quote(strings.Trim(val, `"`)) 211 unmarshaler := &protojson.UnmarshalOptions{} 212 err := unmarshaler.Unmarshal([]byte(val), &r) 213 if err != nil { 214 return nil, err 215 } 216 return &r, nil 217 } 218 219 // Duration converts the given string into a timestamp.Duration. 220 func Duration(val string) (*durationpb.Duration, error) { 221 var r durationpb.Duration 222 val = strconv.Quote(strings.Trim(val, `"`)) 223 unmarshaler := &protojson.UnmarshalOptions{} 224 err := unmarshaler.Unmarshal([]byte(val), &r) 225 if err != nil { 226 return nil, err 227 } 228 return &r, nil 229 } 230 231 // Enum converts the given string into an int32 that should be type casted into the 232 // correct enum proto type. 233 func Enum(val string, enumValMap map[string]int32) (int32, error) { 234 e, ok := enumValMap[val] 235 if ok { 236 return e, nil 237 } 238 239 i, err := Int32(val) 240 if err != nil { 241 return 0, fmt.Errorf("%s is not valid", val) 242 } 243 for _, v := range enumValMap { 244 if v == i { 245 return i, nil 246 } 247 } 248 return 0, fmt.Errorf("%s is not valid", val) 249 } 250 251 // EnumSlice converts 'val' where individual enums are separated by 'sep' 252 // into a int32 slice. Each individual int32 should be type casted into the 253 // correct enum proto type. 254 func EnumSlice(val, sep string, enumValMap map[string]int32) ([]int32, error) { 255 s := strings.Split(val, sep) 256 values := make([]int32, len(s)) 257 for i, v := range s { 258 value, err := Enum(v, enumValMap) 259 if err != nil { 260 return values, err 261 } 262 values[i] = value 263 } 264 return values, nil 265 } 266 267 /* 268 Support fot google.protobuf.wrappers on top of primitive types 269 */ 270 271 // StringValue well-known type support as wrapper around string type 272 func StringValue(val string) (*wrapperspb.StringValue, error) { 273 return &wrapperspb.StringValue{Value: val}, nil 274 } 275 276 // FloatValue well-known type support as wrapper around float32 type 277 func FloatValue(val string) (*wrapperspb.FloatValue, error) { 278 parsedVal, err := Float32(val) 279 return &wrapperspb.FloatValue{Value: parsedVal}, err 280 } 281 282 // DoubleValue well-known type support as wrapper around float64 type 283 func DoubleValue(val string) (*wrapperspb.DoubleValue, error) { 284 parsedVal, err := Float64(val) 285 return &wrapperspb.DoubleValue{Value: parsedVal}, err 286 } 287 288 // BoolValue well-known type support as wrapper around bool type 289 func BoolValue(val string) (*wrapperspb.BoolValue, error) { 290 parsedVal, err := Bool(val) 291 return &wrapperspb.BoolValue{Value: parsedVal}, err 292 } 293 294 // Int32Value well-known type support as wrapper around int32 type 295 func Int32Value(val string) (*wrapperspb.Int32Value, error) { 296 parsedVal, err := Int32(val) 297 return &wrapperspb.Int32Value{Value: parsedVal}, err 298 } 299 300 // UInt32Value well-known type support as wrapper around uint32 type 301 func UInt32Value(val string) (*wrapperspb.UInt32Value, error) { 302 parsedVal, err := Uint32(val) 303 return &wrapperspb.UInt32Value{Value: parsedVal}, err 304 } 305 306 // Int64Value well-known type support as wrapper around int64 type 307 func Int64Value(val string) (*wrapperspb.Int64Value, error) { 308 parsedVal, err := Int64(val) 309 return &wrapperspb.Int64Value{Value: parsedVal}, err 310 } 311 312 // UInt64Value well-known type support as wrapper around uint64 type 313 func UInt64Value(val string) (*wrapperspb.UInt64Value, error) { 314 parsedVal, err := Uint64(val) 315 return &wrapperspb.UInt64Value{Value: parsedVal}, err 316 } 317 318 // BytesValue well-known type support as wrapper around bytes[] type 319 func BytesValue(val string) (*wrapperspb.BytesValue, error) { 320 parsedVal, err := Bytes(val) 321 return &wrapperspb.BytesValue{Value: parsedVal}, err 322 }