и поэтому нельзя создать экземпляры этих классов. Они существуют как базовые классы для предоставления общей функциональности для работы с запросами и ответами Web независимо от протокола, используемого в данной операции. Любой такой запрос всегда делается с помощью определенного протокола (HTTP, Telnet, FTP, SMTP и т. д.) и выполняется с помощью производного класса для этого протокола. В предыдущем коде, хотя ссылочные переменные были определены как ссылки на базовый класс, метод WebRequest.Create()
в действительности давал объект HttpWebRequest
, а метод GetResponse()
возвращал объект HttpWebResponse тоже в действительности. Почему же этого не видно в коде явно? Ответ заключается в том, что компания Microsoft предоставила механизм на основе фабрики для сокрытия деталей иерархии классов от клиентского кода. Тот факт, что требуется объект, который может иметь дело с протоколом HTTP, очевиден из URI, подставляющего в WebRequest.Create()
: http://www.wrox.com
. WebRequest.Create()
проверяет в URI спецификатор протокола и использует это для создания экземпляра и возврата объекта соответствующего класса. Цель состоит в том, чтобы никогда не использовать конструктор для создания экземпляра объекта WebRequest; таким образом появляется в некоторой степени свобода от необходимости что-либо знать о производных классах. Следует заметить, что теория немного отказывает, если нужно использовать какие-то специальные свойства используемого протокола, которые реализованы как методы производного класса, и в этом случае необходимо выполнить преобразование типа ссылки WebRequest
или WebResponse
в производный класс.
Теоретически с помощью этой архитектуры можно обрабатывать отправку запросов с помощью любого из распространенных протоколов. Однако компания Microsoft в действительности написала производные классы, охватывающие протоколы HTTP и file://
. Если желательно иметь дело с другими протоколами, например, FTP, Telnet или SMTP, то нужно либо воспользоваться API Windows и написать свои собственные классы (которые будут внутренне реализованы с помощью Windows API), или ждать, пока независимые поставщики программного обеспечения напишут подходящие классы .NET.
Служебные классы
В этом разделе будет представлена пара служебных классов, которые могут облегчить программирование Web при работе с двумя распространенными темами Интернета — URI и адреса IP.
URI
Uri
и UriBuilder
являются двумя классами в пространстве имен System
(подчеркнем, что не System.Net
) и оба предназначены для представления Uri
. Различие между ними состоит в том, что UriBuilder
создает URI по заданным строкам для его компонентов, в то время как Uri
выполняет синтаксический разбор всего URI.
Поскольку класс Uri
предназначен скорее для разбиения, а не для создания Uri
, он требует полной строки URI, чтобы ее создать.
Uri MSPage =
new Uri('http://www.Microsoft.com/SomeFolder/SomeFile.htm?Order=- true');
Класс представляет большое число свойств, которые предназначены только для чтения. В объекте Uri
не предусмотрены изменения после того, как он был создан.
string Query = MSPage.Query; // Order = true
string AbsolutePath = MSPage.AbsolutePath; // SomeFolder/SomeFile.htm
string Schema = MSPage.Schema; // http
int Port = MSPage.Port; // 80 (по умолчанию для http)
string AbsolutePath = MSPage.AbsolutePath; // SomeFolder/SomeFile.htm
string Host = MSPage.Host; // www.Microsoft.com
bool IsDefaultPort = MSPage.IsDefaultPort; // true, так как
// 80 — значение по умолчанию
UriBuilder
, с другой стороны, реализует меньше свойств: лишь столько, чтобы построить полный URI. Однако эти свойства предназначены для чтения-записи. Можно задать компоненты для создания URI с помощью конструктора:
Uri MSPage =
new UriBuilder('http', 'www.Microsoft.com', 80,
'SomeFolder/SomeFile.htm', 'Order=true');
Или присвоить значения свойствам.
UriBuilder MSPage = new UriBuilder();
MSPage.Schema = 'http';
MSPage.Host = 'www.Microsoft.com';
MSPage.Port = 80;
MSPage.Path = 'SomeFolder/SomeFile.htm';
MSPage.Query = 'Order=true';
После завершения инициализации UriBuilder
получается соответствующий объект Uri
со свойством Uri
.
Uri CompletedUri = MSPage.Uri;
Пример вывода страницы
Мы проиллюстрируем использование UriBuilder
вместе с созданием процесса Internet Explorer на примере DisplayPage
. Этот пример позволяет пользователю ввести компоненты URL. Отметим, что имеется в виду URL, а не URI, так как предполагается, что это запрос HTTP. Пользователь сможет затем щелкнуть на кнопке ViewPage, и приложение выведет весь URL в текстовом поле, а также страницу с помощью элемента управления ActiveX WebBrowser
.
Этот пример, будучи стандартным приложением Windows на C#, выглядит так:

Текстовые поля названы соответственно textBoxServer
, textBoxPath
, textBoxPort
и textBoxURI
. Добавленный код примера полностью находится в обработчике событий кнопки ViewPage
:
private void OnClickViewPage(object sender, System.EventArgs e) {
UriBuilder Address = new UriBuilder();
Address.Host = textBoxServer.Text;
Address.Port = int.Parse(textBoxPort.Text);
Address.Scheme = Uri.UriSchemeHttp;
Address.Path = textBoxFile.Text;
Uri AddressUri = Address.Uri;
Process myProcess = new Process();
myProcess.StartInfo.FileName = 'iexplorer.exe';