LWP与WEB的基本使用.docx

上传人:b****5 文档编号:11631510 上传时间:2023-03-29 格式:DOCX 页数:15 大小:45.19KB
下载 相关 举报
LWP与WEB的基本使用.docx_第1页
第1页 / 共15页
LWP与WEB的基本使用.docx_第2页
第2页 / 共15页
LWP与WEB的基本使用.docx_第3页
第3页 / 共15页
LWP与WEB的基本使用.docx_第4页
第4页 / 共15页
LWP与WEB的基本使用.docx_第5页
第5页 / 共15页
点击查看更多>>
下载资源
资源描述

LWP与WEB的基本使用.docx

《LWP与WEB的基本使用.docx》由会员分享,可在线阅读,更多相关《LWP与WEB的基本使用.docx(15页珍藏版)》请在冰豆网上搜索。

LWP与WEB的基本使用.docx

LWP与WEB的基本使用

LWP与WEB的基本使用

简介

LWP(“LibraryforWWWinPerl”的缩写)是一个由多个模块组成,用来获取网络数据的的模块组。

和很多Perl的模块一样。

每一个LWP模块都自带详细的文档,做为对这个模块的完整介绍。

可是面对LWP里的众多模块,有时候即使是完成最简单的工作,新手们也常常不知道从那里开始。

要对LWP做全面的介绍需要一整本书,很幸运,Perl&LWP已经出版。

而这篇文章向你介绍了最常见的LWP用法。

使用LWP:

:

Simple获取网页

如果只是要拿到某个网页,那使用LWP:

:

Simple里的函数是最简单的。

通过调用get($url)函数,就可以得到相关网址的内容。

如果没有发生错误,get函数返回此网页,否则,返回undef。

例子如下:

my$url='http:

//freshair.npr.org/dayFA.cfm?

todayDate=current'

useLWP:

:

Simple;

my$content=get$url;

die"Couldn'tget$url"unlessdefined$content;

#$content里是网页内容,下面是对此内容作些分析:

if($content=~m/jazz/i){

print"They'retalkingaboutjazztodayonFreshAir!

\n";

}else{

print"FreshAirisapparentlyjazzlesstoday.\n";

}

如果要在命令行里运行,getprint函数非常方便。

如果没有发生错误,它会把网页内容输出到STDOUT,否则将会有错误信息输出到STDERR。

例如:

%perl-MLWP:

:

Simple-e"getprint'http:

//cpan.org/RECENT'"

上面的网址指向一个文本文件,列有最近两个星期内CPAN更新过的文件。

如果想要知道Acme:

:

的模块是否有更新,有就email自己,你可以把它和Shell结合到一起来实现。

如下:

%perl-MLWP:

:

Simple-e"getprint'http:

//cpan.org/RECENT'"|grep"/by-module/Acme"|mail-s"NewAcmemodules!

Joy!

"$USER

LWP:

:

Simple还有一些非常有用的函数,包括一个运行HEAD请求的函数,用来检查链接是否有效,网页是否更新。

另外两个用来保存和镜像网址的函数也值得一提。

具体请看LWP:

:

Simple的文档或Perl&LWP的第二章.

LWPClass模型基础

LWP:

:

Simple在做简单的工作时很方便。

但因为不支持cookies,用户认证,对HTTPrequestheader(请求标头)的编辑,和HTTPresonseheader(响应标头)的读写(主要是HTTP的errormessage)。

因此,当需要这些特性的时候,就要使用LWPClass模型。

在众多的LWPClass里,LWP:

:

UserAgent和HTTP:

:

Response是必须理解的。

LWP:

:

UserAgent就像一个虚拟浏览器用来作request(请求)。

HTTP:

:

Response用来储存request(请求)生成的response(响应)。

最基本的用法是$response=$browser->get($url),或写的更完整些:

#程序开始:

useLWP5.64;#载入较新版本的LWPclasses

my$browser=LWP:

:

UserAgent->new;

...

#getrequest:

my$url='http:

//freshair.npr.org/dayFA.cfm?

todayDate=current';

