2014年12月9日星期二

[PerlChina] 关于OTRS开发

大家好!
我们这里有专业做OTRS开发或服务的吗?

--
您收到此邮件是因为您订阅了 Google 网上论坛的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要向此群组发帖,请发送电子邮件至 perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问 https://groups.google.com/d/optout。

Re: [PerlChina] PerlChina Advent 09: Webqq::Client

鹅厂应该是关闭webqq保留smartqq吧?完全放弃网页版不现实啊,连微信都有网页版。

在 2014年12月9日 下午10:31,arrow.wang@gmail.com <arrow.wang@gmail.com>写道:
讚!但是聽說 webqq近期要關閉,不知道還能用多長時間。

==============================================
9月30日消息,近日登录腾讯WebQQ的用户会看到"WebQQ告别会 相聚有时 后会无期"的公告页面。预示着WebQQ即将停止服务,但公 告页面并没有给出停止服务的具体时间,目前WebQQ及SmartQQ也仍然能正常使用。

据了解,WebQQ于2009年9月15日正式上线,是腾讯公司推出的使用网页方式上QQ的服务,特点是无需下载和安装QQ软件,只要能打 开 WebQQ的网站就可以登录QQ与好友保持联系。具有Web产品固有的便利性,同时在Web上最大限度的保持了客户端软件的操作习惯。去年9 月,WebQQ更名为SmartQQ全新发布,但仍保留了原WebQQ版本。

此外,腾讯"我的QQ中心"的"好友"功能已于2014年7月15日停止服务。据悉,此次WebQQ是继此之后的又一业务调整。



On 2014年12月09日 21:02, chenlin rao wrote:
=encoding utf8

=for advent_year 2014

=for advent_title Webqq::Client模块介绍

=for advent_author Perfi Wang


=head2 Webqq::Client 背景来源

最早的时候,加入了一个Python的群,看到群里有个QQ机器人可以自动帮大家查询天气

群里贴出来的url会自动去获取下html的 <title> 内容,感觉蛮不错的,就想着也搞一个玩一下

这个Python群的群主也很热心,搞了个开源的项目放到了github上:L<https://github.com/coldnight/twqq>

源码下载下来安装的过程很艰辛,因为一些语法特性要求必须python2.7以上版本并且依赖的pycurl包也非常难编译安 装

折腾了很久总算也跑起来了,但毕竟不是Perl写的,不是很熟悉,用起来也觉得不爽

在github上搜索了下 "webqq",得到很多搜索结果,有各种语言的实现,但活跃的项目不多

尤其是基于Perl开发的项目少之又少,反而Python的倒一大堆,看不惯这种情况,决定自己亲自用Perl写一个

在这个过程中也了解到了,目前存在的各自版本的qq机器人都基本上是基于腾讯的webqq协议来实现的

因此要自己从头开发一个难度并不大,另外,自己有管理几个Perl的QQ群

群里经常会有一些新手不知道该去哪里找模块,去哪里查文档,讨论一些代码问题的时候

也总是不方便,因此也萌生了用Perl写一个智能化的QQ机器人,能够在群里协助大家学习Perl语言

例如在QQ群里发一个perldoc -f open,机器人就会自动把相关的文档贴出来,聊天过程中提到了某个模块的名字

机器人也会自动的把模块相关的介绍、作者、用法自动贴出来,很贴心有木有?

当然一个机器人能做的事情远远不止这些,Webqq::Client提供的只是一个客户端的框架,剩下的任凭你的想象力

=head2 原理说明

模块采用AnyEvent的异步框架,尽可能的减少依赖模块,以便于安装和使用,提供面向对象的使用方式

如果你对AnyEvent有一定了解,那么相信不需要花费太多时间就很容易掌握模块的使用方法,如果你并不了解 AnyEvent

也没有关系,你要做的仅仅是三件事:

1、登录

2、设置感兴趣的回调函数,在回调函数中对消息进行处理

3、运行

