replacePathElement replaces a single element in the path []byte. Escape is used to control whether the value will be escaped using Amazon path escape style.
(path, fieldBuf []byte, key, val string, escape bool)
| 22 | // replacePathElement replaces a single element in the path []byte. |
| 23 | // Escape is used to control whether the value will be escaped using Amazon path escape style. |
| 24 | func replacePathElement(path, fieldBuf []byte, key, val string, escape bool) ([]byte, []byte, error) { |
| 25 | // search for "{<key>}". If not found, search for the greedy version "{<key>+}". If none are found, return error |
| 26 | fieldBuf = bufCap(fieldBuf, len(key)+2) // { <key> } |
| 27 | fieldBuf = append(fieldBuf, uriTokenStart) |
| 28 | fieldBuf = append(fieldBuf, key...) |
| 29 | fieldBuf = append(fieldBuf, uriTokenStop) |
| 30 | |
| 31 | start := bytes.Index(path, fieldBuf) |
| 32 | encodeSep := true |
| 33 | if start < 0 { |
| 34 | fieldBuf = bufCap(fieldBuf, len(key)+3) // { <key> [+] } |
| 35 | fieldBuf = append(fieldBuf, uriTokenStart) |
| 36 | fieldBuf = append(fieldBuf, key...) |
| 37 | fieldBuf = append(fieldBuf, uriTokenSkip) |
| 38 | fieldBuf = append(fieldBuf, uriTokenStop) |
| 39 | |
| 40 | start = bytes.Index(path, fieldBuf) |
| 41 | if start < 0 { |
| 42 | return path, fieldBuf, fmt.Errorf("invalid path index, start=%d. %s", start, path) |
| 43 | } |
| 44 | encodeSep = false |
| 45 | } |
| 46 | end := start + len(fieldBuf) |
| 47 | |
| 48 | if escape { |
| 49 | val = EscapePath(val, encodeSep) |
| 50 | } |
| 51 | |
| 52 | fieldBuf = bufCap(fieldBuf, len(val)) |
| 53 | fieldBuf = append(fieldBuf, val...) |
| 54 | |
| 55 | keyLen := end - start |
| 56 | valLen := len(fieldBuf) |
| 57 | |
| 58 | if keyLen == valLen { |
| 59 | copy(path[start:], fieldBuf) |
| 60 | return path, fieldBuf, nil |
| 61 | } |
| 62 | |
| 63 | newLen := len(path) + (valLen - keyLen) |
| 64 | if len(path) < newLen { |
| 65 | path = path[:cap(path)] |
| 66 | } |
| 67 | if cap(path) < newLen { |
| 68 | newURI := make([]byte, newLen) |
| 69 | copy(newURI, path) |
| 70 | path = newURI |
| 71 | } |
| 72 | |
| 73 | // shift |
| 74 | copy(path[start+valLen:], path[end:]) |
| 75 | path = path[:newLen] |
| 76 | copy(path[start:], fieldBuf) |
| 77 | |
| 78 | return path, fieldBuf, nil |
| 79 | } |
| 80 | |
| 81 | // EscapePath escapes part of a URL path in Amazon style. |