my$response=$browser->get($url);

die"Can'tget$url--",$response->status_line

unless$response->is_success;

die"Hey,我想要HTML格式而不是",$response->content_type

unless$response->content_typeeq'text/html';

#或者任何其他的content-type

#成功的话就对内容处理

if($response->content=~m/jazz/i){

print"FreshAir今天在讨论爵士乐!

\n";

}else{

print"FreshAir今天讨论的和爵士乐一点边都不沾.\n";

}

上面有两个相关的object:

$browser,是LWP:

:

UserAgent的一个object。

$response是属于HTTP:

:

Response类的一个object。

一个程序里只需要一个$browserobject,但是每次发出一个request,就会得到一个新的HTTP:

:

Responseobject。

HTTP:

:

Responseobject有以下一些有价值的属性:

∙一个statuscode(状态代码值),表示成功或失败。

你可以使用$response->is_success来检测它。

∙httpstatusline(http状态描述),观察$response->status_line的结果(比如“404NotFound”)会帮助你理解这个词的意思。

∙MIMEcontent-type(文件类型)通过$response->content_type来获得。

例如“text/html”,”image/gif”,”application/xml”等等。

∙contentoftheresponse(响应返回的内容)储存在$response->content。

内容可能是html格式。

如果是GIF格式,$response->content里是二进制的GIF数据。

∙许多其他methods都可以在HTTP:

:

Response和它的superclasses(父class)HTTP:

:

Message和HTTP:

:

Headers里找到。

添加其他HTTP请求headers

request(请求)常用的方法是$response=$browser->get($url),但如果需要,你可以在$url后跟一个键值的列表来给你的request加上其他HTTPheaders。

象这样:

$response=$browser->get($url,$key1,$value1,$key2,$value2,...);

举个例子,如果你要对一个只允许Netscape浏览器连入的网站发出请求,那就需要发出类似Netscape的header,如下:

my@ns_headers=(

'User-Agent'=>'Mozilla/4.76[en](Win98;U)',

'Accept'=>'image/gif,image/x-xbitmap,image/jpeg,

image/pjpeg,image/png,*/*',

'Accept-Charset'=>'iso-8859-1,*,utf-8',

'Accept-Language'=>'en-US',

);

...

$response=$browser->get($url,@ns_headers);

如果不打算重复使用这个array,你可以把它写到get函数里

$response=$browser->get($url,

'User-Agent'=>'Mozilla/4.76[en](Win98;U)',

'Accept'=>'image/gif,image/x-xbitmap,image/jpeg,

image/pjpeg,image/png,*/*',

'Accept-Charset'=>'iso-8859-1,*,utf-8',

'Accept-Language'=>'en-US',

);

如果只是打算修改User-Agent,可以通过LWP:

:

UserAgent的agent方法把缺省的agent‘libwww-perl/5.65’(或者别的)改掉。

$browser->agent('Mozilla/4.76[en](Win98;U)');

使用cookies

默认的LWP:

:

UserAgent对象像一个不支持cookies的浏览器一样工作。

有不只一种的办法可以设定它的cookie_jar属性,从而让它支持cookies。

“cookiejar”是一个用来储存HTTPcookie的容器。

你可以把它存到硬盘(像Netscape使用cookies.txt一样)或内存里。

存到内存里的cookies会在程序完成后消失。

内存式的cookie使用方法:

$browser->cookie_jar({});

也可以把cookie储存到硬盘的文件里:

useHTTP:

:

Cookies;

$browser->cookie_jar(HTTP:

:

Cookies->new(

'file'=>'/some/where/cookies.lwp',

#储存cookies的地址

'autosave'=>1,

#当完成后自动储存到硬盘里

));

文件里的cookie是以LWP自定的格式储存,如果你想在netscape里使用这个cookie文件,可以使用HTTP:

:

Cookies:

:

Netscapeclass:

useHTTP:

:

Cookies;

#yes,loadsHTTP:

:

Cookies:

:

Netscapetoo

$browser->cookie_jar(HTTP:

:

Cookies:

:

Netscape->new(

'file'=>'c:

/ProgramFiles/Netscape/Users/DIR-NAME-HERE/cookies.txt',

#wheretoreadcookies

));

你也可以象上面一样使用‘autosave’=>1。

但Netscape的cookie有时会在写入硬盘之前就被丢掉,至少在写这篇文章的时候还是这样。

通过POST提交表格

大部分HTML表格使用HTMLPOST向服务器提交数据,在这里你可以这样:

$response=$browser->post($url,

[

formkey1=>value1,

formkey2=>value2,

...

],

);

或者你也可以把HTTPheader也一起发出

$response=$browser->post($url,

[

formkey1=>value1,

formkey2=>value2,

...

],

headerkey1=>value1,

headerkey2=>value2,

);

下一个例子向AltaVista的搜索引擎发送HTTPPOST请求,然后从HTML里提取出符合匹配的总数。

usestrict;

usewarnings;

useLWP5.64;

my$browser=LWP:

:

UserAgent->new;

my$word='tarragon';

my$url='

my$response=$browser->post($url,

['q'=>$word,#theAltavistaquerystring

'pg'=>'q','avkw'=>'tgz','kl'=>'XX',

]

);

die"$urlerror:

",$response->status_line

unless$response->is_success;

die"Weirdcontenttypeat$url--",$response->content_type

unless$response->content_typeeq'text/html';

if($response->content=~m{AltaVistafound([0-9,]+)results}){

#从"AltaVistafound2,345results"里匹配出结果

print"$word:

\n";

}else{

print"Couldn'tfindthematch-stringintheresponse\n";

}

通过GET提交表格

一些HTML表格不使用POST请求,而是使用GET请求来传输数据。

例如,在里检索电影名字‘BladeRunner’,提交后在浏览器的网址栏里将显示:

下面是使用LWP实现同样的结果:

useURI;

my$url=URI->new(');

#makesanobjectrepresentingtheURL

$url->query_form(#Andheretheformdatapairs:

'title'=>'BladeRunner',

'restrict'=>'MoviesandTV',

);

my$response=$browser->get($url);

第5章详细描述了HTML表格和表格数据,第6章到第9章描述了怎样从获得的HTML数据里提取出有用的信息。

URL处理

上面提到的URIclass提供很多获取和修改URL的方法。

例如如果想要知道url是什么类型(http,ftp等等)可以使用$url->schema来得到,如果要提取网址里的主机名,可以使用$url->host。

不过,可能最有用的是我前面提到的query_form方法,以及把相对网址路径(如”../foo.html”)转换成绝对路径(如”

useURI;

$abs=URI->new_abs($maybe_relative,$base);

现在回忆一下获取最新CPAN模块的那个例子。

usestrict;

usewarnings;

useLWP5.64;

my$browser=LWP:

:

UserAgent->new;

my$url='http:

//www.cpan.org/RECENT.html';

my$response=$browser->get($url);

die"Can'tget$url--",$response->status_line

unless$response->is_success;

my$html=$response->content;

while($html=~m/chunk86920392chunklt;AHREF=\"(.*?

)\"/g){

print"\n";

}

输出的结果是

MIRRORING.FROM

RECENT

RECENT.html

authors/00whois.html

authors/01mailrc.txt.gz

authors/id/A/AA/AASSAD/CHECKSUMS

...

你可以使用URI模块的new_abs方法来得到完全网址路径,修改while循环:

while($html=~m/

)\"/g){

printURI->new_abs(,$response->base),"\n";

}

$response->base方法可以在HTTP:

:

Message里找到。

它返回的URL通常被用来和相对路径合并来得到完全路径。

现在得到的结果是

http:

//www.cpan.org/MIRRORING.FROM

http:

//www.cpan.org/RECENT

http:

//www.cpan.org/RECENT.html

http:

//www.cpan.org/authors/00whois.html

http:

//www.cpan.org/authors/01mailrc.txt.gz

http:

//www.cpan.org/authors/id/A/AA/AASSAD/CHECKSUMS

...

