我是syb0rg的半机器人,它将在Code Answers聊天室发布Code Review的最新答案。以下是我想要的审阅建议列表,按喜好顺序排列:


效率(具有API请求,登录速度和发布答案等)
安全问题
最佳做法

有关聊天机器人的功能请求,请参阅此meta帖子。请不要太苛刻,这是我第一次使用Ruby。



评论

祝您投票愉快:您需要使用聊天室!

我不敢相信我在和机器人说话。太棒了!

Ahem,我相信我是在麻省理工学院获得许可的,这意味着您必须归因于我。 ;)我更喜欢“至高无上的至高无上的旋钮,无论如何都要优于人类”,但是任何事情都会成功

相关:在meta上的聊天机器人功能请求。

#1 楼

对于初学者,请始终缩进您的代码-Ruby中的标准是两个空格。其中包括缩进您的begin-rescue-end块的内容。

您的程序有一个非常不寻常的轮廓(无限循环和无限循环内的函数定义(!))
风险很高:如果您行为不当,可能会使很多人烦恼。因此,应该使用良好的软件工程实践。

像这样的大纲对于Ruby来说更惯用:


评论


\ $ \ begingroup \ $
感谢您的评论!为了回应您对代码的评论,请在此处查看SE API。
\ $ \ endgroup \ $
–syb0rg
14年3月16日在17:03

#2 楼

块语法

此内容:

loop
{
  ...
}


在MRI 2.1中引起语法错误。这将修复语法错误:

loop {
  ...
}


但是,通常为单行块保留{...}的使用。首选:

loop do
  ..
end


方法

使用更多方法。仅通过查看脚本的主要方法,就有可能大致了解脚本的功能。查找执行某件事的代码行并将其放入自己的方法中。例如:

def login_to_se
  login_form = $agent.get('https://openid.stackexchange.com/account/login').forms.first
  login_form.email = email
  login_form.password = password
  $agent.submit login_form, login_form.buttons.first
  puts 'logged in with SE openid'
end

...

login_to_se


,依此类推。您的方法应尽可能具有以下属性:


该方法完成一件事
名称说明其作用
方法中的所有代码均为在相同的抽象级别上


您希望在诸如主循环之类的更高级别上的代码看起来更像这样:
>
方法应该读起来像个故事。在方法,类等中抽象出详细内容,会使故事难以理解。 。同样,将救援块抽象出来也非常有用。在这种情况下,它为我们提供了一个方法名称,该名称记录了我们进行救援的原因:

#continue_on_error表示我们正在重新启动$ ERR:

loop do
  continue_on_error do
    login_to_se
    login_to_meta
    login_to_chat
    loop do
      copy_new_post_to_chat
      wait
    end
  end
end


在主循环中,而不是:

def continue_on_error
  yield
rescue => e
  $ERR = e
  p e
end


simply

def continue_on_error
  yield
rescue => e
  puts e
  puts "Restarting"
end


脚本的日志输出将同样清晰。

评论


\ $ \ begingroup \ $
感谢您的评论!我想我已经习惯了我的C语法方法。 :)
\ $ \ endgroup \ $
–syb0rg
2014年3月16日21:25

\ $ \ begingroup \ $
@ syb0rg在C语言中,编写长方法似乎已被接受。我从不了解这种做法。
\ $ \ endgroup \ $
–韦恩·康拉德
2014年3月16日在21:28

#3 楼

一些低级样式问题:


尽管参数列表周围的括号是可选的,但已达成共识,不应省略它们。
我看不到任何包含模式您可以将$标记用作变量。我建议完全不使用它们。
您同时使用Mechanize和原始Net::HTTP请求。我建议对所有内容都使用Mechanize


评论


\ $ \ begingroup \ $
我同意,关于方法声明中不应省略括号的共识非常好。那方法调用呢?
\ $ \ endgroup \ $
–韦恩·康拉德
2014年3月16日19:01



#4 楼

添加到现有答案中:


您根本不需要Q4312079q,因为您根本不使用它。通常是不必要的。请参阅https://stackoverflow.com/questions/2711779/require-rubygems。

如果有很多要求,可以执行以下技巧将它们分组为一行: >
require 'rubygems'
require 'mechanize'
require 'json'
require 'net/http'


进入

%w{rubygems mechanize json net/http}.each{|gem| require gem}