=head2 模块用法简介

    use Webqq::Client;
    use Digest::MD5 qw(md5_hex);
    my $qq = 12345678;

    #你的qq密码请使用md5加密后再传递给Webqq::Client
    #我可不想被怀疑有盗号行为
    my $pwd = md5_hex('your password');

    #通过new来初始化一个客户端对象
    #debug=>1来打印debug信息方便调试
    my $client = Webqq::Client->new(debug=>0);

    #通过login进行登录
    $client->login( qq=> $qq, pwd => $pwd);

    #客户端加载ShowMsg插件,用于打印消息内容
    $client->load("ShowMsg");

    #登录成功后设置客户端的发送消息回调函数
    $client->on_send_message=sub{
        #当发送完消息后,传递给回调函数的是三个参数
        my $msg = shift;   #发送的原始消息
        my $is_success = shift; #发送消息状态,True为成功,False为失败
        my $status = shift; #发送消息状态,UTF8编码的中文,"发送成功" 或者 "发送失败"

        #客户端执行插件,这个插件的作用是直接打印消息到屏幕
        $client->call("ShowMsg",$msg);
    };

    #登录成功后设置客户端的接收消息回调函数
    $client->on_receive_message = sub{
        #当收到消息后,传递给回调函数的唯一参数是原始消息的一个hash引用
        my $msg = shift;

        #客户端执行插件,这个插件的作用是直接打印消息到屏幕
        $client->call("ShowMsg",$msg);

        #你可以对收到的消息进行任意其他的处理
        #你也可以使用Data::Dumper这样的模块来查看消息的结构,比如
        #use Data::Dumper;
        #print Dumper $msg;

        ...;
    };
    #客户端进入事件循环,正式开始运行
    $client->run();

更多使用方法和介绍请参见文档

=head2 关于回调函数

目前提供了几种回调函数,可以满足大多是使用场景,请参见模块的文档介绍


但有一点你需要注意,客户端是单线程的,你不应该在回调函数中长时间阻塞,这样会导致整个客户端阻塞,什么事都不做

=head2 关于插件

客户端提供了一个基本的插件管理的机制,来方便你编写和运行插件,我们举个具体的例子说明下什么是插件,怎么写一个插件

比如我想实现一个插件,作用就是当收到群消息的时候就回复一个hello world到这个群上

第一步:写一个插件模块

    package Webqq::Client::Plugin::HelloWorld;
    #模块中定义一个call函数
    sub call{
        #记住,call函数第一个参数永远是客户端对象
        my $client = shift;

        #这个插件还需要额外传入一个客户端收到的群消息才能进行后续的处理
        my $msg = shift;

        #我们只对群消息感兴趣
        return if $msg->{type} ne 'group_message';

        #使用客户端的reply_message()方法进行消息回复
        $client->reply_message($msg,"hello world");
    }
    1;

第二步:加载插件

    #使用load方法进行加载,会自动查找Webqq::Client::Plugin::HelloWorld模块
    $client->load("HelloWorld");

第三部:使用插件

    #使用call()方法调用插件
    $client->on_receieve_message = sub{
        my $msg = shift;
        $client->call("HelloWorld",$msg);
    };
    $client->run();


=head2 模块从哪里获取

目前模块已经发布到了github和cpan上



github更新会比较频繁,建议使用github随时保持和最新版本同步

=head2 补充

腾讯的新版本是smartqq,老版本是webqq,这里统一都称之为webqq,webqq功能本身受限并不能向PC端那样 做很多事情

另外,模块还处于不断开发完善中,存在bug和很多不完善之处是必然的,有什么问题或想法欢迎跟作者反馈

如果你是新手,希望有一个一起学习交流Perl的地方,欢迎加入我所在的QQ群: PERL学习交流 群号:144539789

如果你是高手,又乐于助人,对新手有足够的耐心,也非常欢迎加入

=head2 作者

Perfi, E<lt>sjdy521@163.comE<gt>

=cut


感谢灰灰的投稿,欢迎更多 Perler 参与活动。本文网页地址见: http://advent.perl-china.com/calendar/2014/09/
--
您收到此邮件是因为您订阅了Google网上论坛上的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此群组,请发送电子邮件至perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问https://groups.google.com/d/optout。

--
您收到此邮件是因为您订阅了Google网上论坛上的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此群组,请发送电子邮件至perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问https://groups.google.com/d/optout。

--
您收到此邮件是因为您订阅了Google网上论坛上的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此群组,请发送电子邮件至perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问https://groups.google.com/d/optout。

Re: [PerlChina] PerlChina Advent 09: Webqq::Client

讚!但是聽說 webqq近期要關閉,不知道還能用多長時間。

==============================================
9月30日消息,近日登录腾讯WebQQ的用户会看到"WebQQ告别会 相聚有时 后会无期"的公告页面。预示着WebQQ即将停止服务,但公 告页面并没有给出停止服务的具体时间,目前WebQQ及SmartQQ也仍然能正常使用。

