sq/libsq/core/urlz/urlz.go
Neil O'Toole 9cb42bf579
#244: shell completion for "sq add LOCATION" (#246)
- Shell completion for `sq add LOCATION`.
2023-06-13 10:06:18 -06:00

106 lines
2.2 KiB
Go

// Package urlz contains URL utility functionality.
package urlz
import (
"net/url"
"strings"
"github.com/neilotoole/sq/libsq/core/errz"
)
// QueryParamKeys returns the keys of a URL query. This function
// exists because url.ParseQuery returns a url.Values, which is a
// map type, and the keys don't preserve order.
func QueryParamKeys(query string) (keys []string, err error) {
// Code is adapted from url.ParseQuery.
for query != "" {
var key string
key, query, _ = strings.Cut(query, "&")
if strings.Contains(key, ";") {
err = errz.Errorf("invalid semicolon separator in query")
continue
}
if key == "" {
continue
}
key, _, _ = strings.Cut(key, "=")
key, err1 := url.QueryUnescape(key)
if err1 != nil {
if err == nil {
err = errz.Err(err1)
}
continue
}
keys = append(keys, key)
}
return keys, err
}
// RenameQueryParamKey renames all instances of oldKey in query
// to newKey, where query is a URL query string.
func RenameQueryParamKey(query, oldKey, newKey string) string {
if query == "" {
return ""
}
parts := strings.Split(query, "&")
for i, part := range parts {
if part == oldKey {
parts[i] = newKey
continue
}
if strings.HasPrefix(part, oldKey+"=") {
parts[i] = strings.Replace(part, oldKey, newKey, 1)
}
}
return strings.Join(parts, "&")
}
// StripQuery strips the query params from u.
func StripQuery(u url.URL) string {
u.RawQuery = ""
u.ForceQuery = false
return u.String()
}
// StripPath strips the url's path. If stripQuery is true, the
// query is also stripped.
func StripPath(u url.URL, stripQuery bool) string {
u.Path = ""
if stripQuery {
u.RawQuery = ""
u.ForceQuery = false
}
return u.String()
}
// StripUser strips the URL's user info.
func StripUser(u url.URL) string {
u2 := u
u2.User = nil
s := u2.String()
return s
}
// StripScheme removes the URL's scheme.
func StripScheme(u url.URL) string {
u2 := u
u2.Scheme = ""
s := u2.String()
s = strings.TrimPrefix(s, "//")
return s
}
// StripSchemeAndUser removes the URL's scheme and user info.
func StripSchemeAndUser(u url.URL) string {
u2 := u
u2.User = nil
u2.Scheme = ""
s := u2.String()
s = strings.TrimPrefix(s, "//")
return s
}