Создание сетевого приложения - работа с сокетами (sockets)

Программирование

Метки : , , , , , , ,

0_networkДанный пример представляет собой введение в программирование на Builder C++ сетевых приложений при помощи стандартных компонентов. Для этого мы напишем два простейших приложения - клиент и сервер, которые будут взаимодействовать друг с другом по сети.

Начнем с теории, чтобы понять описание компонентов для работы с сокетами нам необходимо познакомиться с терминологией Интернета вообще и сокетов в частности. Основой сетевого взаимодействия является протокол TCP/IP, Transmission Control Protocol/Internet Protocol (протокол управления передачей/Интернет-протокол), который обеспечивает соединение через сеть. При этом IP отвечает за определение и маршрутизацию датаграмм (datagram), модулей передачи через сеть и схемы адресации. TCP отвечает за высокоуровневые службы доставки.
Если в вашем распоряжении имеется локальная сеть, вы сможете протестировать в ней наши дальнейшие программы, в ином случае можно просто использовать один компьютер в качестве и клиента, и сервера. В этом случае, как я сделал в примере, адрес 127.0.0.1 (или адрес локального хоста, localhost) всегда является адресом текущего компьютера.
IP-адрес — это 32-разрядное число, обычно представленное в виде четырех компонентов (называемых октетами), разделенных точками, при этом первый октет определяет класс сети.
Каждое TCP-соединение работает через порт (port), представляемый в виде 16-разрядного числа. IP-адрес и порт TCP вместе определяют сокет (socket). Различные процессы, выполняющиеся на одном компьютере, не могут использовать один и тот же сокет (т.е. один и тот же порт).
Некоторые порты TCP зарезервированы для стандартного использования конкретными протоколами высокого уровня и службами. Другими словами, следует использовать эти номера портов при реализации этих служб и избегать их использования во всех остальных случаях.

Протокол Порт
HTTP (Hypertext Transfer Protocol) 80
FTP (File Transfer Protocol) 21
SMTP (Simple Mail Transfer Protocol) 25
POP3 (Post Office Protocol, version 3) 110
Telnet 23

В файле C:\WINDOWS\system32\drivers\etc\services перечислены стандартные порты, используемые службами. Сокеты клиентов всегда указывают номер порта или имя службы сокета сервера, с которым им требуется установить соединение.
Протокол — это набор правил для клиента и сервера, определяющий коммуникационный поток. Низкоуровневые протоколы Интернета, такие как TCP/IP, обычно реализуются операционной системой. Однако термин «протокол» также применяется и для высокоуровневых стандартных протоколов Интернета (таких как HTTP, FTP или SMTP). Прикладные протоколы расположены на более высоком уровне, чем протоколы передачи, поскольку они абстрагированы от транспортного механизма, предоставляемого TCP/IP. Это делает протоколы независимыми не только от операционной системы и аппаратного обеспечения, но также и от физической структуры сети.

Как начать коммуникации через сокет? Сначала начинает работать программа-сервер, но она просто ожидает запроса от клиента. Программа-клиент запрашивает соединение у сервера, с которым ей требуется установить соединение. Когда клиент отправляет запрос, сервер может принять соединение, открыв специальный сокет на стороне сервера, который образует соединение с сокетом на стороне клиента.
Для поддержки этой модели существуют три типа сокетных соединений:

  • клиентские соединения инициируются клиентом и связывают локальный сокет клиента с удаленным сокетом сервера. Клиентские сокеты должны описывать сервер, с которым им требуется установить соединение, предоставив либо имя узла, либо IP-адрес и его порт;
  • слушающие соединения (listening connections) — это пассивные серверные сокеты, ожидающие клиента. Как только клиент делает новый запрос, сервер активизирует новый сокет, выделенный для этого конкретного соединения, и затем возвращается к слушанию. Слушающие серверные сокеты должны указывать порт, представляющий реализуемую ими службу (фактически клиент собирается подключаться через этот порт);
  • серверные соединения — это соединения, активизируемые серверами, поскольку они принимают запрос от клиента.
    Различные типы соединений имеют значение только для установления канала от клиента к серверу. После того как канал связи установлен, обе стороны могут обмениваться данными и запросами друг с другом в произвольном порядке.