据了解,WebQQ于2009年9月15日正式上线,是腾讯公司推出的使用网页方式上QQ的服务,特点是无需下载和安装QQ软件,只要能打 开 WebQQ的网站就可以登录QQ与好友保持联系。具有Web产品固有的便利性,同时在Web上最大限度的保持了客户端软件的操作习惯。去年9 月,WebQQ更名为SmartQQ全新发布,但仍保留了原WebQQ版本。

此外,腾讯"我的QQ中心"的"好友"功能已于2014年7月15日停止服务。据悉,此次WebQQ是继此之后的又一业务调整。



On 2014年12月09日 21:02, chenlin rao wrote:
=encoding utf8

=for advent_year 2014

=for advent_title Webqq::Client模块介绍

=for advent_author Perfi Wang


=head2 Webqq::Client 背景来源

最早的时候,加入了一个Python的群,看到群里有个QQ机器人可以自动帮大家查询天气

群里贴出来的url会自动去获取下html的 <title> 内容,感觉蛮不错的,就想着也搞一个玩一下

这个Python群的群主也很热心,搞了个开源的项目放到了github上:L<https://github.com/coldnight/twqq>

源码下载下来安装的过程很艰辛,因为一些语法特性要求必须python2.7以上版本并且依赖的pycurl包也非常难编译安 装

折腾了很久总算也跑起来了,但毕竟不是Perl写的,不是很熟悉,用起来也觉得不爽

在github上搜索了下 "webqq",得到很多搜索结果,有各种语言的实现,但活跃的项目不多

尤其是基于Perl开发的项目少之又少,反而Python的倒一大堆,看不惯这种情况,决定自己亲自用Perl写一个

在这个过程中也了解到了,目前存在的各自版本的qq机器人都基本上是基于腾讯的webqq协议来实现的

因此要自己从头开发一个难度并不大,另外,自己有管理几个Perl的QQ群

群里经常会有一些新手不知道该去哪里找模块,去哪里查文档,讨论一些代码问题的时候

也总是不方便,因此也萌生了用Perl写一个智能化的QQ机器人,能够在群里协助大家学习Perl语言

例如在QQ群里发一个perldoc -f open,机器人就会自动把相关的文档贴出来,聊天过程中提到了某个模块的名字

机器人也会自动的把模块相关的介绍、作者、用法自动贴出来,很贴心有木有?

当然一个机器人能做的事情远远不止这些,Webqq::Client提供的只是一个客户端的框架,剩下的任凭你的想象力

=head2 原理说明

模块采用AnyEvent的异步框架,尽可能的减少依赖模块,以便于安装和使用,提供面向对象的使用方式

如果你对AnyEvent有一定了解,那么相信不需要花费太多时间就很容易掌握模块的使用方法,如果你并不了解 AnyEvent

也没有关系,你要做的仅仅是三件事:

1、登录

2、设置感兴趣的回调函数,在回调函数中对消息进行处理

3、运行

=head2 模块用法简介

    use Webqq::Client;
    use Digest::MD5 qw(md5_hex);
    my $qq = 12345678;

    #你的qq密码请使用md5加密后再传递给Webqq::Client
    #我可不想被怀疑有盗号行为
    my $pwd = md5_hex('your password');

    #通过new来初始化一个客户端对象
    #debug=>1来打印debug信息方便调试
    my $client = Webqq::Client->new(debug=>0);

    #通过login进行登录
    $client->login( qq=> $qq, pwd => $pwd);

    #客户端加载ShowMsg插件,用于打印消息内容
    $client->load("ShowMsg");

    #登录成功后设置客户端的发送消息回调函数
    $client->on_send_message=sub{
        #当发送完消息后,传递给回调函数的是三个参数
        my $msg = shift;   #发送的原始消息
        my $is_success = shift; #发送消息状态,True为成功,False为失败
        my $status = shift; #发送消息状态,UTF8编码的中文,"发送成功" 或者 "发送失败"

        #客户端执行插件,这个插件的作用是直接打印消息到屏幕
        $client->call("ShowMsg",$msg);
    };

    #登录成功后设置客户端的接收消息回调函数
    $client->on_receive_message = sub{
        #当收到消息后,传递给回调函数的唯一参数是原始消息的一个hash引用
        my $msg = shift;

        #客户端执行插件,这个插件的作用是直接打印消息到屏幕
        $client->call("ShowMsg",$msg);

        #你可以对收到的消息进行任意其他的处理
        #你也可以使用Data::Dumper这样的模块来查看消息的结构,比如
        #use Data::Dumper;
        #print Dumper $msg;

        ...;
    };
    #客户端进入事件循环,正式开始运行
    $client->run();

更多使用方法和介绍请参见文档

=head2 关于回调函数

