Ruby Mechanize 自动登陆使用疑问

lukefan · 2014年02月09日 · 最后由 mentor_feng 回复于 2014年02月12日 · 4526 次阅读

我使用 Mechanize 做自动登陆。 尝试:

require 'mechanize'
agent = Mechanize.new
page = agent.get 'http://ruby-china.org/account/sign_in'
form = page.forms[1]
form['user[login]'] = 'username'
form['user[password]'] = 'password'
form.submit
page = agent.get 'http://ruby-china.org'
page.body.match /username/

成功了。

但是到 http://yyets.com 上去试用。

require 'mechanize'
agent = Mechanize.new
page = agent.get 'http://www.yyets.com/User/Login'
form = page.forms[2]
form['email'] = 'username'
form['user_pass'] = 'password'
form.submit
page = agent.get 'http://www.yyets.com'

结果却是失败的。求大牛帮忙看看。

与具体网站有关吧,尝试设置 user-agent .呢?/。

mechanize 可以设置 user_agent_alias 这个(系统和浏览器),是换一下试试。可能是这个问题。

#2 楼 @yfractal 加上了,‘Mac Safari',但依然无效。

最近刚好在用 Mechanize。Mechanize 不支持 js,最后页面 post 的数据不一定是 form 的数据。你可以分析网页的 js,不过抓包比较快捷,抓包结果为 account 和 password

那个网页的登录按钮 type 是 button,form.submit 不行吧

是能够登录的,代码如下:

代码第 9 行和 第 10 行请用你的用户名和密码替换,运行下面的代码,请打开 2.html 文件查看 mechanize 版本为:2.7.1

1 require 'mechanize' 2 agent = Mechanize.new 3 page = agent.get 'http://www.yyets.com/User/Login' 4 form = page.form_with(:id => 'loginform') 5 post_params = {} 6 form.fields.each do |field| 7 post_params[field.name] = form.field_with(:name => field.name).value 8 end 9 post_params['account'] = 'username' 10 post_params['password'] = 'password' 11 post_params['from'] = 'loginpage' 12 post_params['remember'] = 0 13 post_params['url_back'] = '' 14 pay_page = agent.post('http://www.yyets.com/User/Login/ajaxLogin', post_params) 15 agent.get('http://www.yyets.com/user/user/.save('2.html''))

为什么这里用 agent.post -> 请打开 firefox 查看请求记录,就明白了 为什么这里需要这些参数 -> 请打开 firefox 查看请求记录,就明白了

#6 楼 @josh_sulin 最后一句没看懂。 我 get 了 /user/user/ ,这一页面是没有问题的。page.body.match /username/ 是有数值的。但是,再做 agent.get 'http://yyets.com‘或 page.links[21].click 之后。得到的页面再去做 match /username/ 返回的值就是空了。 也就是说依然是未登录的状态。

最后一句写错了:agent.get('http://www.yyets.com/user/user/.save('2.html''')) 应该是这样,复制代码时出错了,不好意思

晕哦,又错了,是 md 处理了 agent.get('http://www.yyets.com/user/user/') . save('2.html''') ,这样,你把空格去掉

#9 楼 @josh_sulin 保存是正确的,但是再访问其他网页的时候,依然是未登录状态。

我登录成功后,就是访问了 http://www.yyets.com/user/user/ 这个个人中心的页面,都是可以进去的啊,你访问的是什么页面啊?

#11 楼 @josh_sulin 我希望能够带着这个登录信息,访问所有的 yyets 下的页面。如果在浏览器里面,登录成功了,就可以用了,但是在程序里面,再访问其他页面,就不行了。

#11 楼 @josh_sulin 是不是要处理 cookie?这个怎么搞呢?

mechanize 操作 cookie 的方式为:

hash = {:name => 'abcd', :value => '123456', :path => '/', :domain => '.qq.com'} cookie = Mechanize::Cookie.new(hash[:name], hash[:value]) cookie.domain = hash[:domain] cookie.path = hash[:path] agent.cookie_jar.add(URI.parse(url), cookie)

通过上面代码,agent 就带上 cookie 了

因为 mechanize 不能执行 JS,功能上确实有局限,你需要更强大的自动化操作,你可以去研究一下 selenium

#3 楼 @lukefan

建议用 capybara,有小伙伴用 capybara 模拟用户登录浏览器登录微信公众账号,主动给用户发图文消息,效果蛮好的。

需要 登录 后方可回复, 如果你还没有账号请 注册新账号