免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
1234下一页
最近访问板块 发新帖
查看: 14904 | 回复: 32
打印 上一主题 下一主题

拿mojo写了个百度音乐的爬虫 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2013-09-25 11:05 |只看该作者 |倒序浏览
本帖最后由 斯文牛氓 于 2013-09-25 18:30 编辑

baidu music
NAME
最近很无聊,前几天写了个模拟百度登录和下载mp3音乐的代码,模块是用的Mojo::UserAgent,下载的时 候之前开了AnyEvent,但是下的太快,百度会有屏蔽,想换ip useragent嫌太麻烦,就串行下 着下着吧,程序的参数是feed,输入百度音乐的一个页面即可,例如张学友的一个歌单是:
  1. [url]http://music.baidu.com/artist/2507[/url]
复制代码
那么你就可以运行:
  1. perl baidu.pl [url]http://music.baidu.com/artist/2507[/url]
复制代码
之后就可以把这个页面的所有码率的歌曲下载出来了,下载路径我写死了’/tmp’,懒的改了, 代码是可以直接运行的,帐号是我的测试帐号,如果你有vip,应该可以下载高品质的mp3, 我这里只能下载一般品质的,但是如果是百度网盘的下载这个程序干不了,貌似百度网盘是 temppath,好了不废话,上代码:
  1.    use Mojo::UserAgent;
  2.     use 5.010;
  3.     use Mojo::UserAgent::CookieJar;
  4.     use YAML 'Dump';
  5.     use Encode qw(decode encode decode_utf8 encode_utf8);
  6.     use Mojo::IOLoop;
  7.     use File::Spec;
  8.     use File::Basename;

  9.     my $feed = shift;
  10.     my $ua   = Mojo::UserAgent->new;
  11.     $ua->name(
  12.     'Mozilla/5.0 (Macintosh; '.
  13.     'Intel Mac OS X 10_8_5) AppleWebKit/537.36 '.
  14.     '(KHTML, like Gecko) Chrome/29.0.1547.76 Safari/537.36'
  15.     );

  16.     # first get baidu index,get first cookie
  17.     say $ua->get('http://www.baidu.com/')->res->code;

  18. =pod
  19.     var bdPass=bdPass||{};
  20.     bdPass.api=bdPass.api||{};
  21.     bdPass.api.params=bdPass.api.params||{};
  22.     bdPass.api.params.login_token='0be08e1d5fa566d2562715a4083ece70';
  23. =cut

  24.     my ($token) = $ua->get(
  25.         'http://passport.baidu.com/v2/api/?getapi&class=login&tpl=mn&tangram=true')
  26.       ->res->body =~ m{login_token\s*=\s*'(.+?)'}six;
  27.     say "token => $token";

  28.     my $staticpage = "http://www.baidu.com/cache/user/html/jump.html";
  29.     my $login_url  = "http://passport.baidu.com/v2/api/?login";
  30.     my $user       = '492003149@qq.com';
  31.     my $password   = 'qq123456';

  32.     my $post_form = {
  33.         charset    => 'utf-8',
  34.         token      => $token,
  35.         isPhone    => "false",
  36.         index      => "0",
  37.         staticpage => $staticpage,
  38.         logintype  => "1",
  39.         'tpl'      => "mn",
  40.         'callback' => "parent.bdPass.api.login._postCallback",
  41.         'username' => $user,
  42.         'password' => $password,
  43.         'mem_pass' => "on",
  44.     };

  45.     # cookies must contain 'BDUSS', 'PTOKEN', 'STOKEN', 'SAVEUSERID'
  46.     my $tx = $ua->post( $login_url => form => $post_form );
  47.     if ( $tx->success ) {
  48.         say "get cookie as :";
  49.         say Dump $tx->res->cookies;
  50.     }

  51.     # now,let's go to validate this cookie,get music.baidu and parse the mp3
  52.     # download address,if you do not login,you can't download the high rate file
  53.     # but take the cookie will be ok!

  54.     my @songs    = ();
  55.     my $base_url = "http://music.baidu.com";

  56.     # find every song's mp3 and album name,title

  57. =pod
  58.     <span class="song-title " style="width: 185px;">
  59.         <a href="/song/7317902" title="相思风雨中"> 相思风雨中 </a> <a title="歌曲MV" target="_blank" href="/mv/7317902" class="mv-icon"></a>
  60.     </span>
  61.     <span class="album-title" style="width: 130px;"> <a href="/album/7311811" title="广东经典101">《广东经典101》</a>        </span>
  62. =cut

  63.     for my $e (
  64.         $ua->get($feed)->res->dom->charset('UTF-8')->find('div.song-item')->each )
  65.     {
  66.         my $node = $e->find('span.[class="song-title "] > a')->first;
  67.         my ( $href, $song_id ) = $node->{href} =~ m/(.*?(\d+))/;
  68.         next unless $song_id;
  69.         my $song_url = $base_url . $href;
  70.         push @songs, {
  71.             link => $song_url,
  72.             name => $node->{title},

  73.             # [url]http://music.baidu.com/song/265898/download?__o=%2Fsong%2F265898[/url]
  74.             download_urls =>
  75.               fetch_mp3_download( $song_url . "/download?__o=/song/$song_id" ),
  76.         };
  77.     }

  78.     download_mp3( \@songs, '/tmp' );
  79.     say Dump( \@songs );

  80.     sub download_mp3 {
  81.         my ( $download_info, $path ) = @_;

  82.         for my $s (@$download_info) {
  83.             for my $d ( @{ $s->{download_urls} } ) {
  84.                 my $abs_path = File::Spec->catfile( $path, $s->{name} );
  85.                 my $file = File::Spec->catfile( $abs_path,
  86.                     $d->{rate} . "_" . $s->{name} . "mp3" );
  87.                 if ( not -d $abs_path ) {
  88.                     mkdir $abs_path;
  89.                 }
  90.                 my $tx = $ua->get( $d->{download_url} );
  91.                 $tx->res->content->asset->move_to($file);
  92.                 $d->{downloaded_mp3} = $file if -e $file;
  93.             }
  94.         }
  95.     }

  96.     sub fetch_mp3_download {
  97.         my ($url) = @_;
  98.         my $tx = $ua->get($url);
  99.         my @downloads;

  100.         if ( $tx->success ) {
  101.             for my $e ( $tx->res->dom->find('a')
  102.                 ->grep( sub { index( $_->{href}, 'mp3' ) != -1 } )->each )
  103.             {
  104.                 push @downloads, {
  105.                     rate         => $e->{id} . "k",
  106.                     download_url => sub { my ($l) = $e->{href} =~ m{link=(.*)}six }
  107.                       ->(),
  108.                 };
  109.             }
  110.         }
  111.         else {
  112.             say "got download box failed";
  113.         }

  114.         return \@downloads;
  115.     }