目前提供了几种回调函数,可以满足大多是使用场景,请参见模块的文档介绍


但有一点你需要注意,客户端是单线程的,你不应该在回调函数中长时间阻塞,这样会导致整个客户端阻塞,什么事都不做

=head2 关于插件

客户端提供了一个基本的插件管理的机制,来方便你编写和运行插件,我们举个具体的例子说明下什么是插件,怎么写一个插件

比如我想实现一个插件,作用就是当收到群消息的时候就回复一个hello world到这个群上

第一步:写一个插件模块

    package Webqq::Client::Plugin::HelloWorld;
    #模块中定义一个call函数
    sub call{
        #记住,call函数第一个参数永远是客户端对象
        my $client = shift;

        #这个插件还需要额外传入一个客户端收到的群消息才能进行后续的处理
        my $msg = shift;

        #我们只对群消息感兴趣
        return if $msg->{type} ne 'group_message';

        #使用客户端的reply_message()方法进行消息回复
        $client->reply_message($msg,"hello world");
    }
    1;

第二步:加载插件

    #使用load方法进行加载,会自动查找Webqq::Client::Plugin::HelloWorld模块
    $client->load("HelloWorld");

第三部:使用插件

    #使用call()方法调用插件
    $client->on_receieve_message = sub{
        my $msg = shift;
        $client->call("HelloWorld",$msg);
    };
    $client->run();


=head2 模块从哪里获取

目前模块已经发布到了github和cpan上



github更新会比较频繁,建议使用github随时保持和最新版本同步

=head2 补充

腾讯的新版本是smartqq,老版本是webqq,这里统一都称之为webqq,webqq功能本身受限并不能向PC端那样 做很多事情

另外,模块还处于不断开发完善中,存在bug和很多不完善之处是必然的,有什么问题或想法欢迎跟作者反馈

如果你是新手,希望有一个一起学习交流Perl的地方,欢迎加入我所在的QQ群: PERL学习交流 群号:144539789

如果你是高手,又乐于助人,对新手有足够的耐心,也非常欢迎加入

=head2 作者

Perfi, E<lt>sjdy521@163.comE<gt>

=cut


感谢灰灰的投稿,欢迎更多 Perler 参与活动。本文网页地址见: http://advent.perl-china.com/calendar/2014/09/
--
您收到此邮件是因为您订阅了Google网上论坛上的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此群组,请发送电子邮件至perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问https://groups.google.com/d/optout。

[PerlChina] PerlChina Advent 09: Webqq::Client

=encoding utf8

=for advent_year 2014

=for advent_title Webqq::Client模块介绍

=for advent_author Perfi Wang


=head2 Webqq::Client 背景来源

最早的时候,加入了一个Python的群,看到群里有个QQ机器人可以自动帮大家查询天气

群里贴出来的url会自动去获取下html的 <title> 内容,感觉蛮不错的,就想着也搞一个玩一下

这个Python群的群主也很热心,搞了个开源的项目放到了github上:L<https://github.com/coldnight/twqq>

源码下载下来安装的过程很艰辛,因为一些语法特性要求必须python2.7以上版本并且依赖的pycurl包也非常难编译安装

折腾了很久总算也跑起来了,但毕竟不是Perl写的,不是很熟悉,用起来也觉得不爽

在github上搜索了下 "webqq",得到很多搜索结果,有各种语言的实现,但活跃的项目不多

尤其是基于Perl开发的项目少之又少,反而Python的倒一大堆,看不惯这种情况,决定自己亲自用Perl写一个

在这个过程中也了解到了,目前存在的各自版本的qq机器人都基本上是基于腾讯的webqq协议来实现的

因此要自己从头开发一个难度并不大,另外,自己有管理几个Perl的QQ群

群里经常会有一些新手不知道该去哪里找模块,去哪里查文档,讨论一些代码问题的时候

也总是不方便,因此也萌生了用Perl写一个智能化的QQ机器人,能够在群里协助大家学习Perl语言

例如在QQ群里发一个perldoc -f open,机器人就会自动把相关的文档贴出来,聊天过程中提到了某个模块的名字

机器人也会自动的把模块相关的介绍、作者、用法自动贴出来,很贴心有木有?

当然一个机器人能做的事情远远不止这些,Webqq::Client提供的只是一个客户端的框架,剩下的任凭你的想象力

=head2 原理说明

模块采用AnyEvent的异步框架,尽可能的减少依赖模块,以便于安装和使用,提供面向对象的使用方式

如果你对AnyEvent有一定了解,那么相信不需要花费太多时间就很容易掌握模块的使用方法,如果你并不了解AnyEvent

