1package httpbinding
2
3import (
4 "math"
5 "math/big"
6 "strconv"
7 "strings"
8)
9
10// URIValue is used to encode named URI parameters
11type URIValue struct {
12 path, rawPath, buffer *[]byte
13
14 key string
15}
16
17func newURIValue(path *[]byte, rawPath *[]byte, buffer *[]byte, key string) URIValue {
18 return URIValue{path: path, rawPath: rawPath, buffer: buffer, key: key}
19}
20
21func (u URIValue) modifyURI(value string) (err error) {
22 *u.path, *u.buffer, err = replacePathElement(*u.path, *u.buffer, u.key, value, false)
23 if err != nil {
24 return err
25 }
26 *u.rawPath, *u.buffer, err = replacePathElement(*u.rawPath, *u.buffer, u.key, value, true)
27 return err
28}
29
30// Boolean encodes v as a URI string value
31func (u URIValue) Boolean(v bool) error {
32 return u.modifyURI(strconv.FormatBool(v))
33}
34
35// String encodes v as a URI string value
36func (u URIValue) String(v string) error {
37 return u.modifyURI(v)
38}
39
40// Byte encodes v as a URI string value
41func (u URIValue) Byte(v int8) error {
42 return u.Long(int64(v))
43}
44
45// Short encodes v as a URI string value
46func (u URIValue) Short(v int16) error {
47 return u.Long(int64(v))
48}
49
50// Integer encodes v as a URI string value
51func (u URIValue) Integer(v int32) error {
52 return u.Long(int64(v))
53}
54
55// Long encodes v as a URI string value
56func (u URIValue) Long(v int64) error {
57 return u.modifyURI(strconv.FormatInt(v, 10))
58}
59
60// Float encodes v as a query string value
61func (u URIValue) Float(v float32) error {
62 return u.float(float64(v), 32)
63}
64
65// Double encodes v as a query string value
66func (u URIValue) Double(v float64) error {
67 return u.float(v, 64)
68}
69
70func (u URIValue) float(v float64, bitSize int) error {
71 switch {
72 case math.IsNaN(v):
73 return u.String(floatNaN)
74 case math.IsInf(v, 1):
75 return u.String(floatInfinity)
76 case math.IsInf(v, -1):
77 return u.String(floatNegInfinity)
78 default:
79 return u.modifyURI(strconv.FormatFloat(v, 'f', -1, bitSize))
80 }
81}
82
83// BigInteger encodes v as a query string value
84func (u URIValue) BigInteger(v *big.Int) error {
85 return u.modifyURI(v.String())
86}
87
88// BigDecimal encodes v as a query string value
89func (u URIValue) BigDecimal(v *big.Float) error {
90 if i, accuracy := v.Int64(); accuracy == big.Exact {
91 return u.Long(i)
92 }
93 return u.modifyURI(v.Text('e', -1))
94}
95
96// SplitURI parses a Smithy HTTP binding trait URI
97func SplitURI(uri string) (path, query string) {
98 queryStart := strings.IndexRune(uri, '?')
99 if queryStart == -1 {
100 path = uri
101 return path, query
102 }
103
104 path = uri[:queryStart]
105 if queryStart+1 >= len(uri) {
106 return path, query
107 }
108 query = uri[queryStart+1:]
109
110 return path, query
111}