При работе с сокетами в Windows возможны несколько подходов. Чтение данных из сокета или запись в него могут осуществляться асинхронно, поэтому это не блокирует выполнение другого кода в вашем сетевом приложении. Такое соединение называется неблокирующим (nonblocking connection). Неблокирующие соединения производят чтение и запись асинхронно. При работе, например, с компонентами ClientSocket и ServerSocket, система генерирует на клиенте события OnRead или OnWrite, а события OnClientRead или OnClientWrite серверов информируют сокет в тот момент, когда другая сторона соединения пытается прочитать или записать данные.
Альтернатива асинхронному подходу — блокирующие соединения, при которых ваше приложение ожидает завершения операций чтения или записи перед выполнением следующей строки кода. В этом случае следует согласованно писать код для обеих сторон, поскольку иначе не будут генерироваться события. При работе с блокирующим соединением необходимо создать на сервере поток и, как правило, работать с потоком также и на стороне клиента.

Перейдем к практике.
Для работы с сокетами в поставку Builder входят наборы сокетных компонентов, при помощи которых можно читать и записывать информацию поверх соединения TCP/IP. На странице Internet палитры компонентов расположены компоненты ClientSocket и ServerSocket, а также новые компоненты TcpClient и TcpServer.
Для использования сокетного компонента необходимо предоставить хост и службу. На стороне сервера хост представляет собой адрес текущего компьютера, на стороне клиента вы можете указать либо имя домена, либо IP-адрес.
Начнем с написания серверной части. Для этого на форму вынесем поле Memo1 и компонент ServerSocket.

01-serverform

Активацию серверного сокета будем производить при запуске формы, для этого в событии Activate пишем код:

02-form_activ

Таким образом, мы задали свой порт сервера (5555) и активировали сокет. Для обработки событий, возникающих при работе сокета, обратимся к испектору объектов.

03-socket_events

В данном примере мы воспользуемся простейшими событиями сокета:

  • OnClientConnect - возникает при подключении клиента
  • OnClientDisconnect - соответственно, возникает при завершении работы с клиентом
  • OnClientRead - возникает при приеме данных от клиента

Код для каждого из этих событий может выглядеть примерно так:

04-server_code

Обратите внимание, что при приеме данных от клиента они считываются функцией ReceiveText(), после которой идет отправка сообщения “ОК” клиенту, чтобы тот был к курсе доставки сообщения. Также не забываем отключить сокет при завершении работы сервера (в FormClose) ServerSocket1->Active=false;
На этом создание простейшего сервера завершено, переходим к клиенту.
Вынесем на форму поле Edit1 и 3 кнопки - для соединения/отключения и передачи данных, а также сам ClientSocket.

05_client_form

Компонент ClientSocket для адресации использует два различных свойства (Host и Address), а служба указывается в свойстве Port или Service. В данном примере запуск и клиента и сервера будет происходить на одной машине, поэтому в качестве адреса сервера вставляем localhost (127.0.0.1) и указываем 5555 порт сервера.

06_client_connect

Настройки сокета и его активация производятся при нажатии кнопки “Соединение“. Для кнопок “Передача” и “Разъединение” используется код:

07_client_send

При этом функцией SendText() от клиента на сервер передается содержимое поля ввода Edit1.
Для проверки доставки воспользуемся событием ClientSocket1Read, которое возникает при получении данных клиентским сокетом. Принимаемое от сервера сообщение “ОК” с помощью функции ReceiveText() помещается обратно в Edit1.

08_client_ok

Программа готова, запускаем сервер и клиент, наблюдаем корректный процесс работы (если есть межсетевой экран, включаем разрешение для клиента)

09_work

Развивая тему программирования сокетов, нельзя не отметить, что если программа должна иметь минимальный размер и ее код не должен сильно зависеть от языка, то необходимо пользоваться не стандартными компонентами, а специальными API-функциями для работы с сетью. В среде Windows есть отдельный раздел таких функций - WINSOCKETS API. Такой вариант работы с сетью мы рассмотрим в одной из следующих статей.

Пожалуйста оцените статью:
Загрузка ... Загрузка ...


Похожие статьи:

Сокеты через WINSOCKET API
В предыдущем примере мы рассмотрели написание сетевого...
Описание CryptoAPI
Более подробно рассмотрены структура, состав и базовые...

Комментарии:

Оставить комментарий

Материал используется исключительно в некоммерческих целях.
Все права на публикуемые графические, текстовые, аудио и видео материалы принадлежат их владельцам, при цитировании или копипасте прошу оставлять ссылку на оригинал.
Я искренне надеюсь на вашу заинтересованность в посещении этого сайта. Спасибо за внимание!