也没有关系,你要做的仅仅是三件事:

1、登录

2、设置感兴趣的回调函数,在回调函数中对消息进行处理

3、运行

=head2 模块用法简介

    use Webqq::Client;
    use Digest::MD5 qw(md5_hex);
    my $qq = 12345678;

    #你的qq密码请使用md5加密后再传递给Webqq::Client
    #我可不想被怀疑有盗号行为
    my $pwd = md5_hex('your password');

    #通过new来初始化一个客户端对象
    #debug=>1来打印debug信息方便调试
    my $client = Webqq::Client->new(debug=>0);

    #通过login进行登录
    $client->login( qq=> $qq, pwd => $pwd);

    #客户端加载ShowMsg插件,用于打印消息内容
    $client->load("ShowMsg");

    #登录成功后设置客户端的发送消息回调函数
    $client->on_send_message=sub{
        #当发送完消息后,传递给回调函数的是三个参数
        my $msg = shift;   #发送的原始消息
        my $is_success = shift; #发送消息状态,True为成功,False为失败
        my $status = shift; #发送消息状态,UTF8编码的中文,"发送成功" 或者 "发送失败"

        #客户端执行插件,这个插件的作用是直接打印消息到屏幕
        $client->call("ShowMsg",$msg);
    };

    #登录成功后设置客户端的接收消息回调函数
    $client->on_receive_message = sub{
        #当收到消息后,传递给回调函数的唯一参数是原始消息的一个hash引用
        my $msg = shift;

        #客户端执行插件,这个插件的作用是直接打印消息到屏幕
        $client->call("ShowMsg",$msg);

        #你可以对收到的消息进行任意其他的处理
        #你也可以使用Data::Dumper这样的模块来查看消息的结构,比如
        #use Data::Dumper;
        #print Dumper $msg;

        ...;
    };
    #客户端进入事件循环,正式开始运行
    $client->run();

更多使用方法和介绍请参见文档

=head2 关于回调函数

目前提供了几种回调函数,可以满足大多是使用场景,请参见模块的文档介绍


但有一点你需要注意,客户端是单线程的,你不应该在回调函数中长时间阻塞,这样会导致整个客户端阻塞,什么事都不做

=head2 关于插件

客户端提供了一个基本的插件管理的机制,来方便你编写和运行插件,我们举个具体的例子说明下什么是插件,怎么写一个插件

比如我想实现一个插件,作用就是当收到群消息的时候就回复一个hello world到这个群上

第一步:写一个插件模块

    package Webqq::Client::Plugin::HelloWorld;
    #模块中定义一个call函数
    sub call{
        #记住,call函数第一个参数永远是客户端对象
        my $client = shift;

        #这个插件还需要额外传入一个客户端收到的群消息才能进行后续的处理
        my $msg = shift;

        #我们只对群消息感兴趣
        return if $msg->{type} ne 'group_message';

        #使用客户端的reply_message()方法进行消息回复
        $client->reply_message($msg,"hello world");
    }
    1;

第二步:加载插件

    #使用load方法进行加载,会自动查找Webqq::Client::Plugin::HelloWorld模块
    $client->load("HelloWorld");

第三部:使用插件

    #使用call()方法调用插件
    $client->on_receieve_message = sub{
        my $msg = shift;
        $client->call("HelloWorld",$msg);
    };
    $client->run();


=head2 模块从哪里获取

目前模块已经发布到了github和cpan上



github更新会比较频繁,建议使用github随时保持和最新版本同步

=head2 补充

腾讯的新版本是smartqq,老版本是webqq,这里统一都称之为webqq,webqq功能本身受限并不能向PC端那样做很多事情

另外,模块还处于不断开发完善中,存在bug和很多不完善之处是必然的,有什么问题或想法欢迎跟作者反馈

如果你是新手,希望有一个一起学习交流Perl的地方,欢迎加入我所在的QQ群: PERL学习交流 群号:144539789

如果你是高手,又乐于助人,对新手有足够的耐心,也非常欢迎加入

=head2 作者

Perfi, E<lt>sjdy521@163.comE<gt>

=cut


感谢灰灰的投稿,欢迎更多 Perler 参与活动。本文网页地址见: http://advent.perl-china.com/calendar/2014/09/

--
您收到此邮件是因为您订阅了Google网上论坛上的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此群组,请发送电子邮件至perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问https://groups.google.com/d/optout。

2014年12月8日星期一

[PerlChina] Re: 2014年12月14日上海地区Perl爱好者聚会