复制代码
运行结果:

  1. - download_urls:
  2.     - download_url: [url]http://zhangmenshiting.baidu.com/data2/music/7344375/732039850400128.mp3?xcode=cd330a33e570d76d254c2deeb463dd6cf424689cd863f193[/url]
  3.       downloaded_mp3: /tmp/味道/128k_味道mp3
  4.       rate: 128k
  5.     - download_url: [url]http://zhangmenshiting.baidu.com/data2/music/44806384/732039850400256.mp3?xcode=cd330a33e570d76df67218ee4cf8e714bcc3362f19e9add9[/url]
  6.       downloaded_mp3: /tmp/味道/256k_味道mp3
  7.       rate: 256k
  8.   link: [url]http://music.baidu.com/song/7320398[/url]
  9.   name: 味道
  10. - download_urls:
  11.     - download_url: [url]http://zhangmenshiting.baidu.com/data2/music/2367646/2131180187200128.mp3?xcode=cd330a33e570d76db655cdf35416240e9609f46fadf8ce7c[/url]
  12.       downloaded_mp3: /tmp/她来听我的演唱会/128k_她来听我的演唱会mp3
  13.       rate: 128k
  14.     - download_url: [url]http://zhangmenshiting.baidu.com/data2/music/44805709/2131180187200256.mp3?xcode=cd330a33e570d76df67218ee4cf8e714aaab344d72bdf967[/url]
  15.       downloaded_mp3: /tmp/她来听我的演唱会/256k_她来听我的演唱会mp3
  16.       rate: 256k
  17.   link: [url]http://music.baidu.com/song/2131180[/url]
  18.   name: 她来听我的演唱会
  19. - download_urls:
  20.     - download_url: [url]http://zhangmenshiting.baidu.com/data2/music/7312444/1028646194400128.mp3?xcode=cd330a33e570d76d21bac3faf65e237dda8fb61a6a1f8c11[/url]
  21.       downloaded_mp3: /tmp/每次都想呼喊你的名字/128k_每次都想呼喊你的名字mp3
  22.       rate: 128k
  23.     - download_url: [url]http://zhangmenshiting.baidu.com/data2/music/44804660/1028646194400256.mp3?xcode=cd330a33e570d76df67218ee4cf8e714e859495a9f88188d[/url]
  24.       downloaded_mp3: /tmp/每次都想呼喊你的名字/256k_每次都想呼喊你的名字mp3
  25.       rate: 256k
