|
|
@@ -12,55 +12,60 @@ import "strings"
|
|
|
// See https://www.iana.org/assignments/uri-schemes/uri-schemes.xhtml
|
|
|
var validURISchemes = []string{
|
|
|
// Most commong schemes on top.
|
|
|
- "https:",
|
|
|
- "http:",
|
|
|
+ "https",
|
|
|
+ "http",
|
|
|
|
|
|
// Then the rest.
|
|
|
- "apt:",
|
|
|
- "bitcoin:",
|
|
|
- "callto:",
|
|
|
- "dav:",
|
|
|
- "davs:",
|
|
|
- "ed2k:",
|
|
|
- "facetime:",
|
|
|
- "feed:",
|
|
|
- "ftp:",
|
|
|
- "geo:",
|
|
|
- "git:",
|
|
|
- "gopher:",
|
|
|
- "irc:",
|
|
|
- "irc6:",
|
|
|
- "ircs:",
|
|
|
- "itms-apps:",
|
|
|
- "itms:",
|
|
|
- "magnet:",
|
|
|
- "mailto:",
|
|
|
- "news:",
|
|
|
- "nntp:",
|
|
|
- "rtmp:",
|
|
|
- "sftp:",
|
|
|
- "sip:",
|
|
|
- "sips:",
|
|
|
- "shortcuts:",
|
|
|
- "skype:",
|
|
|
- "spotify:",
|
|
|
- "ssh:",
|
|
|
- "steam:",
|
|
|
- "svn:",
|
|
|
- "svn+ssh:",
|
|
|
- "tel:",
|
|
|
- "webcal:",
|
|
|
- "xmpp:",
|
|
|
+ "apt",
|
|
|
+ "bitcoin",
|
|
|
+ "callto",
|
|
|
+ "dav",
|
|
|
+ "davs",
|
|
|
+ "ed2k",
|
|
|
+ "facetime",
|
|
|
+ "feed",
|
|
|
+ "ftp",
|
|
|
+ "geo",
|
|
|
+ "git",
|
|
|
+ "gopher",
|
|
|
+ "irc",
|
|
|
+ "irc6",
|
|
|
+ "ircs",
|
|
|
+ "itms-apps",
|
|
|
+ "itms",
|
|
|
+ "magnet",
|
|
|
+ "mailto",
|
|
|
+ "news",
|
|
|
+ "nntp",
|
|
|
+ "rtmp",
|
|
|
+ "sftp",
|
|
|
+ "sip",
|
|
|
+ "sips",
|
|
|
+ "shortcuts",
|
|
|
+ "skype",
|
|
|
+ "spotify",
|
|
|
+ "ssh",
|
|
|
+ "steam",
|
|
|
+ "svn",
|
|
|
+ "svn+ssh",
|
|
|
+ "tel",
|
|
|
+ "webcal",
|
|
|
+ "xmpp",
|
|
|
|
|
|
// iOS Apps
|
|
|
- "opener:", // https://www.opener.link
|
|
|
- "hack:", // https://apps.apple.com/it/app/hack-for-hacker-news-reader/id1464477788?l=en-GB
|
|
|
+ "opener", // https://www.opener.link
|
|
|
+ "hack", // https://apps.apple.com/it/app/hack-for-hacker-news-reader/id1464477788?l=en-GB
|
|
|
}
|
|
|
|
|
|
// HasValidURIScheme reports whether the URL begins with an allowed scheme.
|
|
|
+// The scheme comparison is case-insensitive per RFC 3986 §3.1.
|
|
|
func HasValidURIScheme(absoluteURL string) bool {
|
|
|
- for _, scheme := range validURISchemes {
|
|
|
- if strings.HasPrefix(absoluteURL, scheme) {
|
|
|
+ scheme, _, ok := strings.Cut(absoluteURL, ":")
|
|
|
+ if !ok || scheme == "" {
|
|
|
+ return false
|
|
|
+ }
|
|
|
+ for _, validScheme := range validURISchemes {
|
|
|
+ if strings.EqualFold(scheme, validScheme) {
|
|
|
return true
|
|
|
}
|
|
|
}
|