2014年12月14日上海地区Perl爱好者聚会具体信息如下:
地点:MeLibrary 书吧 上海体育-场-旁龙山新村122号101室蓝色小屋(4号线上海体育-场-站3号出口对面小区门卫亭右手边)可以在豆瓣上查到更详细的信息。
时间:2014年12月14日 10:00 至 13:00
费用:50元包括茶水和一份盒饭

活动联系人 徐鹤军 手机 15901848767


前期发邮件报名的朋友已经将该信息回复了,请查收。



On Monday, December 1, 2014 12:20:50 PM UTC+8, BlackJack wrote:
各位,

上海地区Perl爱好者好久没有聚会了,计划在2014年12月14日10点到13点办一次Perl 爱好者聚会,把上海地区的Perl活动恢复起来。本次活动的内容主要是大家认识一下。基本消费是50元,包括茶和中午的一份快餐。特别欢迎还在上学的同学参加,可以免单。

活动地点基本定在上海体育场 4号地铁站附近,同时方便浦西和浦东的朋友。

请有意参加本次活动的Perl 爱好者通过邮件 xu.hejun@163.com 联系我。

请在邮件中告知 姓名和手机号,方便及时通知活动信息。

我会在或者活动前三天通知活动的具体地址。

另外,也请在perlchian.org上有帐号的朋友将本信息转发到perlchina.org 的上海版上,让更多上海朋友知道。

-Jack

--
您收到此邮件是因为您订阅了Google网上论坛上的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此群组,请发送电子邮件至perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问https://groups.google.com/d/optout。

Re: [PerlChina] PerlChina Advent 08: Future 模块

Fantastic. 
Future 也许就像它的名字一样,真是Future。

非常感谢能继续介绍这些新兴的模块。对我这种懒人来说,真的是帮助非常大。
本来卡住的思想,又能继续前进。差点就要自己写一个类似的东西了,发现有人已经做了,真是一种幸福的感觉。殊途同归啊!

Perl的未来也许不是perl6,而是perl5的不断翻新。

在 2014年12月8日 下午10:29,chenlin rao <rao.chenlin@gmail.com>写道:
# Future

这个名字一听起来还以为是要说 Perl 的发展方向之类的吧。其实我这里要介绍的是一个 CPAN 模块,或者说,一种异步编程模式在 Perl 里的运用。