复制代码
代码有点搓,不过还是能工作的。最后说一下,Mojo::UserAgent 真的粉好用!!!!

AUTHOR
舌尖上的牛氓
qq 群: perl-china交流群 211685345
社区 : perl-china.com

论坛徽章:
0
2 [报告]
发表于 2013-09-25 11:20 |只看该作者
沙发

论坛徽章:
0
3 [报告]
发表于 2013-09-25 11:41 |只看该作者
本帖最后由 RZL_01 于 2013-09-25 12:13 编辑

MARK  MOJO确实是个好东西

论坛徽章:
0
4 [报告]
发表于 2013-09-25 12:33 |只看该作者
回复 1# 斯文牛氓




    到此一游

论坛徽章:
1
2015年辞旧岁徽章
日期:2015-03-03 16:54:15
5 [报告]
发表于 2013-09-25 13:06 |只看该作者
你和Coro一起用就可以控制并发了

论坛徽章:
0
6 [报告]
发表于 2013-09-25 13:37 |只看该作者
牛氓 教主   感谢分享

论坛徽章:
0
7 [报告]
发表于 2013-09-25 14:26 |只看该作者
这个。。一直想看下mojo的代码。。

论坛徽章:
8
双子座
日期:2013-08-31 07:37:12金牛座
日期:2013-09-09 18:49:12处女座
日期:2013-09-23 11:43:14处女座
日期:2013-10-09 19:48:21狮子座
日期:2014-03-24 18:22:12丑牛
日期:2014-04-22 22:07:51申猴
日期:2014-06-12 21:54:13双鱼座
日期:2014-06-13 21:52:31
8 [报告]
发表于 2013-09-25 15:52 |只看该作者
本帖最后由 kernel69 于 2013-09-25 15:53 编辑

这是推广贴?还有个群211685345

论坛徽章:
5
丑牛
日期:2014-01-21 08:26:26卯兔
日期:2014-03-11 06:37:43天秤座
日期:2014-03-25 08:52:52寅虎
日期:2014-04-19 11:39:48午马
日期:2014-08-06 03:56:58
9 [报告]
发表于 2013-09-25 15:58 |只看该作者
确实是个好东西,谢谢。

论坛徽章:
0
10 [报告]
发表于 2013-09-25 16:08 |只看该作者
py 发表于 2013-09-25 13:06
你和Coro一起用就可以控制并发了


封你没商量。。还coro呢。。。
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP