Анимация
JavaScript


Главная  Библионтека 

0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 [ 97 ] 98 99 100 101 102 103

Мы назовем нашу программу webget. Вот как ее можно было бы выполнить:

shell prompt$ webget www.perl.com /guanaco.html

HTTP/1.1 404 File Not Found

Date: Thu, 08 May 1997 18:02:32 GMT

Server: Apache/1.2b6

Connection: close

Content-type: text/html

<HEAD><TITLE>404 File Not Found</TITLE></HEAD> <BODY><Hl>File Not Found </Hl>

The request URL /guanaco.html was not found on this server. <P> </BODY>

Это, конечно, не очень интересно, потому что программа не нашла конкретный документ, однако длинный ответ не поместился бы на этой странице.

Чтобы ознакомиться с более развитой версией данной программы, вам нужно найти программу Iwp-request, входящую в состав модулей LWP из CPAN. (LWP мы вкратце рассмотрели в конце главы 19.)

Интерактивный клиент

Создать программу-клиент, которая просто читает все с сервера или посылает одну команду, получает один ответ, а затем завершает свою работу, очень легко. А как насчет создания чего-нибудь полностью интерактивного, вроде telnet? Мы имеем в виду приложение, которое позволяло бы вам набрать строку, получить ответ, набрать еще одну строку, вновь получить ответ и т.д. (В принципе, telnet обычно работает в символьном, а не в строковом режиме, но идею вы поняли.)

Этот клиент - более сложный, чем те два, с которыми мы имели дело до сих пор, но если вы работаете в системе, которая поддерживает мощный вызов fork, решение получится не слишком сложным. Установив соединение с тем сервисом, с которым вы хотите пообщаться, клонируйте свой процесс вызовом fork. Каждый из созданных идентичных процессов должен выполнить очень простое задание: родительский копирует все из гнезда на стандартный вывод, а порожденный одновременно копирует все со стандартного ввода в гнездо. Реализовать это с помощью только одного процесса было бы гораздо труднее, потому что легче написать два процесса для выполнения одной задачи, чем один процесс - для выполнения двух задач*.

Вот наш код:

# /usr/bin/perl -W use strict; use 10::Socket;

Принцип сохранения простоты - один из краеугольных камней не только философии UNIX, но и высококачественного проектирования программного обеспечения Наверное, именно поэтому он распространился и на другие системы



my {$host, $port, $kidpid, $handle, $line); unless (@ARGV == 2 ) i die "usage: $0 host port" ) ($host, $port) = eARGV;

# создать tcp-соединение с указанным хостом и портом $handle = 10::Socket::INET->new(Proto => "tcp",

PeerAddr => $host, PeerPort => $port)

or die "cant connect to port $port on $host: $"; $handle->autoflush(1); # и результат сразу же попадает туда print STDERR "[Connected to $host:$port]\n";

# разбить программу на два процесса-близнеца

die "cant fork: 5" unless def med {$kidpid = fork());

# блок if{} выполняется только в родительском процессе if{$kidpid) (

# копировать данные из гнезда на стандартный вывод while (defined ($line = <$handle> )) { print STDOUT $line; )

kill ("TERM",$kidpid); # послать в порожденный процесс сигнал SIGTERM

# блок else)) выполняется только в порожденном процессе else {

# копировать данные со стандартного ввода в гнездо while (defined ($line = <STDIN>)) ( print $handle $line; }

Функция kill в блоке if родительского процесса пошлет сигнал в наш порожденный процесс (в текуший момент работающий в блоке else), как только удаленный сервер закроет свою сторону соединения.

Что еще почитать о сетях

о сетях можно говорить и говорить, но мы дадим ссылки на источники, которые помогут вам перейти от разговоров к делу. В главе 6 книги Programming Perl и на тап-странице perlipc(l) описано межпроцессное взаимодействие в общем; на тап-странице IO::Socket(3) - объектная библиотека; на тап-странице Socket(3) - низкоуровневый интерфейс к гнездам. Более опытным программистам рекомендуем книгу Unix Network Programming (by Richard Stevens, Addison-Wesley), в которой очень хорошо освещены все вопросы данной темы. Будьте, однако, осторожны: большинство книг по программированию гнезд написаны С-программистами.



ТемЫу которых мы не коснулись

Как ни странно, даже при таком объеме книги некоторые вопросы все равно остались незатронутыми. Данное приложение содержит полезную дополнительную информацию.

Назначение этого раздела - не обучить вас тем вещам, которые перечислены здесь, а просто дать их перечень. За дальнейшей информацией обращайтесь к книге Programming Perl, на man-страницы perl(l) и perlfaq{\), к HTML-документам, имеющимся в каталоге doc архива CPAN, и к материалам телеконференций Usenet.

Полное межпроцессное взаимодействие

Да, Perl может оказать значительную помощь в создании сети. Кроме потоковых портов TCP/IP, которые мы рассматривали в приложении В, Perl поддерживает также (если ваша система готова к этому) доменные порты UNIX, передачу сообщений по протоколу UDP, совместно используемую память, семафоры, именованные и неименованные каналы и обработку сигналов. Стандартные модули перечислены в главе 6 книги Programming Perl и на тап-странице perlipc(l), а модули разработки третьих фирм - в разделе каталога модулей CPAN, посвященном сетям.

Да, на основе Perl можно организовать сетевой обмен с использованием портов TCP/IP, доменных портов UNIX и обеспечить работу совместно используемой памяти и семафоров в системах, которые поддерживают эти возможности. Дальнейшие сведения см. на тап-странице регНрс{\).



0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 [ 97 ] 98 99 100 101 102 103