Future 模式的定义之类的,大家可以看 Java 或者 C++ 的资料,都会有提。这里直接进入 Perl 相关的部分。[Future 模块](https://metacpan.org/pod/Future)的作者是著名的 Paul Evans,[IO::Async 模块](https://metacpan.org/pod/IO::Async)的作者。事实上 IO::Async 模块现在已经完全依赖于 Future 模块了。

考虑大家其实用 AnyEvent 周边模块比较多,这里展示如何在 AnyEvent 环境里,使用 Future。示例脚本及解释如下:

## 首先加载程序要用的模块及导出函数

    use 5.20.0;
    use experimental 'signatures';
    use AnyEvent;
    use AnyEvent::HTTP;
    use AnyEvent::Future qw/as_future/;
    use Future::Utils qw/fmap/;

## 为 AnyEvent 的异步函数封装成 Future 对象

`as_future` 接收一个匿名函数,内部封装异步操作,这里就是最常见的 `http_get`,匿名函数会传递进去一个 Future 对象。而在异步操作的回调中,我们可以调用该 Future 对象的 **implementation methods**(These methods would primarily be used by implementations of asynchronous interfaces)。

最常见的就是 `->done(@results)` 和 `->fail($exception, @details)` 两个方法,分别传递成功和失败的消息。

这里示例中就是判断只有响应码在 2XX 的时候,成功返回网页;否则失败报错。

    sub future_get($url) {
        return as_future {
            my $f = shift;
            http_get $url, sub($body, $hdr) {
                if ( $hdr->{Status} =~ /^2/ ) {
                    $f->done($body);
                }
                else {
                    $f->fail( $url . " got " . $hdr->{Reason} );
                }
            };
        }

`as_future` 的返回值,也就是这个 Future 对象。所以,我们可以继续在这个对象上调用 Future 的 **sequencing methods**(These methods all return a new future to represent the combination of its invocant followed by another action given by a code reference)。

最常见的,是 `->then( \&code(@result) )`  `->else( \&code($exception) )`。注意为了让链式调用可以继续下去,这里的匿名函数一定也要返回一个新的 Future 对象。

这里示例,就只判断一下失败的报错信息,如果是 404 Not Found,可以认为服务器本身没问题,依然返回一个成功的 Future。事实上这里完全可以再使用其他的异步操作。

        ->else(
            sub($exception) {
                if ( $exception =~ /Not Found/ ) {
                    Future->done("OK, now.");
                }
                else {
                    Future->fail($exception);
                }
            }
        );
    };

好了,函数定义完成。你就可以直接使用了。

## 多个 Future 对象的协同工作

单个 url 下载当然没什么意思,我们这里需要一些复杂逻辑来协同工作。下面这段的效果是:并发 5 个请求请求 URL 列表,但是超过 5 秒没完成就直接停止。

    my $future = Future->wait_any(
        AnyEvent::Future->new_timeout( after => 5 ),
        fmap { future_get(shift) } foreach => \@urls, concurrent => 5
    );

这其中用的是 Future 的 convergent futures(These constructors all take a list of component futures, and return a new future whose readiness somehow depends on the readiness of those components),也就是传入由多个 Future 对象构成的数组,返回一个新的 Future 对象。

常见的有 `->wait_any(@futures)`、`->wait_all(@futures)`、`->needs_all(@futures)`、`->needs_any(@futures)` 四种。wait 表示有返回即可,needs 则要求返回的为成功才行。

`fmap` 则是 [Future::Utils](https://metacpan.org/pod/Future::Utils) 模块额外提供的函数,用来方便的控制循环操作和并发等。模块里还提供了 `repeat`、`try_repeat`、`fmap_concat` 等其他函数和 `while`、`otherwise` 等其他循环控制。

如果这里不用控制,直接简单一点,可以写成一行:

    my $future = Future->needs_all( map { future_get($_) } @urls );

## 正式运行

前面这么多,都还是在定义阶段。现在可以准备运行了。跟运行相关的,叫做 user methods(These methods would primarily be used by users of asynchronous interfaces, on objects returned by such an interface)。

最常用的,有`->get`、`->on_done`、`->on_fail`、`->on_ready`、`->failure` 等。

这里的逻辑是:Future 运行完成的状态,叫 **ready**。ready 且 done 的状态,返回的数据通过 **get** 获取;ready 但是 fail 的状态,返回的数据通过 **failure** 获取。

    $future->on_done( sub { say "everything is ok" } );
    $future->on_fail( sub { say "something wrong!" } );
    $future->get;

## 运行结果

把上面几段代码连起来保存成文件并运行,可以看到如下结果:

> something wrong!
> http://www.baidu got Device not configured at future.pl line 43.

试试自己修改一下 urls 数组的内容,看看结果如何吧?

## 参考

Future 的详细用法示例,大家可以上 pevans 个人博客上看他去年的 [future advent](http://leonerds-code.blogspot.jp/2013/12/futures-advent-day-1.html) 系列。顺带一说,今年他个人博客是又在写响应式编程模式的文章,说不准之后又会推出相应模块吧…



--
您收到此邮件是因为您订阅了Google网上论坛上的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此群组,请发送电子邮件至perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问https://groups.google.com/d/optout。

--
您收到此邮件是因为您订阅了Google网上论坛中的"PerlChina Mongers 讨论组"论坛。
要退订此论坛并停止接收此论坛的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此论坛,请发送电子邮件至perlchina@googlegroups.com。
通过http://groups.google.com/group/perlchina访问此论坛。
要查看更多选项,请访问https://groups.google.com/d/optout。

[PerlChina] PerlChina Advent 08: Future 模块

# Future

这个名字一听起来还以为是要说 Perl 的发展方向之类的吧。其实我这里要介绍的是一个 CPAN 模块,或者说,一种异步编程模式在 Perl 里的运用。

Future 模式的定义之类的,大家可以看 Java 或者 C++ 的资料,都会有提。这里直接进入 Perl 相关的部分。[Future 模块](https://metacpan.org/pod/Future)的作者是著名的 Paul Evans,[IO::Async 模块](https://metacpan.org/pod/IO::Async)的作者。事实上 IO::Async 模块现在已经完全依赖于 Future 模块了。

考虑大家其实用 AnyEvent 周边模块比较多,这里展示如何在 AnyEvent 环境里,使用 Future。示例脚本及解释如下:

## 首先加载程序要用的模块及导出函数

    use 5.20.0;
    use experimental 'signatures';
    use AnyEvent;
    use AnyEvent::HTTP;
    use AnyEvent::Future qw/as_future/;
    use Future::Utils qw/fmap/;

## 为 AnyEvent 的异步函数封装成 Future 对象

`as_future` 接收一个匿名函数,内部封装异步操作,这里就是最常见的 `http_get`,匿名函数会传递进去一个 Future 对象。而在异步操作的回调中,我们可以调用该 Future 对象的 **implementation methods**(These methods would primarily be used by implementations of asynchronous interfaces)。

最常见的就是 `->done(@results)` 和 `->fail($exception, @details)` 两个方法,分别传递成功和失败的消息。

这里示例中就是判断只有响应码在 2XX 的时候,成功返回网页;否则失败报错。

    sub future_get($url) {
        return as_future {
            my $f = shift;
            http_get $url, sub($body, $hdr) {
                if ( $hdr->{Status} =~ /^2/ ) {
                    $f->done($body);
                }
                else {
                    $f->fail( $url . " got " . $hdr->{Reason} );
                }
            };
        }

`as_future` 的返回值,也就是这个 Future 对象。所以,我们可以继续在这个对象上调用 Future 的 **sequencing methods**(These methods all return a new future to represent the combination of its invocant followed by another action given by a code reference)。

最常见的,是 `->then( \&code(@result) )`  `->else( \&code($exception) )`。注意为了让链式调用可以继续下去,这里的匿名函数一定也要返回一个新的 Future 对象。

这里示例,就只判断一下失败的报错信息,如果是 404 Not Found,可以认为服务器本身没问题,依然返回一个成功的 Future。事实上这里完全可以再使用其他的异步操作。

        ->else(
            sub($exception) {
                if ( $exception =~ /Not Found/ ) {
                    Future->done("OK, now.");
                }
                else {
                    Future->fail($exception);
                }
            }
        );
    };

好了,函数定义完成。你就可以直接使用了。

## 多个 Future 对象的协同工作

单个 url 下载当然没什么意思,我们这里需要一些复杂逻辑来协同工作。下面这段的效果是:并发 5 个请求请求 URL 列表,但是超过 5 秒没完成就直接停止。

    my $future = Future->wait_any(
        AnyEvent::Future->new_timeout( after => 5 ),
        fmap { future_get(shift) } foreach => \@urls, concurrent => 5
    );

这其中用的是 Future 的 convergent futures(These constructors all take a list of component futures, and return a new future whose readiness somehow depends on the readiness of those components),也就是传入由多个 Future 对象构成的数组,返回一个新的 Future 对象。

常见的有 `->wait_any(@futures)`、`->wait_all(@futures)`、`->needs_all(@futures)`、`->needs_any(@futures)` 四种。wait 表示有返回即可,needs 则要求返回的为成功才行。

`fmap` 则是 [Future::Utils](https://metacpan.org/pod/Future::Utils) 模块额外提供的函数,用来方便的控制循环操作和并发等。模块里还提供了 `repeat`、`try_repeat`、`fmap_concat` 等其他函数和 `while`、`otherwise` 等其他循环控制。

如果这里不用控制,直接简单一点,可以写成一行:

    my $future = Future->needs_all( map { future_get($_) } @urls );

## 正式运行

前面这么多,都还是在定义阶段。现在可以准备运行了。跟运行相关的,叫做 user methods(These methods would primarily be used by users of asynchronous interfaces, on objects returned by such an interface)。

最常用的,有`->get`、`->on_done`、`->on_fail`、`->on_ready`、`->failure` 等。

这里的逻辑是:Future 运行完成的状态,叫 **ready**。ready 且 done 的状态,返回的数据通过 **get** 获取;ready 但是 fail 的状态,返回的数据通过 **failure** 获取。

    $future->on_done( sub { say "everything is ok" } );
    $future->on_fail( sub { say "something wrong!" } );
    $future->get;

## 运行结果

把上面几段代码连起来保存成文件并运行,可以看到如下结果:

> something wrong!
> http://www.baidu got Device not configured at future.pl line 43.

试试自己修改一下 urls 数组的内容,看看结果如何吧?

## 参考

Future 的详细用法示例,大家可以上 pevans 个人博客上看他去年的 [future advent](http://leonerds-code.blogspot.jp/2013/12/futures-advent-day-1.html) 系列。顺带一说,今年他个人博客是又在写响应式编程模式的文章,说不准之后又会推出相应模块吧…



--
您收到此邮件是因为您订阅了Google网上论坛上的"PerlChina Mongers 讨论组"群组。
要退订此群组并停止接收此群组的电子邮件,请发送电子邮件到perlchina+unsubscribe@googlegroups.com。
要发帖到此群组,请发送电子邮件至perlchina@googlegroups.com。
访问此群组:http://groups.google.com/group/perlchina。
要查看更多选项,请访问https://groups.google.com/d/optout。