URL parser: Difference between revisions

m
→‎{{header|Wren}}: Changed to Wren S/H
m (→‎{{header|Wren}}: Changed to Wren S/H)
 
(47 intermediate revisions by 26 users not shown)
Line 57:
:* &nbsp; <nowiki> urn:oasis:names:specification:docbook:dtd:xml:4.1.2 </nowiki>
<br><br>
 
=={{header|Ada}}==
{{libheader|AWS}}
<syntaxhighlight lang="ada">with Ada.Text_IO;
 
with AWS.URL;
with AWS.Parameters;
with AWS.Containers.Tables;
 
procedure URL_Parser is
 
procedure Parse (URL : in String) is
 
use AWS.URL, Ada.Text_IO;
use AWS.Containers.Tables;
 
procedure Put_Cond (Item : in String;
Value : in String;
When_Not : in String := "") is
begin
if Value /= When_Not then
Put (" "); Put (Item); Put_Line (Value);
end if;
end Put_Cond;
 
Obj : Object;
List : Table_Type;
begin
Put_Line ("Parsing " & URL);
 
Obj := Parse (URL);
List := Table_Type (AWS.Parameters.List'(AWS.URL.Parameters (Obj)));
 
Put_Cond ("Scheme: ", Protocol_Name (Obj));
Put_Cond ("Domain: ", Host (Obj));
Put_Cond ("Port: ", Port (Obj), When_Not => "0");
Put_Cond ("Path: ", Path (Obj));
Put_Cond ("File: ", File (Obj));
Put_Cond ("Query: ", Query (Obj));
Put_Cond ("Fragment: ", Fragment (Obj));
Put_Cond ("User: ", User (Obj));
Put_Cond ("Password: ", Password (Obj));
 
if List.Count /= 0 then
Put_Line (" Parameters:");
end if;
for Index in 1 .. List.Count loop
Put (" "); Put (Get_Name (List, N => Index));
Put (" "); Put ("'" & Get_Value (List, N => Index) & "'");
New_Line;
end loop;
New_Line;
end Parse;
 
begin
Parse ("foo://example.com:8042/over/there?name=ferret#nose");
Parse ("urn:example:animal:ferret:nose");
Parse ("jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true");
Parse ("ftp://ftp.is.co.za/rfc/rfc1808.txt");
Parse ("http://www.ietf.org/rfc/rfc2396.txt#header1");
Parse ("ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two");
Parse ("mailto:John.Doe@example.com");
Parse ("news:comp.infosystems.www.servers.unix");
Parse ("tel:+1-816-555-1212");
Parse ("telnet://192.0.2.16:80/");
Parse ("urn:oasis:names:specification:docbook:dtd:xml:4.1.2");
Parse ("ssh://alice@example.com");
Parse ("https://bob:pass@example.com/place");
Parse ("http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64");
end URL_Parser;</syntaxhighlight>
{{out}}
<pre>
Parsing foo://example.com:8042/over/there?name=ferret#nose
Scheme: foo
Domain: example.com
Port: 8042
Path: /over/
File: there
Query: name=ferret
Fragment: #nose
Parameters:
name 'ferret'
 
Parsing urn:example:animal:ferret:nose
Scheme: urn
File: example:animal:ferret:nose
 
Parsing jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
Scheme: jdbc
Path: mysql://test_user:ouupppssss@localhost:3306/
File: sakila
Query: profileSQL=true
Parameters:
profileSQL 'true'
 
Parsing ftp://ftp.is.co.za/rfc/rfc1808.txt
Scheme: ftp
Domain: ftp.is.co.za
Port: 21
Path: /rfc/
File: rfc1808.txt
 
Parsing http://www.ietf.org/rfc/rfc2396.txt#header1
Scheme: http
Domain: www.ietf.org
Port: 80
Path: /rfc/
File: rfc2396.txt
Fragment: #header1
 
Parsing ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
Scheme: ldap
Domain: 2001:db8::7
Path: /
File: c=GB
Query: objectClass=one&objectClass=two
Parameters:
objectClass 'one'
objectClass 'two'
 
Parsing mailto:John.Doe@example.com
Scheme: mailto
File: John.Doe@example.com
 
Parsing news:comp.infosystems.www.servers.unix
Scheme: news
File: comp.infosystems.www.servers.unix
 
Parsing tel:+1-816-555-1212
Scheme: tel
File: 1-816-555-1212
 
Parsing telnet://192.0.2.16:80/
Scheme: telnet
Domain: 192.0.2.16
Port: 80
Path: /
 
Parsing urn:oasis:names:specification:docbook:dtd:xml:4.1.2
Scheme: urn
File: oasis:names:specification:docbook:dtd:xml:4.1.2
 
Parsing ssh://alice@example.com
Scheme: ssh
Domain: alice@example.com
Path: /
 
Parsing https://bob:pass@example.com/place
Scheme: https
Domain: example.com
Port: 443
Path: /
File: place
User: bob
Password: pass
 
Parsing http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
Scheme: http
Domain: example.com
Port: 80
Path: /
Query: a=1&b=2%202&c=3&c=4&d=encoded
Parameters:
a '1'
b '2 2'
c '3'
c '4'
d 'encoded'
 
</pre>
 
=={{header|ALGOL 68}}==
Line 62 ⟶ 232:
Uses the URI parser here: [[URL_parser/URI_parser_ALGOL68]].
 
<langsyntaxhighlight lang="algol68">PR read "uriParser.a68" PR
 
PROC test uri parser = ( STRING uri )VOID:
Line 99 ⟶ 269:
; test uri parser( "https://bob:pass@example.com/place" )
; test uri parser( "http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64" )
END</langsyntaxhighlight>
{{out}}
<pre>
Line 176 ⟶ 346:
 
</pre>
 
=={{header|AppleScript}}==
 
Thanks to AppleScript's ability to interface with some of macOS's ObjectiveC API, the various components can simply be read off from an ''NSURLComponents'' object set from the URL text.
 
<syntaxhighlight lang="applescript">use AppleScript version "2.4" -- OS X 10.10 (Yosemite) or later
use framework "Foundation"
 
on parseURLString(URLString)
set output to {URLString}
set indent to tab & "• "
set componentsObject to current application's class "NSURLComponents"'s componentsWithString:(URLString)
repeat with thisKey in {"scheme", "user", "password", "host", "port", "path", "query", "fragment"}
set thisValue to (componentsObject's valueForKey:(thisKey))
if (thisValue is not missing value) then set end of output to indent & thisKey & (" = " & thisValue)
end repeat
return join(output, linefeed)
end parseURLString
 
on join(listOfText, delimiter)
set astid to AppleScript's text item delimiters
set AppleScript's text item delimiters to delimiter
set output to listOfText as text
set AppleScript's text item delimiters to astid
return output
end join
 
-- Test code:
local output, URLString
set output to {}
repeat with URLString in {"foo://example.com:8042/over/there?name=ferret#nose", ¬
"urn:example:animal:ferret:nose", ¬
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true", ¬
"ftp://ftp.is.co.za/rfc/rfc1808.txt", ¬
"http://www.ietf.org/rfc/rfc2396.txt#header1", ¬
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two", ¬
"mailto:John.Doe@example.com", ¬
"news:comp.infosystems.www.servers.unix", ¬
"tel:+1-816-555-1212", ¬
"telnet://192.0.2.16:80/", ¬
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2", ¬
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"}
set end of output to parseURLString(URLString's contents)
end repeat
 
return join(output, linefeed & linefeed)</syntaxhighlight>
 
{{output}}
<syntaxhighlight lang="applescript">"foo://example.com:8042/over/there?name=ferret#nose
• scheme = foo
• host = example.com
• port = 8042
• path = /over/there
• query = name=ferret
• fragment = nose
 
urn:example:animal:ferret:nose
• scheme = urn
• path = example:animal:ferret:nose
 
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
• scheme = jdbc
• path = mysql://test_user:ouupppssss@localhost:3306/sakila
• query = profileSQL=true
 
ftp://ftp.is.co.za/rfc/rfc1808.txt
• scheme = ftp
• host = ftp.is.co.za
• path = /rfc/rfc1808.txt
 
http://www.ietf.org/rfc/rfc2396.txt#header1
• scheme = http
• host = www.ietf.org
• path = /rfc/rfc2396.txt
• fragment = header1
 
ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
• scheme = ldap
• host = [2001:db8::7]
• path = /c=GB
• query = objectClass=one&objectClass=two
 
mailto:John.Doe@example.com
• scheme = mailto
• path = John.Doe@example.com
 
news:comp.infosystems.www.servers.unix
• scheme = news
• path = comp.infosystems.www.servers.unix
 
tel:+1-816-555-1212
• scheme = tel
• path = +1-816-555-1212
 
telnet://192.0.2.16:80/
• scheme = telnet
• host = 192.0.2.16
• port = 80
• path = /
 
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
• scheme = urn
• path = oasis:names:specification:docbook:dtd:xml:4.1.2
 
http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
• scheme = http
• host = example.com
• path = /
• query = a=1&b=2+2&c=3&c=4&d=encoded"</syntaxhighlight>
 
=={{header|C sharp|C#}}==
 
<langsyntaxhighlight lang="csharp">using System;
 
namespace RosettaUrlParse
Line 213 ⟶ 493:
}
}
</syntaxhighlight>
</lang>
 
=={{header|Crystal}}==
 
This example demonstrates use of the Crystal standard library's <code>URI</code> class.
 
<syntaxhighlight lang="crystal">require "uri"
 
examples = ["foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
"https://bob:password@[::1]/place?a=1&b=2%202"]
 
examples.each do |example|
puts "Parsing \"#{example}\":"
url = URI.parse example
{% for name in ["scheme", "host", "hostname", "port", "path", "userinfo",
"user", "password", "fragment", "query"] %}
unless url.{{name.id}}.nil?
puts " {{name.id}}: \"#{url.{{name.id}}}\""
end
{% end %}
unless url.query_params.empty?
puts " query_params:"
url.query_params.each do |k, v|
puts " #{k}: \"#{v}\""
end
end
puts
end</syntaxhighlight>
 
{{out}}
<pre>Parsing "foo://example.com:8042/over/there?name=ferret#nose":
scheme: "foo"
host: "example.com"
hostname: "example.com"
port: "8042"
path: "/over/there"
fragment: "nose"
query: "name=ferret"
query_params:
name: "ferret"
 
Parsing "urn:example:animal:ferret:nose":
scheme: "urn"
path: "example:animal:ferret:nose"
 
Parsing "jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true":
scheme: "jdbc"
path: "mysql://test_user:ouupppssss@localhost:3306/sakila"
query: "profileSQL=true"
query_params:
profileSQL: "true"
 
Parsing "ftp://ftp.is.co.za/rfc/rfc1808.txt":
scheme: "ftp"
host: "ftp.is.co.za"
hostname: "ftp.is.co.za"
path: "/rfc/rfc1808.txt"
 
Parsing "http://www.ietf.org/rfc/rfc2396.txt#header1":
scheme: "http"
host: "www.ietf.org"
hostname: "www.ietf.org"
path: "/rfc/rfc2396.txt"
fragment: "header1"
 
Parsing "ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two":
scheme: "ldap"
host: "[2001:db8::7]"
hostname: "2001:db8::7"
path: "/c=GB"
query: "objectClass=one&objectClass=two"
query_params:
objectClass: "one"
objectClass: "two"
 
Parsing "mailto:John.Doe@example.com":
scheme: "mailto"
path: "John.Doe@example.com"
 
Parsing "news:comp.infosystems.www.servers.unix":
scheme: "news"
path: "comp.infosystems.www.servers.unix"
 
Parsing "tel:+1-816-555-1212":
scheme: "tel"
path: "+1-816-555-1212"
 
Parsing "telnet://192.0.2.16:80/":
scheme: "telnet"
host: "192.0.2.16"
hostname: "192.0.2.16"
port: "80"
path: "/"
 
Parsing "urn:oasis:names:specification:docbook:dtd:xml:4.1.2":
scheme: "urn"
path: "oasis:names:specification:docbook:dtd:xml:4.1.2"
 
Parsing "https://bob:password@[::1]/place?a=1&b=2%202":
scheme: "https"
host: "[::1]"
hostname: "::1"
path: "/place"
userinfo: "bob:password"
user: "bob"
password: "password"
query: "a=1&b=2%202"
query_params:
a: "1"
b: "2 2"</pre>
 
=={{header|Elixir}}==
<langsyntaxhighlight lang="elixir">test_cases = [
"foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
Line 236 ⟶ 635:
IO.puts "\n#{str}"
IO.inspect URI.parse(str)
end)</langsyntaxhighlight>
 
{{out}}
Line 314 ⟶ 713:
<li>The System.URI class does some "Scheme-Based Normalization" (c/f rfc3986 section 6.2.3), i. e. it knows about certain
defaults for some schemes. With the test data this shows with the port numbers for http, ftp, ldap, mailto.</li></ul>
<langsyntaxhighlight lang="fsharp">open System
open System.Text.RegularExpressions
 
Line 343 ⟶ 742:
writeline " query:" (if u.Query.Length > 0 then u.Query.Substring(1) else "")
writeline " fragment:" (if u.Fragment.Length > 0 then u.Fragment.Substring(1) else "")
)</langsyntaxhighlight>
{{out}}
<pre style="height:3cm">
Line 409 ⟶ 808:
This uses Go's standard [https://golang.org/pkg/net/url/ <tt>net/url</tt>] package.
The [https://golang.org/src/net/url/url.go source code] for this package (excluding tests) is in a single file of ~720 lines.
<langsyntaxhighlight lang="go">package main
 
import (
Line 483 ⟶ 882:
fmt.Println(" Fragment:", u.Fragment)
}
}</langsyntaxhighlight>
{{out}}
<pre>
Line 553 ⟶ 952:
Key: "c" Values: ["3" "4"]
Key: "d" Values: ["encoded"]
</pre>
 
=={{header|Groovy}}==
{{Trans|Java}}
 
Test:
<syntaxhighlight lang="groovy">import java.net.URI
 
[
"foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2"
].each { String url ->
 
// magic happens here
URI u = url.toURI()
 
// Results displayed here
println """
|Parsing $url
| scheme = ${u.scheme}
| domain = ${u.host}
| port = ${(u.port + 1) ? u.port : 'default' }
| path = ${u.path ?: u.schemeSpecificPart}
| query = ${u.query}
| fragment = ${u.fragment}""".stripMargin()
}</syntaxhighlight>
 
Output:
<pre style="height:30ex;overflow:scroll;">
Parsing foo://example.com:8042/over/there?name=ferret#nose
scheme = foo
domain = example.com
port = 8042
path = /over/there
query = name=ferret
fragment = nose
 
Parsing urn:example:animal:ferret:nose
scheme = urn
domain = null
port = default
path = example:animal:ferret:nose
query = null
fragment = null
 
Parsing jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme = jdbc
domain = null
port = default
path = mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
query = null
fragment = null
 
Parsing ftp://ftp.is.co.za/rfc/rfc1808.txt
scheme = ftp
domain = ftp.is.co.za
port = default
path = /rfc/rfc1808.txt
query = null
fragment = null
 
Parsing http://www.ietf.org/rfc/rfc2396.txt#header1
scheme = http
domain = www.ietf.org
port = default
path = /rfc/rfc2396.txt
query = null
fragment = header1
 
Parsing ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
scheme = ldap
domain = [2001:db8::7]
port = default
path = /c=GB
query = objectClass=one&objectClass=two
fragment = null
 
Parsing mailto:John.Doe@example.com
scheme = mailto
domain = null
port = default
path = John.Doe@example.com
query = null
fragment = null
 
Parsing news:comp.infosystems.www.servers.unix
scheme = news
domain = null
port = default
path = comp.infosystems.www.servers.unix
query = null
fragment = null
 
Parsing tel:+1-816-555-1212
scheme = tel
domain = null
port = default
path = +1-816-555-1212
query = null
fragment = null
 
Parsing telnet://192.0.2.16:80/
scheme = telnet
domain = 192.0.2.16
port = 80
path = /
query = null
fragment = null
 
Parsing urn:oasis:names:specification:docbook:dtd:xml:4.1.2
scheme = urn
domain = null
port = default
path = oasis:names:specification:docbook:dtd:xml:4.1.2
query = null
fragment = null</pre>
 
=={{header|Haskell}}==
 
Example uses [https://hackage.haskell.org/package/network-uri <tt>network-uri</tt>] package:
 
<syntaxhighlight lang="haskell">module Main (main) where
 
import Data.Foldable (for_)
import Network.URI
( URI
, URIAuth
, parseURI
, uriAuthority
, uriFragment
, uriPath
, uriPort
, uriQuery
, uriRegName
, uriScheme
, uriUserInfo
)
 
uriStrings :: [String]
uriStrings =
[ "https://bob:pass@example.com/place"
, "foo://example.com:8042/over/there?name=ferret#nose"
, "urn:example:animal:ferret:nose"
, "jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true"
, "ftp://ftp.is.co.za/rfc/rfc1808.txt"
, "http://www.ietf.org/rfc/rfc2396.txt#header1"
, "ldap://[2001:db8::7]/c=GB?objectClass?one"
, "mailto:John.Doe@example.com"
, "news:comp.infosystems.www.servers.unix"
, "tel:+1-816-555-1212"
, "telnet://192.0.2.16:80/"
, "urn:oasis:names:specification:docbook:dtd:xml:4.1.2"
]
 
trimmedUriScheme :: URI -> String
trimmedUriScheme = init . uriScheme
 
trimmedUriUserInfo :: URIAuth -> Maybe String
trimmedUriUserInfo uriAuth =
case uriUserInfo uriAuth of
[] -> Nothing
userInfo -> if last userInfo == '@' then Just (init userInfo) else Nothing
 
trimmedUriPath :: URI -> String
trimmedUriPath uri = case uriPath uri of '/' : t -> t; p -> p
 
trimmedUriQuery :: URI -> Maybe String
trimmedUriQuery uri = case uriQuery uri of '?' : t -> Just t; _ -> Nothing
 
trimmedUriFragment :: URI -> Maybe String
trimmedUriFragment uri = case uriFragment uri of '#' : t -> Just t; _ -> Nothing
 
main :: IO ()
main = do
for_ uriStrings $ \uriString -> do
case parseURI uriString of
Nothing -> putStrLn $ "Could not parse" ++ uriString
Just uri -> do
putStrLn uriString
putStrLn $ " scheme = " ++ trimmedUriScheme uri
case uriAuthority uri of
Nothing -> return ()
Just uriAuth -> do
case trimmedUriUserInfo uriAuth of
Nothing -> return ()
Just userInfo -> putStrLn $ " user-info = " ++ userInfo
putStrLn $ " domain = " ++ uriRegName uriAuth
putStrLn $ " port = " ++ uriPort uriAuth
putStrLn $ " path = " ++ trimmedUriPath uri
case trimmedUriQuery uri of
Nothing -> return ()
Just query -> putStrLn $ " query = " ++ query
case trimmedUriFragment uri of
Nothing -> return ()
Just fragment -> putStrLn $ " fragment = " ++ fragment
putStrLn ""</syntaxhighlight>
{{out}}
<pre>
https://bob:pass@example.com/place
scheme = https
user-info = bob:pass
domain = example.com
port =
path = place
 
foo://example.com:8042/over/there?name=ferret#nose
scheme = foo
domain = example.com
port = :8042
path = over/there
query = name=ferret
fragment = nose
 
urn:example:animal:ferret:nose
scheme = urn
path = example:animal:ferret:nose
 
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme = jdbc
path = mysql://test_user:ouupppssss@localhost:3306/sakila
query = profileSQL=true
 
ftp://ftp.is.co.za/rfc/rfc1808.txt
scheme = ftp
domain = ftp.is.co.za
port =
path = rfc/rfc1808.txt
 
http://www.ietf.org/rfc/rfc2396.txt#header1
scheme = http
domain = www.ietf.org
port =
path = rfc/rfc2396.txt
fragment = header1
 
ldap://[2001:db8::7]/c=GB?objectClass?one
scheme = ldap
domain = [2001:db8::7]
port =
path = c=GB
query = objectClass?one
 
mailto:John.Doe@example.com
scheme = mailto
path = John.Doe@example.com
 
news:comp.infosystems.www.servers.unix
scheme = news
path = comp.infosystems.www.servers.unix
 
tel:+1-816-555-1212
scheme = tel
path = +1-816-555-1212
 
telnet://192.0.2.16:80/
scheme = telnet
domain = 192.0.2.16
port = :80
path =
 
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
scheme = urn
path = oasis:names:specification:docbook:dtd:xml:4.1.2
</pre>
 
Line 563 ⟶ 1,234:
Implementation:
 
<langsyntaxhighlight Jlang="j">split=:1 :0
({. ; ] }.~ 1+[)~ i.&m
)
Line 609 ⟶ 1,280:
export=. ;:'scheme user creds host port path query fragment'
(#~ 0<#@>@{:"1) (,. do each) export
)</langsyntaxhighlight>
 
Task examples:
 
<langsyntaxhighlight lang="j"> taskparts 'foo://example.com:8042/over/there?name=ferret#nose'
┌────────┬─────────────┐
│scheme │foo │
Line 708 ⟶ 1,379:
├──────┼───────────────────────────────────────────────┤
│path │oasis:names:specification:docbook:dtd:xml:4.1.2│
└──────┴───────────────────────────────────────────────┘</langsyntaxhighlight>
 
Note that the <code>path</code> of the example <code>jdbc</code> uri is itself a uri which may be parsed:
 
<langsyntaxhighlight Jlang="j"> taskparts 'mysql://test_user:ouupppssss@localhost:3306/sakila'
┌──────┬──────────┐
│scheme│mysql │
Line 725 ⟶ 1,396:
├──────┼──────────┤
│path │/sakila │
└──────┴──────────┘</langsyntaxhighlight>
 
Also, examples borrowed from the <code>go</code> implementation:
 
<langsyntaxhighlight Jlang="j"> taskparts 'ssh://alice@example.com'
┌──────┬───────────┐
│scheme│ssh │
Line 760 ⟶ 1,431:
│ ││a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64││
│ │└─────────────────────────────────────────┘│
└──────┴───────────────────────────────────────────┘</langsyntaxhighlight>
 
Note that escape decoding is left to the consumer (as well as decoding things like '+' as a replacement for the space character and determining the absolute significance of relative paths and the details of ip address parsing and so on...). This seems like a good match to the hierarchical nature of uri parsing. See [[URL_decoding#J|URL decoding]] for an implementation of escape decoding.
Line 767 ⟶ 1,438:
 
Note that w3c recommends a handling for query strings which differs from that of RFC-3986. For example, the use of <code>;</code> as replacement for the <code>&</code> delimiter, or the use of the query element name as the query element value when the <code>=</code> delimiter is omitted from the name/value pair. We do not implement that here, as it's not a part of this task. But that sort of implementation could be achieved by replacing the definition of <code>queryparts</code>. And, of course, other treatments of query strings are also possible, should that become necessary...
 
=={{header|Java}}==
Java offers the ''URI'' class which will parse a URL. URNs are not supported.
<syntaxhighlight lang="java">
URI uri;
try {
uri = new URI("foo://example.com:8042/over/there?name=ferret#nose");
} catch (URISyntaxException exception) {
/* invalid URI */
}
</syntaxhighlight>
You would then use any of the accompanying class methods to retrieve the value you're looking for.<br />
For example, to get the scheme value, you would use the following.
<syntaxhighlight lang="java">
uri.getScheme()
</syntaxhighlight>
It successfully parsed a majority of the test URLs.
<pre>
foo://example.com:8042/over/there?name=ferret#nose
scheme: foo
userinfo:
host: example.com
port: 8042
authority: example.com:8042
path: /over/there
query: name=ferret
fragment: nose
</pre>
To parse the 'jdbc:' URL you'll need to remove the prefix.
<pre>
mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme: mysql
userinfo: test_user:ouupppssss
host: localhost
port: 3306
authority: test_user:ouupppssss@localhost:3306
path: /sakila
query: profileSQL=true
fragment:
</pre>
The others work as expected, except for 'mailto', 'news', and 'tel'.<br />
Although, these are not too complicated to parse. For 'mailto', I used a class with two records.<br />
RFC 6068 defines a 'mailto' scheme. https://datatracker.ietf.org/doc/html/rfc6068.
<syntaxhighlight lang="java">
import java.net.URLDecoder;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.List;
 
public class MailTo {
private final To to;
private List<Field> fields;
 
public MailTo(String string) {
if (string == null)
throw new NullPointerException();
if (string.isBlank() || !string.toLowerCase().startsWith("mailto:"))
throw new IllegalArgumentException("Requires 'mailto' scheme");
string = string.substring(string.indexOf(':') + 1);
/* we can use the 'URLDecoder' class to decode any entities */
string = URLDecoder.decode(string, StandardCharsets.UTF_8);
/* the address and fields are separated by a '?' */
int indexOf = string.indexOf('?');
String[] address;
if (indexOf == -1)
address = string.split("@");
else {
address = string.substring(0, indexOf).split("@");
string = string.substring(indexOf + 1);
/* each field is separated by a '&' */
String[] fields = string.split("&");
String[] field;
this.fields = new ArrayList<>(fields.length);
for (String value : fields) {
field = value.split("=");
this.fields.add(new Field(field[0], field[1]));
}
}
to = new To(address[0], address[1]);
}
 
record To(String user, String host) { }
record Field(String name, String value) { }
}
</syntaxhighlight>
I ran a majority of the examples from RFC 6068 and got the expected results
<pre>
mailto:infobot@example.com?subject=current-issue
user infobot
host example.com
name subject
value current-issue
 
mailto:list@example.org?In-Reply-To=%3C3469A91.D10AF4C@example.com%3E
user list
host example.org
name In-Reply-To
value <3469A91.D10AF4C@example.com>
</pre>
Both 'tel' and 'news' are similar, and actually simpler.<br />
RFC 3966 outlines the 'tel' syntaxs. https://datatracker.ietf.org/doc/html/rfc3966.<br />
And RFC 5538 outlines the 'news' syntax. https://www.rfc-editor.org/rfc/rfc5538.html.
 
=={{header|JavaScript}}==
Line 774 ⟶ 1,547:
Here is an example, tested against the JavaScript engines of current versions of Chrome and Safari, of taking this 'Gordian knot' approach to the task:
 
<langsyntaxhighlight JavaScriptlang="javascript">(function (lstURL) {
 
var e = document.createElement('a'),
Line 819 ⟶ 1,592:
"https://bob:pass@example.com/place",
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"
]);</langsyntaxhighlight>
 
Results of applying this approach in the JavaScript of Safari 8
<syntaxhighlight lang="json">[
<lang JSON>[
{
"hash": "#nose",
Line 963 ⟶ 1,736:
"search": "?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"
}
]</langsyntaxhighlight>
 
=={{header|jq}}==
{{works with|jq}}
'''Works with gojq, the Go implementation of jq.'''
 
Since jq does not provide a URL parser, and since the RFC 3986
specification is in fact quite complex, this entry will for the most
part focus on the task of parsing a correctly formed URL into
the five main components specified in Appendix B of the RFC:
 
# scheme
# authority
# path
# query
# fragment
 
However, since the Rosetta Code task description above evinces particular interest in
"authority" segments of the form:
 
* [username:password@]domain[:port]
 
this entry will adopt a hierarchical approach to parsing so that the
full URL parser defined here will when possible also break down the "authority"
segment into the four components `username`, `password`, `domain` and `port`.
 
One advantage of this hierarchical approach is that it facilitates
further refinements and extensions, including error-handling
in the event of invalid components.
 
Note that the regular expression used to define the jq filter `URL` here is
equivalent to the one specified in Appendix B of the RFC and can
therefore be taken as authoritative.
 
Note also that the following does not tackle the task of decoding special characters (e.g. "+" in the query string).
 
<syntaxhighlight lang=jq>
# See Appendix B of RFC 3986
def URL:
capture("^((?<scheme>[^:/?#]+):)?(//(?<authority>[^/?#]*))?(?<path>[^?#]*)(\\?(?<query>[^#]*))?(#(?<fragment>.*))?");
 
# The authority could be of the form: [username:password@]domain[:port]
def authority:
capture( "^((?<username>[^:@/]*):(?<password>[^@]*)@)?(?<domain>[^:?]*)(:(?<port>[0-9]*))?$" );
 
# The following filter first parses a valid URL into the five basic
# components, producing a JSON object with five keys; if the "authority"
# field can be futher parsed by `authority`, it is replaced by the
# corresponding JSON object.
def uri:
URL
| if .authority
then (.authority|authority) as $authority
| if $authority then .authority |= $authority
else .
end
else .
end;
</syntaxhighlight>
 
'''Examples'''
<syntaxhighlight lang=jq>
def tests:
"foo://example.com:8042/over/there?name=ferret&color=grey#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2"
;
 
# For brevity, drop the `null`s:
tests
| [., (uri | (.. | select(.==null)) |= empty) ]
</syntaxhighlight>
{{output}}
<pre>
[
"foo://example.com:8042/over/there?name=ferret&color=grey#nose",
{
"scheme": "foo",
"authority": {
"domain": "example.com",
"port": "8042"
},
"path": "/over/there",
"query": "name=ferret&color=grey",
"fragment": "nose"
}
]
[
"urn:example:animal:ferret:nose",
{
"scheme": "urn",
"path": "example:animal:ferret:nose"
}
]
[
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
{
"scheme": "jdbc",
"path": "mysql://test_user:ouupppssss@localhost:3306/sakila",
"query": "profileSQL=true"
}
]
[
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
{
"scheme": "ftp",
"authority": {
"domain": "ftp.is.co.za"
},
"path": "/rfc/rfc1808.txt"
}
]
[
"http://www.ietf.org/rfc/rfc2396.txt#header1",
{
"scheme": "http",
"authority": {
"domain": "www.ietf.org"
},
"path": "/rfc/rfc2396.txt",
"fragment": "header1"
}
]
[
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two"
]
[
"mailto:John.Doe@example.com",
{
"scheme": "mailto",
"path": "John.Doe@example.com"
}
]
[
"news:comp.infosystems.www.servers.unix",
{
"scheme": "news",
"path": "comp.infosystems.www.servers.unix"
}
]
[
"tel:+1-816-555-1212",
{
"scheme": "tel",
"path": "+1-816-555-1212"
}
]
[
"telnet://192.0.2.16:80/",
{
"scheme": "telnet",
"authority": {
"domain": "192.0.2.16",
"port": "80"
},
"path": "/"
}
]
[
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
{
"scheme": "urn",
"path": "oasis:names:specification:docbook:dtd:xml:4.1.2"
}
]
</pre>
 
=={{header|Julia}}==
This solution uses Julia's [https://github.com/JuliaWeb/URIParser.jl URIParser] package. The <code>detailview</code> function shows all of the non-empty components of the <code>URI</code> object created by this parser. No attempt is made to further parse more complex components, e.g. query or userinfo. Error detection is limited to indicating whether a string is parsable as a URI and providing a hint as to whether the <code>URI</code> is valid (according to this package's <code>isvalid</code> function).
<syntaxhighlight lang="julia">using Printf, URIParser
<lang Julia>
 
using URIParser
const FIELDS = names(URI)
 
Line 1,021 ⟶ 1,967:
println(detailview(uri))
end
</syntaxhighlight>
</lang>
 
{{out}}
Line 1,145 ⟶ 2,091:
</pre>
 
=={{header|MathematicaKotlin}}==
Although the java.net.URL class can parse urls just fine, unfortunately (as far as this task is concerned) the constructor throws an exception if it does not recognize the scheme (or 'protocol' as it calls it). To deal with unrecognized protocols such as 'foo', we therefore need to replace them with a valid protocol such as 'http' to trick the URL class into parsing them properly:
<lang Mathematica>URLParse["foo://example.com:8042/over/there?name=ferret#nose"]</lang>
<syntaxhighlight lang="scala">// version 1.1.2
 
import java.net.URL
import java.net.MalformedURLException
 
fun parseUrl(url: String) {
var u: URL
var scheme: String
try {
u = URL(url)
scheme = u.protocol
}
catch (ex: MalformedURLException) {
val index = url.indexOf(':')
scheme = url.take(index)
u = URL("http" + url.drop(index))
}
println("Parsing $url")
println(" scheme = $scheme")
with(u) {
if (userInfo != null) println(" userinfo = $userInfo")
if (!host.isEmpty()) println(" domain = $host")
if (port != -1) println(" port = $port")
if (!path.isEmpty()) println(" path = $path")
if (query != null) println(" query = $query")
if (ref != null) println(" fragment = $ref")
}
println()
}
 
fun main(args: Array<String>){
val urls = arrayOf(
"foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
"ssh://alice@example.com",
"https://bob:pass@example.com/place",
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"
)
for (url in urls) parseUrl(url)
}</syntaxhighlight>
 
{{out}}
<pre>
Parsing foo://example.com:8042/over/there?name=ferret#nose
scheme = foo
domain = example.com
port = 8042
path = /over/there
query = name=ferret
fragment = nose
 
Parsing urn:example:animal:ferret:nose
scheme = urn
path = example:animal:ferret:nose
 
Parsing jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme = jdbc
path = mysql://test_user:ouupppssss@localhost:3306/sakila
query = profileSQL=true
 
Parsing ftp://ftp.is.co.za/rfc/rfc1808.txt
scheme = ftp
domain = ftp.is.co.za
path = /rfc/rfc1808.txt
 
Parsing http://www.ietf.org/rfc/rfc2396.txt#header1
scheme = http
domain = www.ietf.org
path = /rfc/rfc2396.txt
fragment = header1
 
Parsing ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
scheme = ldap
domain = [2001:db8::7]
path = /c=GB
query = objectClass=one&objectClass=two
 
Parsing mailto:John.Doe@example.com
scheme = mailto
path = John.Doe@example.com
 
Parsing news:comp.infosystems.www.servers.unix
scheme = news
path = comp.infosystems.www.servers.unix
 
Parsing tel:+1-816-555-1212
scheme = tel
path = +1-816-555-1212
 
Parsing telnet://192.0.2.16:80/
scheme = telnet
domain = 192.0.2.16
port = 80
path = /
 
Parsing urn:oasis:names:specification:docbook:dtd:xml:4.1.2
scheme = urn
path = oasis:names:specification:docbook:dtd:xml:4.1.2
 
Parsing ssh://alice@example.com
scheme = ssh
userinfo = alice
domain = example.com
 
Parsing https://bob:pass@example.com/place
scheme = https
userinfo = bob:pass
domain = example.com
path = /place
 
Parsing http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
scheme = http
domain = example.com
path = /
query = a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
</pre>
 
=={{header|Lua}}==
{{works with|Lua|5.1 - 5.3}}
{{libheader|LuaSocket}}
 
<syntaxhighlight lang="lua">local url = require('socket.url')
 
local tests = {
'foo://example.com:8042/over/there?name=ferret#nose',
'urn:example:animal:ferret:nose',
'jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true',
'ftp://ftp.is.co.za/rfc/rfc1808.txt',
'http://www.ietf.org/rfc/rfc2396.txt#header1',
'ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two',
'mailto:John.Doe@example.com',
'news:comp.infosystems.www.servers.unix',
'tel:+1-816-555-1212',
'telnet://192.0.2.16:80/',
'urn:oasis:names:specification:docbook:dtd:xml:4.1.2'
}
 
for _, test in ipairs(tests) do
local parsed = url.parse(test)
 
io.write('URI: ' .. test .. '\n')
 
for k, v in pairs(parsed) do
io.write(string.format(' %s: %s\n', k, v))
end
 
io.write('\n')
end
</syntaxhighlight>
{{out}}
<pre>
URI: foo://example.com:8042/over/there?name=ferret#nose
fragment: nose
authority: example.com:8042
host: example.com
query: name=ferret
scheme: foo
path: /over/there
port: 8042
 
URI: urn:example:animal:ferret:nose
scheme: urn
path: example:animal:ferret:nose
 
URI: jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
query: profileSQL=true
scheme: jdbc
path: mysql://test_user:ouupppssss@localhost:3306/sakila
 
URI: ftp://ftp.is.co.za/rfc/rfc1808.txt
host: ftp.is.co.za
path: /rfc/rfc1808.txt
authority: ftp.is.co.za
scheme: ftp
 
URI: http://www.ietf.org/rfc/rfc2396.txt#header1
fragment: header1
authority: www.ietf.org
host: www.ietf.org
path: /rfc/rfc2396.txt
scheme: http
 
URI: ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
scheme: ldap
query: objectClass=one&objectClass=two
host: 2001:db8::7
path: /c=GB
authority: [2001:db8::7]
 
URI: mailto:John.Doe@example.com
scheme: mailto
path: John.Doe@example.com
 
URI: news:comp.infosystems.www.servers.unix
scheme: news
path: comp.infosystems.www.servers.unix
 
URI: tel:+1-816-555-1212
scheme: tel
path: +1-816-555-1212
 
URI: telnet://192.0.2.16:80/
authority: 192.0.2.16:80
host: 192.0.2.16
scheme: telnet
path: /
port: 80
 
URI: urn:oasis:names:specification:docbook:dtd:xml:4.1.2
scheme: urn
path: oasis:names:specification:docbook:dtd:xml:4.1.2
</pre>
 
=={{header|M2000 Interpreter}}==
===Using M2000 script to parse URL===
<syntaxhighlight lang="m2000 interpreter">
Module checkit {
any=lambda (z$)->{=lambda z$ (a$)->instr(z$,a$)>0}
one=lambda (z$)->{=lambda z$ (a$)->z$=a$}
number$="0123456789"
series=Lambda -> {
func=Array([])
=lambda func (&line$, &res$)->{
if line$="" then exit
k=each(func)
def p=0,ok as boolean
while k {
ok=false : p++ : f=array(k)
if not f(mid$(line$,p,1)) then exit
ok=true
}
if ok then res$=left$(line$, p) : line$=mid$(line$, p+1)
=ok
}
}
is_any=lambda series, any (c$) ->series(any(c$))
is_one=lambda series, one (c$) ->series(one(c$))
Is_Alpha=series(lambda (a$)-> a$ ~ "[a-zA-Z]")
Is_digit=series(any(number$))
Is_hex=any(number$+"abcdefABCDEF")
optionals=Lambda -> {
func=Array([])
=lambda func (&line$, &res$)->{
k=each(func)
def ok as boolean
while k {
f=array(k)
if f(&line$,&res$) then ok=true : exit
}
=ok
}
}
repeated=Lambda (func)-> {
=lambda func (&line$, &res$)->{
def ok as boolean, a$
res$=""
do {
sec=len(line$)
if not func(&line$,&a$) then exit
res$+=a$
ok=true
} until line$="" or sec=len(line$)
=ok
}
}
oneAndoptional=lambda (func1, func2) -> {
=lambda func1, func2 (&line$, &res$)->{
def ok as boolean, a$
res$=""
if not func1(&line$,&res$) then exit
if func2(&line$,&a$) then res$+=a$
=True
}
}
many=Lambda -> {
func=Array([])
=lambda func (&line$, &res$)->{
k=each(func)
def p=0,ok as boolean, acc$
oldline$=line$
while k {
ok=false
res$=""
if line$="" then exit
f=array(k)
if not f(&line$,&res$) then exit
acc$+=res$
ok=true
}
if not ok then {line$=oldline$} else res$=acc$
=ok
}
}
is_safe=series(any("$-_@.&"))
Is_extra=series(any("!*'(),"+chr$(34)))
Is_Escape=series(any("%"), is_hex, is_hex)
\\Is_reserved=series(any("=;/#?: "))
is_xalpha=optionals(Is_Alpha, is_digit, is_safe, is_extra, is_escape)
is_xalphas=oneAndoptional(is_xalpha,repeated(is_xalpha))
is_xpalpha=optionals(is_xalpha, is_one("+"))
is_xpalphas=oneAndoptional(is_xpalpha,repeated(is_xpalpha))
Is_ialpha=oneAndoptional(Is_Alpha,repeated(is_xpalphas))
is_fragmentid=lambda is_xalphas (&lines$, &res$) -> {
=is_xalphas(&lines$, &res$)
}
is_search=oneAndoptional(is_xalphas, repeated(many(series(one("+")), is_xalphas)))
is_void=lambda (f)-> {
=lambda f (&oldline$, &res$)-> {
line$=oldline$
if f(&line$, &res$) then {oldline$=line$ } else res$=""
=true
}
}
is_scheme=is_ialpha
is_path=repeated(oneAndoptional(is_void(is_xpalphas), series(one("/"))))
is_uri=oneAndoptional(many(is_scheme, series(one(":")), is_path), many(series(one("?")),is_search))
is_fragmentaddress=oneAndoptional(is_uri, many(series(one("#")),is_fragmentid ))
data "foo://example.com:8042/over/there?name=ferret#nose"
data "urn:example:animal:ferret:nose"
data "jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true "
data "ftp://ftp.is.co.za/rfc/rfc1808.txt"
data "http://www.ietf.org/rfc/rfc2396.txt#header1"
data "ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two"
data "mailto:John.Doe@example.com"
data "tel:+1-816-555-1212"
data "telnet://192.0.2.16:80/"
data "urn:oasis:names:specification:docbook:dtd:xml:4.1.2"
while not empty {
read What$
pen 15 {
Print What$
}
a$=""
If is_scheme(&What$, &a$) Then Print "Scheme=";a$ : What$=mid$(What$,2)
If is_path(&What$, &a$) Then {
count=0
while left$(a$, 1)="/" { a$=mid$(a$,2): count++}
if count>1 then {
domain$=leftpart$(a$+"/", "/")
a$=rightpart$(a$,"/")
if domain$<>"" Then Print "Domain:";Domain$
if a$<>"" Then Print "Path:";a$
} else.if left$(What$,1) =":" then {
Print "path:";a$+What$: What$=""
} Else Print "Data:"; a$
}
if left$(What$,1) =":" then {
is_number=repeated(is_digit)
What$=mid$(What$,2): If is_number(&What$, &a$) Then Print "Port:";a$
if not left$(What$,1)="/" then exit
If is_path(&What$, &a$) Then {
while left$(a$, 1)="/" { a$=mid$(a$,2)}
if a$<>"" Then Print "Path:";a$
}
}
if left$(What$, 1)="?" then {
What$=mid$(What$,2)
If is_search(&What$, &a$) Then {
v$=""
if left$(What$, 1)="=" then {
What$=mid$(What$,2)
If is_search(&What$, &v$) Then Print "Query:";a$;"=";v$
} else Print "Query:";a$
}
}
While left$(What$, 1)="#" {
What$=mid$(What$,2)
if not is_xalphas(&What$, &a$) Then exit
Print "fragment:";a$
}
if What$<>"" Then Print "Data:"; What$
}
}
Checkit
</syntaxhighlight>
{{out}}
<pre style="height:30ex;overflow:scroll">
foo://example.com:8042/over/there?name=ferret#nose
Scheme=foo
Domain:example.com
Port:8042
Path:over/there
Query:name=ferret
fragment:nose
urn:example:animal:ferret:nose
Scheme=urn
path:example:animal:ferret:nose
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
Scheme=jdbc
path:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
ftp://ftp.is.co.za/rfc/rfc1808.txt
Scheme=ftp
Domain:ftp.is.co.za
Path:rfc/rfc1808.txt
http://www.ietf.org/rfc/rfc2396.txt#header1
Scheme=http
Domain:www.ietf.org
Path:rfc/rfc2396.txt
fragment:header1
ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
Scheme=ldap
Data:[2001:db8::7]/c=GB?objectClass=one&objectClass=two
mailto:John.Doe@example.com
Scheme=mailto
Data:John.Doe@example.com
tel:+1-816-555-1212
Scheme=tel
Data:+1-816-555-1212
telnet://192.0.2.16:80/
Scheme=telnet
Domain:192.0.2.16
Port:80
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
Scheme=urn
path:oasis:names:specification:docbook:dtd:xml:4.1.2
</pre >
 
===Using an internal function (variation of String$())===
<syntaxhighlight lang="m2000 interpreter">
module Checkit {
Stack New {
Data "foo://example.com:8042/over/there?name=ferret#nose", "urn:example:animal:ferret:nose"
Data "jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true", "ftp://ftp.is.co.za/rfc/rfc1808.txt"
Data "http://www.ietf.org/rfc/rfc2396.txt#header1", "ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two"
Data "mailto:John.Doe@example.com", "news:comp.infosystems.www.servers.unix", "tel:+1-816-555-1212"
Data "telnet://192.0.2.16:80/", "urn:oasis:names:specification:docbook:dtd:xml:4.1.2", "ssh://alice@example.com"
Data "https://bob:pass@example.com/place", "http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"
a=Array([])
}
function prechar$(a$, b$) {
if a$<>"" then {=quote$(b$+a$)} else ={""}
}
z=each(a)
document s$="["+{
}
While z {
a$=array$(z)
s1$={ "uri": }+quote$(a$)+{,
"authority": }+ quote$(string$(a$ as URLAuthority))+{,
"userInfo": }+ quote$(string$(a$ as URLUserInfo))+{,
"scheme": }+quote$(string$(a$ as URLScheme))+{,
"hostname": }+quote$(string$(a$ as UrlHost))+{,
"Port": }+quote$(string$(a$ as UrlPort))+{,
"pathname": }+quote$(string$(a$ as UrlPath))+{,
"search": }+prechar$(string$(a$ as URLpart 6),"?")+{,
"hash": }+prechar$(string$(a$ as UrlFragment),"#")+{
}
s$=" {"+{
}+s1$+" }"
\\ z^ is the iteraror's counter (z is an iterator of a, a touple - array in M2000)
if z^<len(a)-1 then s$=" ," ' append to document
s$={
}
}
s$="]"
Print "Press any keyboard key or mouse key to continue scrolling"
Report s$
Clipboard s$
}
Checkit
</syntaxhighlight>
{{out}}
<pre style="height:30ex;overflow:scroll">
[
{
"uri": "foo://example.com:8042/over/there?name=ferret#nose",
"authority": "example.com:8042",
"userInfo": "",
"scheme": "foo",
"hostname": "example.com",
"Port": "8042",
"pathname": "/over/there",
"search": "?name=ferret",
"hash": "#nose"
} ,
{
"uri": "urn:example:animal:ferret:nose",
"authority": "",
"userInfo": "",
"scheme": "urn",
"hostname": "",
"Port": "",
"pathname": "example:animal:ferret:nose",
"search": "",
"hash": ""
} ,
{
"uri": "jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"authority": "",
"userInfo": "",
"scheme": "jdbc",
"hostname": "",
"Port": "",
"pathname": "mysql://test_user:ouupppssss@localhost:3306/sakila",
"search": "?profileSQL=true",
"hash": ""
} ,
{
"uri": "ftp://ftp.is.co.za/rfc/rfc1808.txt",
"authority": "ftp.is.co.za",
"userInfo": "",
"scheme": "ftp",
"hostname": "ftp.is.co.za",
"Port": "21",
"pathname": "/rfc/rfc1808.txt",
"search": "",
"hash": ""
} ,
{
"uri": "http://www.ietf.org/rfc/rfc2396.txt#header1",
"authority": "www.ietf.org",
"userInfo": "",
"scheme": "http",
"hostname": "www.ietf.org",
"Port": "80",
"pathname": "/rfc/rfc2396.txt",
"search": "",
"hash": "#header1"
} ,
{
"uri": "ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"authority": "2001:db8::7",
"userInfo": "",
"scheme": "ldap",
"hostname": "2001:db8::7",
"Port": "389",
"pathname": "/c=GB",
"search": "?objectClass=one&objectClass=two",
"hash": ""
} ,
{
"uri": "mailto:John.Doe@example.com",
"authority": "",
"userInfo": "",
"scheme": "mailto",
"hostname": "",
"Port": "",
"pathname": "John.Doe@example.com",
"search": "",
"hash": ""
} ,
{
"uri": "news:comp.infosystems.www.servers.unix",
"authority": "",
"userInfo": "",
"scheme": "news",
"hostname": "",
"Port": "",
"pathname": "comp.infosystems.www.servers.unix",
"search": "",
"hash": ""
} ,
{
"uri": "tel:+1-816-555-1212",
"authority": "",
"userInfo": "",
"scheme": "tel",
"hostname": "",
"Port": "",
"pathname": "+1-816-555-1212",
"search": "",
"hash": ""
} ,
{
"uri": "telnet://192.0.2.16:80/",
"authority": "192.0.2.16:80",
"userInfo": "",
"scheme": "telnet",
"hostname": "192.0.2.16",
"Port": "80",
"pathname": "",
"search": "",
"hash": ""
} ,
{
"uri": "urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
"authority": "",
"userInfo": "",
"scheme": "urn",
"hostname": "",
"Port": "",
"pathname": "oasis:names:specification:docbook:dtd:xml:4.1.2",
"search": "",
"hash": ""
} ,
{
"uri": "ssh://alice@example.com",
"authority": "alice@example.com",
"userInfo": "alice",
"scheme": "ssh",
"hostname": "example.com",
"Port": "",
"pathname": "",
"search": "",
"hash": ""
} ,
{
"uri": "https://bob:pass@example.com/place",
"authority": "bob:pass@example.com",
"userInfo": "bob:pass",
"scheme": "https",
"hostname": "example.com",
"Port": "443",
"pathname": "/place",
"search": "",
"hash": ""
} ,
{
"uri": "http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64",
"authority": "example.com",
"userInfo": "",
"scheme": "http",
"hostname": "example.com",
"Port": "80",
"pathname": "/",
"search": "?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64",
"hash": ""
}
]
</pre >
 
=={{header|Mathematica}}/{{header|Wolfram Language}}==
<syntaxhighlight lang="mathematica">URLParse["foo://example.com:8042/over/there?name=ferret#nose"]</syntaxhighlight>
{{out}}
<pre><|"Scheme" -> "foo", "User" -> None, "Domain" -> "example.com",
"Port" -> 8042, "Path" -> {"", "over", "there"},
"Query" -> {"name" -> "ferret"}, "Fragment" -> "nose"|></pre>
 
=={{header|Nim}}==
The <code>uri</code> module provides a <code>parseUri</code> proc.
 
<syntaxhighlight lang="nim">import uri, strformat
 
proc printUri(url: string) =
echo url
let res = parseUri(url)
if res.scheme != "":
echo &"\t Scheme: {res.scheme}"
if res.hostname != "":
echo &"\tHostname: {res.hostname}"
if res.username != "":
echo &"\tUsername: {res.username}"
if res.password != "":
echo &"\tPassword: {res.password}"
if res.path != "":
echo &"\t Path: {res.path}"
if res.query != "":
echo &"\t Query: {res.query}"
if res.port != "":
echo &"\t Port: {res.port}"
if res.anchor != "":
echo &"\t Anchor: {res.anchor}"
if res.opaque:
echo &"\t Opaque: {res.opaque}"
 
let urls = ["foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
"ssh://alice@example.com",
"https://bob:pass@example.com/place",
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"]
 
for url in urls:
printUri(url)</syntaxhighlight>
{{out}}
<pre>foo://example.com:8042/over/there?name=ferret#nose
Scheme: foo
Hostname: example.com
Path: /over/there
Query: name=ferret
Port: 8042
Anchor: nose
urn:example:animal:ferret:nose
Scheme: urn
Path: example:animal:ferret:nose
Opaque: true
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
Scheme: jdbc
Path: mysql://test_user:ouupppssss@localhost:3306/sakila
Query: profileSQL=true
Opaque: true
ftp://ftp.is.co.za/rfc/rfc1808.txt
Scheme: ftp
Hostname: ftp.is.co.za
Path: /rfc/rfc1808.txt
http://www.ietf.org/rfc/rfc2396.txt#header1
Scheme: http
Hostname: www.ietf.org
Path: /rfc/rfc2396.txt
Anchor: header1
ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
Scheme: ldap
Hostname: 2001:db8::7
Path: /c=GB
Query: objectClass=one&objectClass=two
mailto:John.Doe@example.com
Scheme: mailto
Hostname: example.com
Username: John.Doe
Opaque: true
news:comp.infosystems.www.servers.unix
Scheme: news
Path: comp.infosystems.www.servers.unix
Opaque: true
tel:+1-816-555-1212
Scheme: tel
Path: +1-816-555-1212
Opaque: true
telnet://192.0.2.16:80/
Scheme: telnet
Hostname: 192.0.2.16
Path: /
Port: 80
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
Scheme: urn
Path: oasis:names:specification:docbook:dtd:xml:4.1.2
Opaque: true
ssh://alice@example.com
Scheme: ssh
Hostname: example.com
Username: alice
https://bob:pass@example.com/place
Scheme: https
Hostname: example.com
Username: bob
Password: pass
Path: /place
http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
Scheme: http
Hostname: example.com
Path: /
Query: a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64</pre>
 
=={{header|Objeck}}==
 
<syntaxhighlight lang="objeck">use Web.HTTP;
 
class Test {
function : Main(args : String[]) ~ Nil {
urls := [
"foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64:"];
 
each(i : urls) {
url := Url->New(urls[i]);
if(url->Parsed()) {
url->ToString()->PrintLine();
};
};
}
}</syntaxhighlight>
 
{{out}}
<pre>foo://example.com:8042/over/there?name=ferret#nose
scheme='foo'
host='example.com'
path='/over/there'
port='8042'
query='name=ferret'
fragment='nose'
 
urn:example:animal:ferret:nose
scheme='urn'
path='example:animal:ferret:nose'
 
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme='jdbc'
path='mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true'
 
ftp://ftp.is.co.za/rfc/rfc1808.txt
scheme='ftp'
host='ftp.is.co.za'
path='/rfc/rfc1808.txt'
 
http://www.ietf.org/rfc/rfc2396.txt#header1
scheme='http'
host='www.ietf.org'
path='/rfc/rfc2396.txt'
fragment='header1'
 
ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
scheme='ldap'
host='[2001:db8::7]'
path='/c=GB'
query='objectClass=one&objectClass=two'
 
mailto:John.Doe@example.com
scheme='mailto'
path='John.Doe@example.com'
 
news:comp.infosystems.www.servers.unix
scheme='news'
path='comp.infosystems.www.servers.unix'
 
tel:+1-816-555-1212
scheme='tel'
path='+1-816-555-1212'
 
telnet://192.0.2.16:80/
scheme='telnet'
host='192.0.2.16'
path='/'
port='80'
 
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
scheme='urn'
path='oasis:names:specification:docbook:dtd:xml:4.1.2'
 
http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64:
scheme='http'
host='example.com'
path='/'
query='a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64:'</pre>
 
=={{header|Perl}}==
You can use the URI module from CPAN to parse URIs. Note that the output is a bit different: for example, you don't get the host from the <code>foo://</code> scheme, as host is only valid for schemes that define it.
<langsyntaxhighlight lang="perl">#!/usr/bin/perl
use warnings;
use strict;
Line 1,181 ⟶ 2,972:
}
 
}</langsyntaxhighlight>
{{out}}
<pre>foo://example.com:8042/over/there?name=ferret#nose
Line 1,235 ⟶ 3,026:
scheme urn
path oasis:names:specification:docbook:dtd:xml:4.1.2</pre>
 
=={{header|Perl 6}}==
{{works with|rakudo|2015-11-02}}
Uses the URI library which implements a Perl 6 grammar based on the RFC 3986 BNF grammar.
<lang perl6>use URI;
 
my @test-uris = <
foo://example.com:8042/over/there?name=ferret#nose
urn:example:animal:ferret:nose
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
ftp://ftp.is.co.za/rfc/rfc1808.txt
http://www.ietf.org/rfc/rfc2396.txt#header1
ldap://[2001:db8::7]/c=GB?objectClass?one
mailto:John.Doe@example.com
news:comp.infosystems.www.servers.unix
tel:+1-816-555-1212
telnet://192.0.2.16:80/
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
>;
 
my $u = URI.new;
 
for @test-uris -> $uri {
say "URI:\t", $uri;
$u.parse($uri);
for <scheme host port path query frag> -> $t {
my $token = try {$u."$t"()} || '';
say "$t:\t", $token if $token;
}
say '';
}</lang>
{{out}}
<pre>URI: foo://example.com:8042/over/there?name=ferret#nose
scheme: foo
host: example.com
port: 8042
path: /over/there
query: name=ferret
frag: nose
 
URI: urn:example:animal:ferret:nose
scheme: urn
path: example:animal:ferret:nose
 
URI: jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme: jdbc
path: mysql://test_user:ouupppssss@localhost:3306/sakila
query: profileSQL=true
 
URI: ftp://ftp.is.co.za/rfc/rfc1808.txt
scheme: ftp
host: ftp.is.co.za
port: 21
path: /rfc/rfc1808.txt
 
URI: http://www.ietf.org/rfc/rfc2396.txt#header1
scheme: http
host: www.ietf.org
port: 80
path: /rfc/rfc2396.txt
frag: header1
 
URI: ldap://[2001:db8::7]/c=GB?objectClass?one
scheme: ldap
host: [2001:db8::7]
port: 389
path: /c=GB
query: objectClass?one
 
URI: mailto:John.Doe@example.com
scheme: mailto
path: John.Doe@example.com
 
URI: news:comp.infosystems.www.servers.unix
scheme: news
port: 119
path: comp.infosystems.www.servers.unix
 
URI: tel:+1-816-555-1212
scheme: tel
path: +1-816-555-1212
 
URI: telnet://192.0.2.16:80/
scheme: telnet
host: 192.0.2.16
port: 80
path: /
 
URI: urn:oasis:names:specification:docbook:dtd:xml:4.1.2
scheme: urn
path: oasis:names:specification:docbook:dtd:xml:4.1.2
</pre>
 
=={{header|Phix}}==
There are some fairly rudimentary and lightly documented routines in builtins/url.e.
{{improve|Phix}}
<!--<syntaxhighlight lang="phix">(phixonline)-->
There is a rudimentary and undocumented routine in pfile.e, but it fails several of these tests.
<span style="color: #008080;">with</span> <span style="color: #008080;">javascript_semantics</span>
<lang Phix>include builtins\pfile.e
<span style="color: #008080;">include</span> <span style="color: #000000;">builtins</span><span style="color: #0000FF;">/</span><span style="color: #000000;">url</span><span style="color: #0000FF;">.</span><span style="color: #000000;">e</span>
 
sequence descs = repeat("",8)
<span style="color: #008080;">procedure</span> <span style="color: #000000;">show_url_details</span><span style="color: #0000FF;">(</span><span style="color: #004080;">string</span> <span style="color: #000000;">uri</span><span style="color: #0000FF;">)</span>
descs[URL_PROTOCOL] = "scheme"
<span style="color: #0000FF;">?</span><span style="color: #000000;">uri</span>
descs[URL_HOSTNAME] = "domain"
<span style="color: #004080;">sequence</span> <span style="color: #000000;">r</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">parse_url</span><span style="color: #0000FF;">(</span><span style="color: #000000;">uri</span><span style="color: #0000FF;">)</span>
descs[URL_PORT] = "port"
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span> <span style="color: #008080;">to</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">r</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">do</span>
descs[URL_PATH] = "path"
<span style="color: #008080;">if</span> <span style="color: #000000;">r</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">]!=</span><span style="color: #000000;">0</span> <span style="color: #008080;">then</span>
descs[URL_USER] = "user"
<span style="color: #004080;">string</span> <span style="color: #000000;">desc</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">url_element_desc</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">)</span>
descs[URL_PASSWORD] = "password"
<span style="color: #7060A8;">printf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"%s : %v\n"</span><span style="color: #0000FF;">,{</span><span style="color: #000000;">desc</span><span style="color: #0000FF;">,</span><span style="color: #000000;">r</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">]})</span>
descs[URL_QUERY_STRING] = "query"
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
descs[URL_FRAGMENT] = "fragment"
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
 
<span style="color: #7060A8;">puts</span><span style="color: #0000FF;">(</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"\n"</span><span style="color: #0000FF;">)</span>
procedure show_url_details(sequence res)
<span style="color: #008080;">end</span> <span style="color: #008080;">procedure</span>
for i=1 to length(descs) do
printf(1,"%s : %s\n",{descs[i],sprint(res[i])})
<span style="color: #008080;">constant</span> <span style="color: #000000;">tests</span> <span style="color: #0000FF;">=</span> <span style="color: #0000FF;">{</span>
end for
<span style="color: #008000;">"foo://example.com:8042/over/there?name=ferret#nose"</span><span style="color: #0000FF;">,</span>
puts(1,"\n")
<span style="color: #008000;">"urn:example:animal:ferret:nose"</span><span style="color: #0000FF;">,</span>
end procedure
<span style="color: #008000;">"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true"</span><span style="color: #0000FF;">,</span>
 
<span style="color: #008000;">"ftp://ftp.is.co.za/rfc/rfc1808.txt"</span><span style="color: #0000FF;">,</span>
constant tests = {
<span style="color: #008000;">"http://www.ietf.org/rfc/rfc2396.txt#header1"</span><span style="color: #0000FF;">,</span>
"foo://example.com:8042/over/there?name=ferret#nose",
<span style="color: #008000;">"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two"</span><span style="color: #0000FF;">,</span>
-- "urn:example:animal:ferret:nose", -- crashes
<span style="color: #008000;">"mailto:John.Doe@example.com"</span><span style="color: #0000FF;">,</span>
-- "jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true", -- wrong
<span style="color: #008000;">"news:comp.infosystems.www.servers.unix"</span><span style="color: #0000FF;">,</span>
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
<span style="color: #008000;">"tel:+1-816-555-1212"</span><span style="color: #0000FF;">,</span>
"http://www.ietf.org/rfc/rfc2396.txt#header1",
<span style="color: #008000;">"telnet://192.0.2.16:80/"</span><span style="color: #0000FF;">,</span>
-- "ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two", -- crashes
<span style="color: #008000;">"urn:oasis:names:specification:docbook:dtd:xml:4.1.2"</span><span style="color: #0000FF;">,</span>
"mailto:John.Doe@example.com",
<span style="color: #008000;">"ssh://alice@example.com"</span><span style="color: #0000FF;">,</span>
"news:comp.infosystems.www.servers.unix",
<span style="color: #008000;">"https://bob:pass@example.com/place"</span><span style="color: #0000FF;">,</span>
"tel:+1-816-555-1212",
<span style="color: #008000;">"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"</span>
"telnet://192.0.2.16:80/",
<span style="color: #0000FF;">}</span>
-- "urn:oasis:names:specification:docbook:dtd:xml:4.1.2", -- crashes
"ssh://alice@example.com",
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span> <span style="color: #008080;">to</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">tests</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">do</span>
"https://bob:pass@example.com/place",
<span style="color: #000000;">show_url_details</span><span style="color: #0000FF;">(</span><span style="color: #000000;">tests</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">])</span>
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
}
<!--</syntaxhighlight>-->
 
sequence res
for i=1 to length(tests) do
?tests[i]
res = parse_url(tests[i])
show_url_details(res)
end for</lang>
{{Out}}
<pre>
Line 1,380 ⟶ 3,073:
port : 8042
path : "/over/there"
user : 0
password : 0
query : "name=ferret"
fragment : "nose"
 
"urn:example:animal:ferret:nose"
scheme : "urn"
path : "example:animal:ferret:nose"
 
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true"
scheme : "jdbc"
path : "mysql://test_user:ouupppssss@localhost:3306/sakila"
query : "profileSQL=true"
 
"ftp://ftp.is.co.za/rfc/rfc1808.txt"
scheme : "ftp"
domain : "ftp.is.co.za"
port : 0
path : "/rfc/rfc1808.txt"
user : 0
password : 0
query : 0
fragment : 0
 
"http://www.ietf.org/rfc/rfc2396.txt#header1"
scheme : "http"
domain : "www.ietf.org"
port : 0
path : "/rfc/rfc2396.txt"
user : 0
password : 0
query : 0
fragment : "header1"
 
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two"
scheme : "ldap"
domain : "[2001:db8::7]"
path : "/c=GB"
query : "objectClass=one&objectClass=two"
 
"mailto:John.Doe@example.com"
scheme : "mailto"
domainpath : "John.Doe@example.com"
port : 0
path : 0
user : "John.Doe"
password : 0
query : 0
fragment : 0
 
"news:comp.infosystems.www.servers.unix"
scheme : "news"
domainpath : "comp.infosystems.www.servers.unix"
port : 0
path : 0
user : 0
password : 0
query : 0
fragment : 0
 
"tel:+1-816-555-1212"
scheme : "tel"
domainpath : "+1-816-555-1212"
port : 0
path : 0
user : 0
password : 0
query : 0
fragment : 0
 
"telnet://192.0.2.16:80/"
Line 1,440 ⟶ 3,119:
port : 80
path : "/"
 
user : 0
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2"
password : 0
queryscheme : 0"urn"
path : "oasis:names:specification:docbook:dtd:xml:4.1.2"
fragment : 0
 
"ssh://alice@example.com"
scheme : "ssh"
domain : "example.com"
port : 0
path : 0
user : "alice"
password : 0
query : 0
fragment : 0
 
"https://bob:pass@example.com/place"
scheme : "https"
domain : "example.com"
port : 0
path : "/place"
user : "bob"
password : "pass"
query : 0
fragment : 0
 
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"
scheme : "http"
domain : "example.com"
port : 0
path : "/"
user : 0
password : 0
query : "a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64"
fragment : 0
</pre>
 
=={{header|PHP}}==
 
Using the parse_url function (Parse a URL and return its components)
 
<syntaxhighlight lang="php"><?php
 
$urls = array(
'foo://example.com:8042/over/there?name=ferret#nose',
'urn:example:animal:ferret:nose',
'jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true',
'ftp://ftp.is.co.za/rfc/rfc1808.txt',
'http://www.ietf.org/rfc/rfc2396.txt#header1',
'ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two',
'mailto:John.Doe@example.com',
'news:comp.infosystems.www.servers.unix',
'tel:+1-816-555-1212',
'telnet://192.0.2.16:80/',
'urn:oasis:names:specification:docbook:dtd:xml:4.1.2',
);
 
foreach ($urls AS $url) {
$p = parse_url($url);
echo $url, PHP_EOL;
print_r($p);
echo PHP_EOL;
}</syntaxhighlight>
 
{{out}}
<pre style="height:256px">foo://example.com:8042/over/there?name=ferret#nose
Array
(
[scheme] => foo
[host] => example.com
[port] => 8042
[path] => /over/there
[query] => name=ferret
[fragment] => nose
)
 
urn:example:animal:ferret:nose
Array
(
[scheme] => urn
[path] => example:animal:ferret:nose
)
 
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
Array
(
[scheme] => jdbc
[path] => mysql://test_user:ouupppssss@localhost:3306/sakila
[query] => profileSQL=true
)
 
ftp://ftp.is.co.za/rfc/rfc1808.txt
Array
(
[scheme] => ftp
[host] => ftp.is.co.za
[path] => /rfc/rfc1808.txt
)
 
http://www.ietf.org/rfc/rfc2396.txt#header1
Array
(
[scheme] => http
[host] => www.ietf.org
[path] => /rfc/rfc2396.txt
[fragment] => header1
)
 
ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
Array
(
[scheme] => ldap
[host] => [2001:db8::7]
[path] => /c=GB
[query] => objectClass=one&objectClass=two
)
 
mailto:John.Doe@example.com
Array
(
[scheme] => mailto
[path] => John.Doe@example.com
)
 
news:comp.infosystems.www.servers.unix
Array
(
[scheme] => news
[path] => comp.infosystems.www.servers.unix
)
 
tel:+1-816-555-1212
Array
(
[scheme] => tel
[path] => +1-816-555-1212
)
 
telnet://192.0.2.16:80/
Array
(
[scheme] => telnet
[host] => 192.0.2.16
[port] => 80
[path] => /
)
 
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
Array
(
[scheme] => urn
[path] => oasis:names:specification:docbook:dtd:xml:4.1.2
)</pre>
 
=={{header|PowerShell}}==
I was confused about the '''Path''' parameter. PowerShell returns '''LocalPath''', '''AbsolutePath''' and '''AbsoluteUri'''; I defaulted to '''LocalPath''', but all properties are returned in the <code>$parsedUrls</code> variable.
<syntaxhighlight lang="powershell">
<lang PowerShell>
function Get-ParsedUrl
{
Line 1,522 ⟶ 3,306:
}
}
</syntaxhighlight>
</lang>
<syntaxhighlight lang="powershell">
<lang PowerShell>
[string[]]$urls = @'
foo://example.com:8042/over/there?name=ferret#nose
Line 1,541 ⟶ 3,325:
 
$parsedUrls | Select-Object -Property Scheme, Port, Domain, Path, Query, Fragment | Format-Table
</syntaxhighlight>
</lang>
{{Out}}
<pre>
Line 1,561 ⟶ 3,345:
=={{header|Python}}==
Links to Python Documentation: v2: [https://docs.python.org/2/library/urlparse.html#module-urlparse], v3: [https://docs.python.org/3.4/library/urllib.parse.html]
<langsyntaxhighlight Pythonlang="python">import urllib.parse as up # urlparse for Python v2
 
url = up.urlparse('http://user:pass@example.com:8081/path/file.html;params?query1=1#fragment')
Line 1,575 ⟶ 3,359:
print('url.username = ', url.username)
print('url.password = ', url.password)
</syntaxhighlight>
</lang>
{{out}}
<pre>
Line 1,588 ⟶ 3,372:
url.username = user
url.password = pass
</pre>
 
=={{header|R}}==
urltools::url_parse() do all the actually work. The rest is just for nice output.
<syntaxhighlight lang="rsplus">
library(urltools)
 
urls <- c("foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
"ssh://alice@example.com",
"https://bob:pass@example.com/place",
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64")
 
for (an_url in urls) {
parsed <- url_parse(an_url)
cat(an_url,"\n")
for (idx in 1:ncol(parsed)) {
if (!is.na(parsed[[idx]])) {
cat(colnames(parsed)[[idx]],"\t:",parsed[[idx]],"\n")
}
}
cat("\n")
}
</syntaxhighlight>
{{out}}
<pre>
foo://example.com:8042/over/there?name=ferret#nose
scheme : foo
domain : example.com
port : 8042
path : over/there
parameter : name=ferret
fragment : nose
 
urn:example:animal:ferret:nose
domain : urn
port : example:animal:ferret:nose
 
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme : jdbc:mysql
domain : localhost
port : 3306
path : sakila
parameter : profileSQL=true
 
ftp://ftp.is.co.za/rfc/rfc1808.txt
scheme : ftp
domain : ftp.is.co.za
path : rfc/rfc1808.txt
 
http://www.ietf.org/rfc/rfc2396.txt#header1
scheme : http
domain : www.ietf.org
path : rfc/rfc2396.txt
fragment : header1
 
ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
scheme : ldap
path : c=GB
parameter : objectClass=one&objectClass=two
 
mailto:John.Doe@example.com
domain : example.com
 
news:comp.infosystems.www.servers.unix
domain : news
port : comp.infosystems.www.servers.unix
 
tel:+1-816-555-1212
domain : tel
port : +1-816-555-1212
 
telnet://192.0.2.16:80/
scheme : telnet
domain : 192.0.2.16
port : 80
 
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
domain : urn
port : oasis:names:specification:docbook:dtd:xml:4.1.2
 
ssh://alice@example.com
scheme : ssh
domain : example.com
 
https://bob:pass@example.com/place
scheme : https
domain : example.com
path : place
 
http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
scheme : http
domain : example.com
parameter : a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
</pre>
 
Line 1,593 ⟶ 3,480:
Links: [http://docs.racket-lang.org/net/url.html?q=url#%28def._%28%28lib._net%2Furl-structs..rkt%29._url%29%29 <code>url</code> structure in Racket documentation].
 
<langsyntaxhighlight lang="racket">#lang racket/base
(require racket/match net/url)
(define (debug-url-string U)
Line 1,628 ⟶ 3,515:
"tel:+1-816-555-1212"
"telnet://192.0.2.16:80/"
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2"))</langsyntaxhighlight>
 
{{out}}
Line 1,709 ⟶ 3,596:
path bits: ("oasis:names:specification:docbook:dtd:xml:4.1.2")</pre>
 
=={{header|Raku}}==
(formerly Perl 6)
{{works with|rakudo|2015-11-02}}
Uses the URI library which implements a Raku grammar based on the RFC 3986 BNF grammar.
<syntaxhighlight lang="raku" line>use URI;
use URI::Escape;
 
my @test-uris = <
foo://example.com:8042/over/there?name=ferret#nose
urn:example:animal:ferret:nose
jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
ftp://ftp.is.co.za/rfc/rfc1808.txt
http://www.ietf.org/rfc/rfc2396.txt#header1
ldap://[2001:db8::7]/c=GB?objectClass?one
mailto:John.Doe@example.com
news:comp.infosystems.www.servers.unix
tel:+1-816-555-1212
telnet://192.0.2.16:80/
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
ssh://alice@example.com
https://bob:pass@example.com/place
http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
>;
 
my $u = URI.new;
 
for @test-uris -> $uri {
say "URI:\t", $uri;
$u.parse($uri);
for <scheme host port path query frag> -> $t {
my $token = try {$u."$t"()} || '';
say "$t:\t", uri-unescape $token.Str if $token;
}
say '';
}</syntaxhighlight>
{{out}}
<pre>URI: foo://example.com:8042/over/there?name=ferret#nose
scheme: foo
host: example.com
port: 8042
path: /over/there
query: name=ferret
frag: nose
 
URI: urn:example:animal:ferret:nose
scheme: urn
path: example:animal:ferret:nose
 
URI: jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme: jdbc
path: mysql://test_user:ouupppssss@localhost:3306/sakila
query: profileSQL=true
 
URI: ftp://ftp.is.co.za/rfc/rfc1808.txt
scheme: ftp
host: ftp.is.co.za
port: 21
path: /rfc/rfc1808.txt
 
URI: http://www.ietf.org/rfc/rfc2396.txt#header1
scheme: http
host: www.ietf.org
port: 80
path: /rfc/rfc2396.txt
frag: header1
 
URI: ldap://[2001:db8::7]/c=GB?objectClass?one
scheme: ldap
host: [2001:db8::7]
port: 389
path: /c=GB
query: objectClass?one
 
URI: mailto:John.Doe@example.com
scheme: mailto
path: John.Doe@example.com
 
URI: news:comp.infosystems.www.servers.unix
scheme: news
port: 119
path: comp.infosystems.www.servers.unix
 
URI: tel:+1-816-555-1212
scheme: tel
path: 1-816-555-1212
 
URI: telnet://192.0.2.16:80/
scheme: telnet
host: 192.0.2.16
port: 80
path: /
 
URI: urn:oasis:names:specification:docbook:dtd:xml:4.1.2
scheme: urn
path: oasis:names:specification:docbook:dtd:xml:4.1.2
 
URI: ssh://alice@example.com
scheme: ssh
host: example.com
port: 22
path:
 
URI: https://bob:pass@example.com/place
scheme: https
host: example.com
port: 443
path: /place
 
URI: http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
scheme: http
host: example.com
port: 80
path: /
query: a=1&b=2 2&c=3&c=4&d=encoded</pre>
 
=={{header|Ruby}}==
Line 1,714 ⟶ 3,715:
 
As you can see in the output below, the URI library doesn't parse all of these as recommended.
<langsyntaxhighlight Rubylang="ruby">require 'uri'
 
test_cases = [
Line 1,741 ⟶ 3,742:
puts " #{attr.rjust(8)} = #{uri.send(attr)}" if uri.send(attr)
end
end</langsyntaxhighlight>
{{out}}
<pre>foo://example.com:8042/over/there?name=ferret#nose
Line 1,802 ⟶ 3,803:
path = /
query = a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64</pre>
 
=={{header|Rust}}==
<syntaxhighlight lang="rust">use url::Url;
 
fn print_fields(url: Url) -> () {
println!("scheme: {}", url.scheme());
println!("username: {}", url.username());
 
if let Some(password) = url.password() {
println!("password: {}", password);
}
 
if let Some(domain) = url.domain() {
println!("domain: {}", domain);
}
 
if let Some(port) = url.port() {
println!("port: {}", port);
}
println!("path: {}", url.path());
 
if let Some(query) = url.query() {
println!("query: {}", query);
}
 
if let Some(fragment) = url.fragment() {
println!("fragment: {}", fragment);
}
}
fn main() {
let urls = vec![
"foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
"ssh://alice@example.com",
"https://bob:pass@example.com/place",
"http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64",
];
 
for url in urls {
println!("Parsing {}", url);
match Url::parse(url) {
Ok(valid_url) => {
print_fields(valid_url);
println!();
}
Err(e) => println!("Error Parsing url - {:?}", e),
}
}
}
</syntaxhighlight>
Output:
<pre>
Parsing foo://example.com:8042/over/there?name=ferret#nose
scheme: foo
username:
domain: example.com
port: 8042
path: /over/there
query: name=ferret
fragment: nose
 
Parsing urn:example:animal:ferret:nose
scheme: urn
username:
path: example:animal:ferret:nose
 
Parsing jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
scheme: jdbc
username:
path: mysql://test_user:ouupppssss@localhost:3306/sakila
query: profileSQL=true
 
Parsing ftp://ftp.is.co.za/rfc/rfc1808.txt
scheme: ftp
username:
domain: ftp.is.co.za
path: /rfc/rfc1808.txt
 
Parsing http://www.ietf.org/rfc/rfc2396.txt#header1
scheme: http
username:
domain: www.ietf.org
path: /rfc/rfc2396.txt
fragment: header1
 
Parsing ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
scheme: ldap
username:
path: /c=GB
query: objectClass=one&objectClass=two
 
Parsing mailto:John.Doe@example.com
scheme: mailto
username:
path: John.Doe@example.com
 
Parsing news:comp.infosystems.www.servers.unix
scheme: news
username:
path: comp.infosystems.www.servers.unix
 
Parsing tel:+1-816-555-1212
scheme: tel
username:
path: +1-816-555-1212
 
Parsing telnet://192.0.2.16:80/
scheme: telnet
username:
domain: 192.0.2.16
port: 80
path: /
 
Parsing urn:oasis:names:specification:docbook:dtd:xml:4.1.2
scheme: urn
username:
path: oasis:names:specification:docbook:dtd:xml:4.1.2
 
Parsing ssh://alice@example.com
scheme: ssh
username: alice
domain: example.com
path:
 
Parsing https://bob:pass@example.com/place
scheme: https
username: bob
password: pass
domain: example.com
path: /place
 
Parsing http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
scheme: http
username:
domain: example.com
path: /
query: a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
</pre>
 
=={{header|Scala}}==
<syntaxhighlight lang="scala">import java.net.URI
 
object WebAddressParser extends App {
 
parseAddress("foo://example.com:8042/over/there?name=ferret#nose")
parseAddress("ftp://ftp.is.co.za/rfc/rfc1808.txt")
parseAddress("http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64")
parseAddress("http://www.ietf.org/rfc/rfc2396.txt#header1")
parseAddress("https://bob:pass@example.com/place")
parseAddress("jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true")
parseAddress("ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two")
parseAddress("ldap://[2001:db8::7]/c=GB?objectClass?one")
parseAddress("mailto:John.Doe@example.com")
parseAddress("news:comp.infosystems.www.servers.unix")
parseAddress("ssh://alice@example.com")
parseAddress("tel:+1-816-555-1212")
parseAddress("telnet://192.0.2.16:80/")
parseAddress("urn:example:animal:ferret:nose")
parseAddress("urn:oasis:names:specification:docbook:dtd:xml:4.1.2")
parseAddress("This is not a URI!")
 
private def parseAddress(a: String): Unit = {
print(f"Parsing $a%-72s")
try {
val u = new URI(a)
print("\u2714\tscheme = " + u.getScheme)
print("\tdomain = " + u.getHost)
print("\tport = " + (if (-1 == u.getPort) "default" else u.getPort))
print("\tpath = " + (if (u.getPath == null) u.getSchemeSpecificPart else u.getPath))
print("\tquery = " + u.getQuery)
println("\tfragment = " + u.getFragment)
} catch { case ex: Throwable => println('\u2718') }
}
}</syntaxhighlight>
{{Out}}See it in running in your browser by [https://scastie.scala-lang.org/GZdtfkhfRsa9QPKZQ7W4XQ Scastie (JVM)].
 
=={{header|Tcl}}==
Line 1,815 ⟶ 4,000:
The <tt>uri</tt> package doesn't presently handle IPv6 syntx as used in the example: a bug and patch will be submitted presently ..
 
<langsyntaxhighlight Tcllang="tcl">package require uri
package require uri::urn
 
Line 1,854 ⟶ 4,039:
puts \n$uri
pdict [parse_uri $uri]
}</langsyntaxhighlight>
 
{{out}}
Line 1,915 ⟶ 4,100:
 
=={{header|VBScript}}==
<syntaxhighlight lang="vb">
<lang vb>
Function parse_url(url)
parse_url = "URL: " & url
Line 2,012 ⟶ 4,197:
WScript.StdOut.WriteLine "-------------------------------"
WScript.StdOut.WriteLine parse_url("this code is messy, long, and needs a makeover!!!")
</syntaxhighlight>
</lang>
 
{{Out}}
Line 2,074 ⟶ 4,259:
URL: this code is messy, long, and needs a makeover!!!
Invalid!!!
</pre>
 
=={{header|V (Vlang)}}==
{{trans|Go}}
<syntaxhighlight lang="v (vlang)">import net.urllib
 
const urls = ['jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true',
'ftp://ftp.is.co.za/rfc/rfc1808.txt',
'http://www.ietf.org/rfc/rfc2396.txt#header1',
'ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two',
'mailto:John.Doe@example.com',
'news:comp.infosystems.www.servers.unix',
'tel:+1-816-555-1212',
'telnet://192.0.2.16:80/',
'urn:oasis:names:specification:docbook:dtd:xml:4.1.2',
'foo://example.com:8042/over/there?name=ferret#nose'
]
 
fn main() {
for url in urls {
u := urllib.parse(url)?
println(u)
print_url(u)
}
}
 
fn print_url(u urllib.URL) {
println(" Scheme: $u.scheme")
if u.opaque != "" {
println(" Opaque: $u.opaque")
}
if u.str() == '' {
println(" Username: $u.user.username")
if u.user.password != '' {
println(" Password: $u.user.password")
}
}
if u.host != "" {
if u.port() != '' {
println(" Host: ${u.hostname()}")
println(" Port: ${u.port()}")
} else {
println(" Host: $u.host")
}
}
if u.path != "" {
println(" Path: $u.path")
}
if u.raw_query != "" {
println(" RawQuery: $u.raw_query")
m := u.query().data
for q in m {
println(" Key: $q.key Values: $q.value")
}
}
if u.fragment != "" {
println(" Fragment: $u.fragment")
}
}</syntaxhighlight>
{{out}}
<pre>jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
Scheme: jdbc
Opaque: mysql://test_user:ouupppssss@localhost:3306/sakila
RawQuery: profileSQL=true
Key: profileSQL Values: true
ftp://ftp.is.co.za/rfc/rfc1808.txt
Scheme: ftp
Host: ftp.is.co.za
Path: /rfc/rfc1808.txt
http://www.ietf.org/rfc/rfc2396.txt#header1
Scheme: http
Host: www.ietf.org
Path: /rfc/rfc2396.txt
Fragment: header1
ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
Scheme: ldap
Host: [2001:db8::7]
Path: /c=GB
RawQuery: objectClass=one&objectClass=two
Key: objectClass Values: one
Key: objectClass Values: two
mailto:John.Doe@example.com
Scheme: mailto
Opaque: John.Doe@example.com
news:comp.infosystems.www.servers.unix
Scheme: news
Opaque: comp.infosystems.www.servers.unix
tel:+1-816-555-1212
Scheme: tel
Opaque: +1-816-555-1212
telnet://192.0.2.16:80/
Scheme: telnet
Host: 192.0.2.16
Port: 80
Path: /
urn:oasis:names:specification:docbook:dtd:xml:4.1.2
Scheme: urn
Opaque: oasis:names:specification:docbook:dtd:xml:4.1.2
foo://example.com:8042/over/there?name=ferret#nose
Scheme: foo
Host: example.com
Port: 8042
Path: /over/there
RawQuery: name=ferret
Key: name Values: ferret
Fragment: nose
</pre>
 
=={{header|Wren}}==
{{trans|VBScript}}
... though modified quite a bit.
<syntaxhighlight lang="wren">var urlParse = Fn.new { |url|
var parseUrl = "URL = " + url
var index
if ((index = url.indexOf("//")) && index >= 0 && url[0...index].count { |c| c == ":" } == 1) {
// parse the scheme
var scheme = url.split("//")
parseUrl = parseUrl + "\n" + "Scheme = " + scheme[0][0..-2]
// parse the domain
var domain = scheme[1].split("/")
// check if the domain includes a username, password and port
if (domain[0].contains("@")) {
var cred = domain[0].split("@")
var split = [cred[0], ""]
if (cred[0].contains(".")) {
split = cred[0].split(".")
} else if (cred[0].contains(":")) {
split = cred[0].split(":")
}
var username = split[0]
var password = split[1]
parseUrl = parseUrl + "\n" + "Username = " + username
if (password != "") parseUrl = parseUrl + "\n" + "Password = " + password
// check if the domain has a port
if (cred[1].contains(":")) {
split = cred[1].split(":")
var host = split[0]
var port = ":" + split[1]
parseUrl = parseUrl + "\n" + "Domain = " + host + "\n" + "Port = " + port
} else {
parseUrl = parseUrl + "\n" + "Domain = " + cred[1]
}
} else if (domain[0].contains(":") && !domain[0].contains("[") && !domain[0].contains("]")) {
var split = domain[0].split(":")
var host = split[0]
var port = ":" + split[1]
parseUrl = parseUrl + "\n" + "Domain = " + host + "\n" + "Port = " + port
} else if (domain[0].contains("[") && domain[0].contains("]:")) {
var split = domain[0].split("]")
var host = split[0] + "]"
var port = ":" + split[1][1..-1]
parseUrl = parseUrl + "\n" + "Domain = " + host + "\n" + "Port = " + port
} else {
parseUrl = parseUrl + "\n" + "Domain = " + domain[0]
}
// parse the path if it exists
if (domain.count > 1) {
var path = "/"
for (i in 1...domain.count) {
if (i < domain.count - 1) {
path = path + domain[i] + "/"
} else if (domain[i].contains("?")) {
var split = domain[i].split("?")
path = path + split[0]
if (domain[i].contains("#")) {
var split2 = split[1].split("#")
var query = split2[0]
var fragment = split2[1]
path = path + "\n" + "Query = " + query + "\n" + "Fragment = " + fragment
} else {
var query = split[1]
path = path + "\n" + "Query = " + query
}
} else if (domain[i].contains("#")) {
var split = domain[i].split("#")
var fragment = split[1]
path = path + split[0] + "\n" + "Fragment = " + fragment
} else {
path = path + domain[i]
}
}
parseUrl = parseUrl + "\n" + "Path = " + path
}
} else if (url.contains(":")) {
var index = url.indexOf(":")
var scheme = url[0...index]
parseUrl = parseUrl + "\n" + "Scheme = " + scheme + "\n"
var path = url[index+1..-1]
if (!path.contains("?")) {
parseUrl = parseUrl + "Path = " + path
} else {
var split = path.split("?")
var query = split[1]
parseUrl = parseUrl + "Path = " + split[0] + "\n"
if (!query.contains("#")) {
parseUrl = parseUrl + "Query = " + query
} else {
split = query.split("#")
var fragment = split[1]
parseUrl = parseUrl + "Query = " + split[0] + "Fragment = " + fragment
}
}
} else {
parseUrl = parseUrl + "\n" + "Invalid!!!"
}
System.print(parseUrl)
System.print()
}
 
var urls = [
"foo://example.com:8042/over/there?name=ferret#nose",
"urn:example:animal:ferret:nose",
"jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true",
"ftp://ftp.is.co.za/rfc/rfc1808.txt",
"http://www.ietf.org/rfc/rfc2396.txt#header1",
"ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two",
"mailto:John.Doe@example.com",
"news:comp.infosystems.www.servers.unix",
"tel:+1-816-555-1212",
"telnet://192.0.2.16:80/",
"urn:oasis:names:specification:docbook:dtd:xml:4.1.2",
"ssh://alice@example.com",
"https://bob:pass@example.com/place",
"http://example.com/?a=1&b=2+2&c=3&c=4&d=\%65\%6e\%63\%6F\%64\%65\%64"
]
for (url in urls) urlParse.call(url)</syntaxhighlight>
 
{{out}}
<pre>
URL = foo://example.com:8042/over/there?name=ferret#nose
Scheme = foo
Domain = example.com
Port = :8042
Path = /over/there
Query = name=ferret
Fragment = nose
 
URL = urn:example:animal:ferret:nose
Scheme = urn
Path = example:animal:ferret:nose
 
URL = jdbc:mysql://test_user:ouupppssss@localhost:3306/sakila?profileSQL=true
Scheme = jdbc
Path = mysql://test_user:ouupppssss@localhost:3306/sakila
Query = profileSQL=true
 
URL = ftp://ftp.is.co.za/rfc/rfc1808.txt
Scheme = ftp
Domain = ftp.is.co.za
Path = /rfc/rfc1808.txt
 
URL = http://www.ietf.org/rfc/rfc2396.txt#header1
Scheme = http
Domain = www.ietf.org
Path = /rfc/rfc2396.txt
Fragment = header1
 
URL = ldap://[2001:db8::7]/c=GB?objectClass=one&objectClass=two
Scheme = ldap
Domain = [2001:db8::7]
Path = /c=GB
Query = objectClass=one&objectClass=two
 
URL = mailto:John.Doe@example.com
Scheme = mailto
Path = John.Doe@example.com
 
URL = news:comp.infosystems.www.servers.unix
Scheme = news
Path = comp.infosystems.www.servers.unix
 
URL = tel:+1-816-555-1212
Scheme = tel
Path = +1-816-555-1212
 
URL = telnet://192.0.2.16:80/
Scheme = telnet
Domain = 192.0.2.16
Port = :80
Path = /
 
URL = urn:oasis:names:specification:docbook:dtd:xml:4.1.2
Scheme = urn
Path = oasis:names:specification:docbook:dtd:xml:4.1.2
 
URL = ssh://alice@example.com
Scheme = ssh
Username = alice
Domain = example.com
 
URL = https://bob:pass@example.com/place
Scheme = https
Username = bob
Password = pass
Domain = example.com
Path = /place
 
URL = http://example.com/?a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
Scheme = http
Domain = example.com
Path = /
Query = a=1&b=2+2&c=3&c=4&d=%65%6e%63%6F%64%65%64
</pre>
9,482

edits