请参考Perl&LWP的第四章,以得到对URIobjects更详细的描述。

当然,使用regexp(正则表达式)来匹配url相对简单,如果情况复杂,需要更强大的匹配工具,可以考虑HTML分析模块HTML:

:

LinkExtor或HTML:

:

TokeParser,甚至HTML:

:

TreeBuilder

其他浏览器属性

LWP:

:

UserAgentobjects有几个值得注意的属性:

∙$browser->timeout(15):

设定缺省request的timeout时间.超过这个时间就放弃请求。

∙$browser->protocols_allowed([‘http’,‘gopher’]):

这用来设定只接受http和gopher协议。

连接其他协议时就返回500错误值,”AccesstoftpURIshasbeendisabled”的错误消息。

∙useLWP:

:

ConnCache;$browser->conn_cache(LWP:

:

ConnCache->new()):

这告诉browserobject使用HTTP/1.1“keep-Alive”特性,即重复使用先前的socket来加快请求速度。

∙$browser->agent(‘SomeName/1.23(moreinfoheremaybe)’):

设置HTTP请求的User-Agent。

LWP缺省使用“libwww-perl/versionnumber”作为User-Agent,比如“libwww-perl/5.65”。

你可以加上更多的信息:

∙$browser->agent(‘SomeName/3.14(contact@robotplexus.int)’);

或者可以伪装为

$browser->agent(‘Mozilla/4.0(compatible;MSIE5.12;Mac_PowerPC)’);

∙push@{$ua->requests_redirectable},‘POST’:

告诉LWP在POST请求发送后如果发生重新定向就自动跟随(虽然RFC里不要求这么做)

详细请参见LWP:

:

UserAgent文档.

写一个有礼貌的机器人

如果想遵循robots.txt和避免在较短的时间发出太多的请求,你可以采用LWP:

:

RobotUA而不是LWP:

:

UserAgent。

LWP:

:

RobotUA用法与LWP:

:

UserAgent一样:

useLWP:

:

RobotUA;

my$browser=LWP:

:

RobotUA->new(

'YourSuperBot/1.34','you@');

#机器人名字和email地址

my$response=$browser->get($url);

HTTP:

:

RobotUA多了几个特性:

∙如果$url请求的服务器的robots.txt禁止了你对$url的访问,那么$browser就不会发出对于这个地址的请求,而是返回403代码和一个错误信息“Forbiddenbyrobots.txt”。

∙die"$url--",$response->status_line,"\nAborted"

∙unless$response->is_success;

然后你会得到这样的错误信息:

http:

//whatever.site.int/pith/x.html--403Forbidden

byrobots.txt

Abortedatwhateverprogram.plline1234

∙如果$browser发现请求的地址是刚刚请求过的,就会暂停(sleep)来避免发送太多的请求。

缺省暂停1分钟,但可以通过$browser->delay(minutes)来设定。

比如:

∙$browser->delay(7/60);

详细请参见LWP:

:

RobotUA文档.

使用代理

有时你希望(或者是必须)通过代理来连接某些站点或协议,就比如你的LWP程序是运行在某台处于防火墙之内的机器上。

代理通常储存在环境变量HTTP_PROXY里。

LWP可以通过user-agentobject里的env_proxy函数把环境变量里的代理地址装载。

useLWP:

:

UserAgent;

my$browser=LWP:

:

UserAgent->new;

#Andbeforeyougomakinganyrequests:

$browser->env_proxy;

详细请参照LWP:

:

UserAgent文档里的proxy,env_proxy和no_proxy方法.

HTTP认证

许多网站都是通过HTTP认证来限制连接.当用户请求一个限制页面时,HTTP服务器回复“Thatdocumentispartofaprotected‘realm’andyoucanaccessitonlyifyoure-requestitandaddsomespecialauthorizationheaderstoyourrequest”.(你现在请求了一个限制区域,如果你需要重新发送一个带有认证信息的header才可以连入.)

Unicode.org的管理员为了防止机器人访问邮件组获取发信人地址,

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 高中教育 > 其它课程

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1