From e5679d7b02ae551543ee073ea1181881f96ea11b Mon Sep 17 00:00:00 2001
From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com>
Date: Tue, 10 Feb 2026 14:34:45 +0000
Subject: [PATCH 1/4] Refine Host documentation: C#-only examples, clarify
IdnHost behavior
Co-authored-by: MihaZupan <25307628+MihaZupan@users.noreply.github.com>
---
.../Uri/HostComparison/Project.csproj} | 4 +-
.../System/Uri/HostComparison/source.cs | 50 +++++
.../TableAttribute/Overview/Project.vbproj | 12 --
xml/System/Uri.xml | 194 ++++++++----------
4 files changed, 141 insertions(+), 119 deletions(-)
rename snippets/csharp/{System.Linq/Enumerable/AggregateBy/Enumerable.csproj => System/Uri/HostComparison/Project.csproj} (70%)
create mode 100644 snippets/csharp/System/Uri/HostComparison/source.cs
delete mode 100644 snippets/visualbasic/System.Data.Linq/TableAttribute/Overview/Project.vbproj
diff --git a/snippets/csharp/System.Linq/Enumerable/AggregateBy/Enumerable.csproj b/snippets/csharp/System/Uri/HostComparison/Project.csproj
similarity index 70%
rename from snippets/csharp/System.Linq/Enumerable/AggregateBy/Enumerable.csproj
rename to snippets/csharp/System/Uri/HostComparison/Project.csproj
index 92e46ddaccf..dd4b56868ac 100644
--- a/snippets/csharp/System.Linq/Enumerable/AggregateBy/Enumerable.csproj
+++ b/snippets/csharp/System/Uri/HostComparison/Project.csproj
@@ -1,8 +1,6 @@
-
Exe
- net9.0
+ net8.0
-
diff --git a/snippets/csharp/System/Uri/HostComparison/source.cs b/snippets/csharp/System/Uri/HostComparison/source.cs
new file mode 100644
index 00000000000..38be1206f6b
--- /dev/null
+++ b/snippets/csharp/System/Uri/HostComparison/source.cs
@@ -0,0 +1,50 @@
+using System;
+
+public class UriHostComparison
+{
+ public static void Main()
+ {
+ //
+ // Demonstrate differences between Host, IdnHost, and DnsSafeHost.
+
+ // Example 1: Regular hostname (ASCII).
+ Console.WriteLine("Example 1: Regular ASCII hostname");
+ Uri uri1 = new Uri("http://www.contoso.com:8080/path");
+ Console.WriteLine($" Host: {uri1.Host}"); // www.contoso.com
+ Console.WriteLine($" IdnHost: {uri1.IdnHost}"); // www.contoso.com
+ Console.WriteLine($" DnsSafeHost: {uri1.DnsSafeHost}"); // www.contoso.com
+ Console.WriteLine();
+
+ // Example 2: International domain name (non-ASCII).
+ Console.WriteLine("Example 2: International domain name");
+ Uri uri2 = new Uri("http://münchen.de/path");
+ Console.WriteLine($" Host: {uri2.Host}"); // münchen.de (original)
+ Console.WriteLine($" IdnHost: {uri2.IdnHost}"); // xn--mnchen-3ya.de (punycode)
+ Console.WriteLine($" DnsSafeHost: {uri2.DnsSafeHost}"); // münchen.de
+ Console.WriteLine();
+
+ // Example 3: IPv6 address without zone ID.
+ Console.WriteLine("Example 3: IPv6 address without zone ID");
+ Uri uri3 = new Uri("http://[::1]:8080/path");
+ Console.WriteLine($" Host: {uri3.Host}"); // [::1] (with brackets)
+ Console.WriteLine($" IdnHost: {uri3.IdnHost}"); // ::1 (without brackets)
+ Console.WriteLine($" DnsSafeHost: {uri3.DnsSafeHost}"); // ::1 (without brackets)
+ Console.WriteLine();
+
+ // Example 4: IPv6 link-local address with zone ID.
+ Console.WriteLine("Example 4: IPv6 link-local address with zone ID");
+ Uri uri4 = new Uri("http://[fe80::1%10]:8080/path");
+ Console.WriteLine($" Host: {uri4.Host}"); // [fe80::1] (with brackets, no zone ID)
+ Console.WriteLine($" IdnHost: {uri4.IdnHost}"); // fe80::1%10 (without brackets, with zone ID)
+ Console.WriteLine($" DnsSafeHost: {uri4.DnsSafeHost}"); // fe80::1%10 (without brackets, with zone ID)
+ Console.WriteLine();
+
+ // Example 5: IPv4 address.
+ Console.WriteLine("Example 5: IPv4 address");
+ Uri uri5 = new Uri("http://192.168.1.1:8080/path");
+ Console.WriteLine($" Host: {uri5.Host}"); // 192.168.1.1
+ Console.WriteLine($" IdnHost: {uri5.IdnHost}"); // 192.168.1.1
+ Console.WriteLine($" DnsSafeHost: {uri5.DnsSafeHost}"); // 192.168.1.1
+ //
+ }
+}
diff --git a/snippets/visualbasic/System.Data.Linq/TableAttribute/Overview/Project.vbproj b/snippets/visualbasic/System.Data.Linq/TableAttribute/Overview/Project.vbproj
deleted file mode 100644
index c4963049dfd..00000000000
--- a/snippets/visualbasic/System.Data.Linq/TableAttribute/Overview/Project.vbproj
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
-
- Exe
- net48
-
-
-
-
-
-
-
diff --git a/xml/System/Uri.xml b/xml/System/Uri.xml
index 3bcf5e86f49..11c5b3d7c02 100644
--- a/xml/System/Uri.xml
+++ b/xml/System/Uri.xml
@@ -1648,7 +1648,57 @@ For `uriString`, an IPv6 address in string form must be enclosed within brackets
## Remarks
For IPv6 addresses, the brackets ([]) are removed and the property is set, if one was specified when this instance was constructed.
-If you used an escaped string to construct this instance (for example, `"http://[fe80::200:39ff:fe36:1a2d%254]/temp/example.htm"`), then DnsSafeHost returns an escaped string. Unescape any escaped string returned from `DnsSafeHost` before using that string for DNS resolution (see the Example). If you used an invalid unescaped string to construct this instance (for example, "http://[fe80::200:39ff:fe36:1a2d%4]/temp/example.htm"), then DnsSafeHost returns an unescaped string.
+If you used an escaped string to construct this instance (for example, `"http://[fe80::200:39ff:fe36:1a2d%254]/temp/example.htm"`), then returns an escaped string. Unescape any escaped string returned from `DnsSafeHost` before using that string for DNS resolution (see the Example). If you used an invalid unescaped string to construct this instance (for example, "http://[fe80::200:39ff:fe36:1a2d%4]/temp/example.htm"), then returns an unescaped string.
+
+## Comparison with other Host properties
+
+ The class provides two main host properties:
+
+ - : Returns the host as it appears in the URI. For IPv6, includes brackets but not the zone ID.
+ - : Returns a format suitable for DNS resolution. For valid international domain names, applies punycode encoding. For IPv6, doesn't include brackets but does include the zone ID.
+
+ The property is a legacy property that depends on configuration settings. Use instead for consistent, configuration-independent behavior.
+
+ The property is dependent on configuration settings in .NET Framework apps, as discussed later in this topic. The property is provided as the preferred alternative to using because is guaranteed to always be DNS safe.
+
+ The property was extended in .NET Framework v3.5, 3.0 SP1, and 2.0 SP1 to provide International Resource Identifier (IRI) support based on RFC 3987. However, to ensure application compatibility with prior versions, you must specifically enable it in .NET Framework apps. To enable support for IRI, the following two changes are required:
+
+1. Add the following line to the *machine.config* file under the .NET Framework 2.0 directory:
+
+ `\`
+
+2. Specify whether you want Internationalized Domain Name (IDN) parsing applied to the domain name and whether IRI parsing rules should be applied. This can be done in the *machine.config* or in the *app.config* file. For example, add the following:
+
+ ```xml
+
+
+
+
+
+
+ ```
+
+ Enabling IDN converts all Unicode labels in a domain name to their Punycode equivalents. Punycode names contain only ASCII characters and always start with the xn-- prefix. The reason for this is to support existing DNS servers on the Internet, since most DNS servers only support ASCII characters (see RFC 3940).
+
+ Enabling IDN only affects the value of the property.
+
+ There are three possible values for IDN depending on the DNS servers that are used:
+
+- idn enabled = All
+
+ This value will convert any Unicode domain names to their Punycode equivalents (IDN names).
+
+- idn enabled = AllExceptIntranet
+
+ This value will convert all external Unicode domain names to use the Punycode equivalents (IDN names). In this case to handle international names on the local Intranet, the DNS servers that are used for the Intranet should support Unicode names.
+
+- idn enabled = None
+
+ This value won't convert any Unicode domain names to use Punycode. This is the default value, which is consistent with the .NET Framework 2.0 behavior.
+
+ Enabling IRI parsing (iriParsing enabled = `true`) normalizes and checks characters according to the IRI rules in RFC 3987. The default value is `false` and normalizes and checks characters according to RFC 2396 and RFC 2732 (for IPv6 literals).
+
+ For more information on IRI support, see the Remarks section for the class.
## Examples
The following example creates a instance from a string. It illustrates the difference between the value returned from , which returns the host name or address specified in the URI, and the value returned from , which returns an address that is safe to use in DNS resolution.
@@ -1657,7 +1707,7 @@ If you used an escaped string to construct this instance (for example, `"http://
:::code language="fsharp" source="~/snippets/fsharp/System/Uri/.ctor/nclurienhancements.fs" id="Snippet4":::
:::code language="vb" source="~/snippets/visualbasic/System/Uri/.ctor/nclurienhancements.vb" id="Snippet4":::
- As explained in Remarks, unescape the host name before resolving it. You can use the method to unescape the host name, and you can resolve it by calling the method.
+ As explained in Remarks, unescape the host name before resolving it. You can use the method to unescape the host name, and you can resolve it by calling the method.
]]>
@@ -2636,7 +2686,24 @@ The following examples show a URI and the results of calling property, this property value does not include the port number.
+ Unlike the property, this property value doesn't include the port number.
+
+ The behavior of this property depends on the host type:
+
+ - For **regular DNS hostnames**: Returns the escaped input. Non-ASCII characters are returned as-is without punycode encoding.
+ - For **IPv6 addresses**: Returns the address with square brackets (for example, `[::1]` or `[fe80::1]`) but doesn't include the zone ID (scope) even if one was specified in the original URI.
+ - For **IPv4 addresses**: Returns the dotted-decimal notation (for example, `192.168.1.1`).
+
+## Comparison with IdnHost
+
+ The class provides two main host properties:
+
+ - : Returns the host as it appears in the URI. For IPv6, includes brackets but not the zone ID.
+ - : Returns a format suitable for DNS resolution. For valid international domain names, applies punycode encoding. For IPv6, doesn't include brackets but does include the zone ID.
+
+ Which property to use depends on your scenario:
+ - Use when you need the original host string as it appears in the URI (for display or comparison).
+ - Use when you need a format suitable for DNS resolution or network APIs.
## Examples
The following example writes the host name (`www.contoso.com`) of the server to the console.
@@ -2645,113 +2712,32 @@ The following examples show a URI and the results of calling
-
- This instance represents a relative URI, and this property is valid only for absolute URIs.
-
-
-
-
-
-
-
-
-
- Property
-
- System.Runtime
- 4.1.0.0
- 4.2.0.0
- 4.2.1.0
- 4.2.2.0
- 5.0.0.0
- 6.0.0.0
- 7.0.0.0
- 8.0.0.0
- 9.0.0.0
- 10.0.0.0
- 11.0.0.0
-
-
- System
- 1.0.5000.0
- 2.0.0.0
- 2.0.5.0
- 4.0.0.0
-
-
- netstandard
- 2.0.0.0
- 2.1.0.0
-
-
- System.UriHostNameType
-
-
- Gets the type of the host name specified in the URI.
- A member of the enumeration.
-
- instance and writes the to the console.
+## Comparison with Host
- :::code language="csharp" source="~/snippets/csharp/System/Uri/CheckSchemeName/uriexamples.cs" id="Snippet9":::
- :::code language="fsharp" source="~/snippets/fsharp/System/Uri/CheckSchemeName/uriexamples.fs" id="Snippet9":::
- :::code language="vb" source="~/snippets/visualbasic/System/Uri/CheckSchemeName/uriexamples.vb" id="Snippet9":::
+ The class provides two main host properties:
- ]]>
-
- This instance represents a relative URI, and this property is valid only for absolute URIs.
-
-
-
-
-
-
-
-
-
- Property
-
- System.Runtime
- 4.1.0.0
- 4.2.0.0
- 4.2.1.0
- 4.2.2.0
- 5.0.0.0
- 6.0.0.0
- 7.0.0.0
- 8.0.0.0
- 9.0.0.0
- 10.0.0.0
- 11.0.0.0
-
-
- System
- 2.0.5.0
- 4.0.0.0
-
-
- netstandard
- 2.0.0.0
- 2.1.0.0
-
-
- System.String
-
-
- Gets the RFC 3490 compliant International Domain Name of the host, using Punycode as appropriate. This string, after being unescaped if necessary, is safe to use for DNS resolution.
- The hostname, formatted with Punycode according to the IDN standard.
-
- : Returns the host as it appears in the URI. For IPv6, includes brackets but not the zone ID.
+ - : Returns a format suitable for DNS resolution. For valid international domain names, applies punycode encoding. For IPv6, doesn't include brackets but does include the zone ID.
-## Remarks
- This property is provided for the use of lower-level networking protocols that require the domain name in Punycode form. If your code does not require that specific format, use for the hostname.
+ Which property to use depends on your scenario:
+ - Use when you need the original host string as it appears in the URI (for display or comparison).
+ - Use when you need a format suitable for DNS resolution or network APIs.
+
+ The deprecated property is dependent on *app.config* settings, which can't be changed by Windows Store applications. is provided as the preferred alternative to using because is guaranteed to always be DNS safe, no matter what the current *app.config* settings might be.
+
+## Escaping behavior
+
+ If you used an escaped string to construct this instance (for example, `"http://[fe80::200:39ff:fe36:1a2d%254]/temp/example.htm"`), then returns an escaped string. You should unescape any escaped string returned from before using that string for DNS resolution. Be aware that if you used an invalid unescaped string to construct this instance (for example, "http://[fe80::200:39ff:fe36:1a2d%4]/temp/example.htm"), then returns an unescaped string.
+
+## Examples
-IdnHost is provided as the preferred alternative to using the deprecated property, because is guaranteed to always be DNS safe.
+ The following example demonstrates the differences between and for various URI types:
- If you used an escaped string to construct this instance (for example, `"http://[fe80::200:39ff:fe36:1a2d%254]/temp/example.htm"`), then IdnHost returns an escaped string. You should unescape any escaped string returned from IdnHost before using that string for DNS resolution. Be aware that if you used an invalid unescaped string to construct this instance (for example, "http://[fe80::200:39ff:fe36:1a2d%4]/temp/example.htm"), then IdnHost returns an unescaped string.
+ :::code language="csharp" source="~/snippets/csharp/System/Uri/HostComparison/source.cs" id="SnippetHostComparison":::
]]>
From 67108dd79ccb8e495684306da2cc0b5cf02687ea Mon Sep 17 00:00:00 2001
From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com>
Date: Mon, 8 Jun 2026 15:22:07 +0000
Subject: [PATCH 2/4] Address PR review comments: change net8.0 to net6.0,
soften DNS safe guarantees
---
snippets/csharp/System/Uri/HostComparison/Project.csproj | 2 +-
xml/System/Uri.xml | 4 ++--
2 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/snippets/csharp/System/Uri/HostComparison/Project.csproj b/snippets/csharp/System/Uri/HostComparison/Project.csproj
index dd4b56868ac..a69c6ed4609 100644
--- a/snippets/csharp/System/Uri/HostComparison/Project.csproj
+++ b/snippets/csharp/System/Uri/HostComparison/Project.csproj
@@ -1,6 +1,6 @@
Exe
- net8.0
+ net6.0
diff --git a/xml/System/Uri.xml b/xml/System/Uri.xml
index 11c5b3d7c02..ef94d85abfc 100644
--- a/xml/System/Uri.xml
+++ b/xml/System/Uri.xml
@@ -1659,7 +1659,7 @@ If you used an escaped string to construct this instance (for example, `"http://
The property is a legacy property that depends on configuration settings. Use instead for consistent, configuration-independent behavior.
- The property is dependent on configuration settings in .NET Framework apps, as discussed later in this topic. The property is provided as the preferred alternative to using because is guaranteed to always be DNS safe.
+ The property is dependent on configuration settings in .NET Framework apps, as discussed later in this topic. The property is provided as the preferred alternative to using , because typically returns a value that's suitable for DNS resolution.
The property was extended in .NET Framework v3.5, 3.0 SP1, and 2.0 SP1 to provide International Resource Identifier (IRI) support based on RFC 3987. However, to ensure application compatibility with prior versions, you must specifically enable it in .NET Framework apps. To enable support for IRI, the following two changes are required:
@@ -2727,7 +2727,7 @@ The following examples show a URI and the results of calling when you need the original host string as it appears in the URI (for display or comparison).
- Use when you need a format suitable for DNS resolution or network APIs.
- The deprecated property is dependent on *app.config* settings, which can't be changed by Windows Store applications. is provided as the preferred alternative to using because is guaranteed to always be DNS safe, no matter what the current *app.config* settings might be.
+ The legacy property is dependent on *app.config* settings, which can't be changed by Windows Store applications. is provided as the preferred alternative to using because it doesn't depend on *app.config* settings, and it's designed to produce a host value that works for typical DNS resolution scenarios. Callers should still validate or normalize the returned value, especially for malformed hostnames or IPv6 addresses that include a zone ID.
## Escaping behavior
From 946ce15efb79b776416b03347da62c7258bec73c Mon Sep 17 00:00:00 2001
From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com>
Date: Mon, 8 Jun 2026 15:37:25 +0000
Subject: [PATCH 3/4] Restore HostNameType/IdnHost members, revert Linq and
vbproj, minimal Uri.xml refinements
---
.../Enumerable/AggregateBy/Enumerable.csproj | 8 +
.../System/Uri/HostComparison/Project.csproj | 2 +
.../TableAttribute/Overview/Project.vbproj | 12 ++
xml/System/Uri.xml | 199 +++++++++++-------
4 files changed, 141 insertions(+), 80 deletions(-)
create mode 100644 snippets/csharp/System.Linq/Enumerable/AggregateBy/Enumerable.csproj
create mode 100644 snippets/visualbasic/System.Data.Linq/TableAttribute/Overview/Project.vbproj
diff --git a/snippets/csharp/System.Linq/Enumerable/AggregateBy/Enumerable.csproj b/snippets/csharp/System.Linq/Enumerable/AggregateBy/Enumerable.csproj
new file mode 100644
index 00000000000..92e46ddaccf
--- /dev/null
+++ b/snippets/csharp/System.Linq/Enumerable/AggregateBy/Enumerable.csproj
@@ -0,0 +1,8 @@
+
+
+
+ Exe
+ net9.0
+
+
+
diff --git a/snippets/csharp/System/Uri/HostComparison/Project.csproj b/snippets/csharp/System/Uri/HostComparison/Project.csproj
index a69c6ed4609..8493fb5b09d 100644
--- a/snippets/csharp/System/Uri/HostComparison/Project.csproj
+++ b/snippets/csharp/System/Uri/HostComparison/Project.csproj
@@ -1,6 +1,8 @@
+
Exe
net6.0
+
diff --git a/snippets/visualbasic/System.Data.Linq/TableAttribute/Overview/Project.vbproj b/snippets/visualbasic/System.Data.Linq/TableAttribute/Overview/Project.vbproj
new file mode 100644
index 00000000000..c4963049dfd
--- /dev/null
+++ b/snippets/visualbasic/System.Data.Linq/TableAttribute/Overview/Project.vbproj
@@ -0,0 +1,12 @@
+
+
+
+ Exe
+ net48
+
+
+
+
+
+
+
diff --git a/xml/System/Uri.xml b/xml/System/Uri.xml
index ef94d85abfc..634d3bb5bb7 100644
--- a/xml/System/Uri.xml
+++ b/xml/System/Uri.xml
@@ -1648,57 +1648,9 @@ For `uriString`, an IPv6 address in string form must be enclosed within brackets
## Remarks
For IPv6 addresses, the brackets ([]) are removed and the property is set, if one was specified when this instance was constructed.
-If you used an escaped string to construct this instance (for example, `"http://[fe80::200:39ff:fe36:1a2d%254]/temp/example.htm"`), then returns an escaped string. Unescape any escaped string returned from `DnsSafeHost` before using that string for DNS resolution (see the Example). If you used an invalid unescaped string to construct this instance (for example, "http://[fe80::200:39ff:fe36:1a2d%4]/temp/example.htm"), then returns an unescaped string.
+ is a legacy property whose behavior depends on configuration settings in .NET Framework apps. For new code, prefer , which is configuration-independent and produces a value suitable for DNS resolution. See and for guidance on choosing a host property.
-## Comparison with other Host properties
-
- The class provides two main host properties:
-
- - : Returns the host as it appears in the URI. For IPv6, includes brackets but not the zone ID.
- - : Returns a format suitable for DNS resolution. For valid international domain names, applies punycode encoding. For IPv6, doesn't include brackets but does include the zone ID.
-
- The property is a legacy property that depends on configuration settings. Use instead for consistent, configuration-independent behavior.
-
- The property is dependent on configuration settings in .NET Framework apps, as discussed later in this topic. The property is provided as the preferred alternative to using , because typically returns a value that's suitable for DNS resolution.
-
- The property was extended in .NET Framework v3.5, 3.0 SP1, and 2.0 SP1 to provide International Resource Identifier (IRI) support based on RFC 3987. However, to ensure application compatibility with prior versions, you must specifically enable it in .NET Framework apps. To enable support for IRI, the following two changes are required:
-
-1. Add the following line to the *machine.config* file under the .NET Framework 2.0 directory:
-
- `\`
-
-2. Specify whether you want Internationalized Domain Name (IDN) parsing applied to the domain name and whether IRI parsing rules should be applied. This can be done in the *machine.config* or in the *app.config* file. For example, add the following:
-
- ```xml
-
-
-
-
-
-
- ```
-
- Enabling IDN converts all Unicode labels in a domain name to their Punycode equivalents. Punycode names contain only ASCII characters and always start with the xn-- prefix. The reason for this is to support existing DNS servers on the Internet, since most DNS servers only support ASCII characters (see RFC 3940).
-
- Enabling IDN only affects the value of the property.
-
- There are three possible values for IDN depending on the DNS servers that are used:
-
-- idn enabled = All
-
- This value will convert any Unicode domain names to their Punycode equivalents (IDN names).
-
-- idn enabled = AllExceptIntranet
-
- This value will convert all external Unicode domain names to use the Punycode equivalents (IDN names). In this case to handle international names on the local Intranet, the DNS servers that are used for the Intranet should support Unicode names.
-
-- idn enabled = None
-
- This value won't convert any Unicode domain names to use Punycode. This is the default value, which is consistent with the .NET Framework 2.0 behavior.
-
- Enabling IRI parsing (iriParsing enabled = `true`) normalizes and checks characters according to the IRI rules in RFC 3987. The default value is `false` and normalizes and checks characters according to RFC 2396 and RFC 2732 (for IPv6 literals).
-
- For more information on IRI support, see the Remarks section for the class.
+If you used an escaped string to construct this instance (for example, `"http://[fe80::200:39ff:fe36:1a2d%254]/temp/example.htm"`), then DnsSafeHost returns an escaped string. Unescape any escaped string returned from `DnsSafeHost` before using that string for DNS resolution (see the Example). If you used an invalid unescaped string to construct this instance (for example, "http://[fe80::200:39ff:fe36:1a2d%4]/temp/example.htm"), then DnsSafeHost returns an unescaped string.
## Examples
The following example creates a instance from a string. It illustrates the difference between the value returned from , which returns the host name or address specified in the URI, and the value returned from , which returns an address that is safe to use in DNS resolution.
@@ -1707,7 +1659,7 @@ If you used an escaped string to construct this instance (for example, `"http://
:::code language="fsharp" source="~/snippets/fsharp/System/Uri/.ctor/nclurienhancements.fs" id="Snippet4":::
:::code language="vb" source="~/snippets/visualbasic/System/Uri/.ctor/nclurienhancements.vb" id="Snippet4":::
- As explained in Remarks, unescape the host name before resolving it. You can use the method to unescape the host name, and you can resolve it by calling the method.
+ As explained in Remarks, unescape the host name before resolving it. You can use the method to unescape the host name, and you can resolve it by calling the method.
]]>
@@ -2686,24 +2638,15 @@ The following examples show a URI and the results of calling property, this property value doesn't include the port number.
+ Unlike the property, this property value does not include the port number.
- The behavior of this property depends on the host type:
+ The value returned by this property depends on the host type:
- - For **regular DNS hostnames**: Returns the escaped input. Non-ASCII characters are returned as-is without punycode encoding.
- - For **IPv6 addresses**: Returns the address with square brackets (for example, `[::1]` or `[fe80::1]`) but doesn't include the zone ID (scope) even if one was specified in the original URI.
+ - For **DNS host names** (including international domain names): Returns the escaped input. Non-ASCII characters are returned as-is and aren't punycode encoded.
+ - For **IPv6 addresses**: Returns the address enclosed in square brackets (for example, `[::1]`), but doesn't include the zone ID (scope) even if one was specified in the original URI.
- For **IPv4 addresses**: Returns the dotted-decimal notation (for example, `192.168.1.1`).
-## Comparison with IdnHost
-
- The class provides two main host properties:
-
- - : Returns the host as it appears in the URI. For IPv6, includes brackets but not the zone ID.
- - : Returns a format suitable for DNS resolution. For valid international domain names, applies punycode encoding. For IPv6, doesn't include brackets but does include the zone ID.
-
- Which property to use depends on your scenario:
- - Use when you need the original host string as it appears in the URI (for display or comparison).
- - Use when you need a format suitable for DNS resolution or network APIs.
+ For DNS resolution or other lower-level networking scenarios, use instead, which returns a punycode-encoded form for valid international domain names and includes the zone ID (without brackets) for IPv6 addresses. Use when you want the host as it appears in the URI (for example, for display or comparison).
## Examples
The following example writes the host name (`www.contoso.com`) of the server to the console.
@@ -2712,30 +2655,126 @@ The following examples show a URI and the results of calling and differ across DNS, IDN, IPv4, and IPv6 inputs:
+
+ :::code language="csharp" source="~/snippets/csharp/System/Uri/HostComparison/source.cs" id="SnippetHostComparison":::
+
+ ]]>
+
+ This instance represents a relative URI, and this property is valid only for absolute URIs.
+
+
+
+
+
+
+
+
+
+ Property
+
+ System.Runtime
+ 4.1.0.0
+ 4.2.0.0
+ 4.2.1.0
+ 4.2.2.0
+ 5.0.0.0
+ 6.0.0.0
+ 7.0.0.0
+ 8.0.0.0
+ 9.0.0.0
+ 10.0.0.0
+ 11.0.0.0
+
+
+ System
+ 1.0.5000.0
+ 2.0.0.0
+ 2.0.5.0
+ 4.0.0.0
+
+
+ netstandard
+ 2.0.0.0
+ 2.1.0.0
+
+
+ System.UriHostNameType
+
+
+ Gets the type of the host name specified in the URI.
+ A member of the enumeration.
+
+ instance and writes the to the console.
- The class provides two main host properties:
+ :::code language="csharp" source="~/snippets/csharp/System/Uri/CheckSchemeName/uriexamples.cs" id="Snippet9":::
+ :::code language="fsharp" source="~/snippets/fsharp/System/Uri/CheckSchemeName/uriexamples.fs" id="Snippet9":::
+ :::code language="vb" source="~/snippets/visualbasic/System/Uri/CheckSchemeName/uriexamples.vb" id="Snippet9":::
- - : Returns the host as it appears in the URI. For IPv6, includes brackets but not the zone ID.
- - : Returns a format suitable for DNS resolution. For valid international domain names, applies punycode encoding. For IPv6, doesn't include brackets but does include the zone ID.
+ ]]>
+
+ This instance represents a relative URI, and this property is valid only for absolute URIs.
+
+
+
+
+
+
+
+
+
+ Property
+
+ System.Runtime
+ 4.1.0.0
+ 4.2.0.0
+ 4.2.1.0
+ 4.2.2.0
+ 5.0.0.0
+ 6.0.0.0
+ 7.0.0.0
+ 8.0.0.0
+ 9.0.0.0
+ 10.0.0.0
+ 11.0.0.0
+
+
+ System
+ 2.0.5.0
+ 4.0.0.0
+
+
+ netstandard
+ 2.0.0.0
+ 2.1.0.0
+
+
+ System.String
+
+
+ Gets the RFC 3490 compliant International Domain Name of the host, using Punycode as appropriate. This string, after being unescaped if necessary, is safe to use for DNS resolution.
+ The hostname, formatted with Punycode according to the IDN standard.
+
+ for the hostname.
- Which property to use depends on your scenario:
- - Use when you need the original host string as it appears in the URI (for display or comparison).
- - Use when you need a format suitable for DNS resolution or network APIs.
+ The value returned by this property depends on the host type:
- The legacy property is dependent on *app.config* settings, which can't be changed by Windows Store applications. is provided as the preferred alternative to using because it doesn't depend on *app.config* settings, and it's designed to produce a host value that works for typical DNS resolution scenarios. Callers should still validate or normalize the returned value, especially for malformed hostnames or IPv6 addresses that include a zone ID.
+ - For **DNS host names**: For valid international domain names, non-ASCII characters are punycode encoded (for example, `münchen.de` becomes `xn--mnchen-3ya.de`). Hostnames that aren't valid IDNs might be returned as-is and include non-ASCII characters.
+ - For **IPv6 addresses**: Returns the address without the surrounding brackets, and includes the zone ID (scope) if one was specified (for example, `::1` or `fe80::1%18`).
+ - For **IPv4 addresses**: Returns the dotted-decimal notation (for example, `192.168.1.1`).
-## Escaping behavior
+ is the preferred alternative to the legacy property, because its behavior doesn't depend on *app.config* settings and it's designed to produce a value suitable for DNS resolution. Note that for IPv6 results that include a zone ID, callers may still need to strip the zone ID before passing the value to APIs that don't accept it.
- If you used an escaped string to construct this instance (for example, `"http://[fe80::200:39ff:fe36:1a2d%254]/temp/example.htm"`), then returns an escaped string. You should unescape any escaped string returned from before using that string for DNS resolution. Be aware that if you used an invalid unescaped string to construct this instance (for example, "http://[fe80::200:39ff:fe36:1a2d%4]/temp/example.htm"), then returns an unescaped string.
+ If you used an escaped string to construct this instance (for example, `"http://[fe80::200:39ff:fe36:1a2d%254]/temp/example.htm"`), then IdnHost returns an escaped string. You should unescape any escaped string returned from IdnHost before using that string for DNS resolution. Be aware that if you used an invalid unescaped string to construct this instance (for example, "http://[fe80::200:39ff:fe36:1a2d%4]/temp/example.htm"), then IdnHost returns an unescaped string.
## Examples
-
- The following example demonstrates the differences between and for various URI types:
+ The following example shows how and differ across DNS, IDN, IPv4, and IPv6 inputs:
:::code language="csharp" source="~/snippets/csharp/System/Uri/HostComparison/source.cs" id="SnippetHostComparison":::
From 3d5907961dcc29f66545557dea6bf4d1c4df7d93 Mon Sep 17 00:00:00 2001
From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com>
Date: Mon, 8 Jun 2026 16:03:01 +0000
Subject: [PATCH 4/4] Add already-encoded IDN host example to HostComparison
snippet
---
.../System/Uri/HostComparison/source.cs | 20 +++++++++++++------
1 file changed, 14 insertions(+), 6 deletions(-)
diff --git a/snippets/csharp/System/Uri/HostComparison/source.cs b/snippets/csharp/System/Uri/HostComparison/source.cs
index 38be1206f6b..7a2531aba07 100644
--- a/snippets/csharp/System/Uri/HostComparison/source.cs
+++ b/snippets/csharp/System/Uri/HostComparison/source.cs
@@ -23,24 +23,32 @@ public static void Main()
Console.WriteLine($" DnsSafeHost: {uri2.DnsSafeHost}"); // münchen.de
Console.WriteLine();
- // Example 3: IPv6 address without zone ID.
- Console.WriteLine("Example 3: IPv6 address without zone ID");
+ // Example 3: International domain name already in punycode (encoded) form.
+ Console.WriteLine("Example 3: Already-encoded international domain name");
+ Uri uri2Encoded = new Uri("http://xn--mnchen-3ya.de/path");
+ Console.WriteLine($" Host: {uri2Encoded.Host}"); // xn--mnchen-3ya.de (as provided)
+ Console.WriteLine($" IdnHost: {uri2Encoded.IdnHost}"); // xn--mnchen-3ya.de (already punycode)
+ Console.WriteLine($" DnsSafeHost: {uri2Encoded.DnsSafeHost}"); // xn--mnchen-3ya.de
+ Console.WriteLine();
+
+ // Example 4: IPv6 address without zone ID.
+ Console.WriteLine("Example 4: IPv6 address without zone ID");
Uri uri3 = new Uri("http://[::1]:8080/path");
Console.WriteLine($" Host: {uri3.Host}"); // [::1] (with brackets)
Console.WriteLine($" IdnHost: {uri3.IdnHost}"); // ::1 (without brackets)
Console.WriteLine($" DnsSafeHost: {uri3.DnsSafeHost}"); // ::1 (without brackets)
Console.WriteLine();
- // Example 4: IPv6 link-local address with zone ID.
- Console.WriteLine("Example 4: IPv6 link-local address with zone ID");
+ // Example 5: IPv6 link-local address with zone ID.
+ Console.WriteLine("Example 5: IPv6 link-local address with zone ID");
Uri uri4 = new Uri("http://[fe80::1%10]:8080/path");
Console.WriteLine($" Host: {uri4.Host}"); // [fe80::1] (with brackets, no zone ID)
Console.WriteLine($" IdnHost: {uri4.IdnHost}"); // fe80::1%10 (without brackets, with zone ID)
Console.WriteLine($" DnsSafeHost: {uri4.DnsSafeHost}"); // fe80::1%10 (without brackets, with zone ID)
Console.WriteLine();
- // Example 5: IPv4 address.
- Console.WriteLine("Example 5: IPv4 address");
+ // Example 6: IPv4 address.
+ Console.WriteLine("Example 6: IPv4 address");
Uri uri5 = new Uri("http://192.168.1.1:8080/path");
Console.WriteLine($" Host: {uri5.Host}"); // 192.168.1.1
Console.WriteLine($" IdnHost: {uri5.IdnHost}"); // 192.168.1.1