使用 RSpec 为 TDD/BDD 建立帮助
Build up help for TDD/BDD with RSpec
大约 2 周前我开始学习 Ruby,我使用 'open-uri' 和 'nokogiri' 制作了一个 WebParser / Page WordCounter。所以我只是 运行 使用 'ruby counter.rb http://test.com word' 和我以及那个词的匹配数量,不区分大小写,所以我可以抓住一切。
所以我在这里学习 RSpec、TDD、BDD 和所有这些东西,我想知道如何使用 RSpec 示例和期望来构造我的代码。我已经阅读了所有文档,我正在构建简单的示例进行测试等。
我想知道是否有人可以将我的代码构建到 RSpec 示例和期望中,这样我就可以研究你做了什么以及你是怎么做的。
这是我的代码:
require 'open-uri'
require 'nokogiri'
class Counter
def initialize(url)
@url = url
end
def count(word, url)
doc = Nokogiri::HTML(open(url))
doc.css('head').remove
doc.text.scan(/#{word}/i).size
end
end
url, word = ARGV
puts "Found: #{Counter.new(url).count(word, url)} matches."
希望有人能帮助我,我真的很喜欢 ruby 并且发现这个 RSpec 太棒了,
谢谢大家,我会学习等待的!
有一个 rspec --init
命令可以创建您的样板文件。
完成此操作后,打开 spec_helper.rb
并需要您的代码文件。
顺便说一下,您的初始化接受 url 并将其分配给实例变量有点奇怪,但是 count 方法将 url 作为参数。
所以假设它被重构为:
attr_reader :url
def initialize(url)
@url = url
end
def count(word)
doc = Nokogiri::HTML(open(url)) # this uses the attr_reader
doc.css('head').remove
doc.text.scan(/#{word}/i).size
end
那么你可以这样写一个测试用例(这里不是全面覆盖,只是一个例子):
describe "Counter" do
let(:url) { "http://some_url" }
let(:counter) { Counter.new url }
it "counts words" do
expect(counter.count("foo")).to(
eq("<whatever the expected result is>")
)
end
end
使用let
设置变量是可选的。您也可以在 it ... do
块内设置变量,但您必须对每种情况重复一次。
除了.to
你还有.not_to
,除了eq
还有很多有用的方法。我建议阅读 RSpec 匹配器文档以熟悉这些内容。
还值得一提的是,此测试用例将进行 HTTP 调用,有时需要,有时不需要。例如,如果您有很多案例并希望快速 运行 它们,那么删除 HTTP 调用将是有益的。但是这样做意味着您实际上不再测试 url 的状态。如果标记发生变化怎么办?除非您的测试用例实际进行了 HTTP 调用,否则您无法确定。
不过,了解如何删除 HTTP 调用还是有好处的,因为基础概念("mocking" 或 "stubbing")有很多用途。像这样:
it "counts words" do
mock_html = <<-HTML
<!doctype html>
<html lang='en'>
<head></head>
<body>foo</body>
</html>
HTML
expect(Object).to(
receive(:open).with(any_args).at_least(1).times.and_return(mock_html)
)
expect(counter.count("foo")).to eq(1)
expect(counter.count("bar")).to eq(0)
end
any_args
是一个可以在存根方法时使用的特殊术语。你也可以在这里使用 url
因为你知道传递的参数是什么。
有关更多信息,我将再次向您推荐 RSpec 的文档,这次是关于模拟/存根的文档。
通常您希望主要关注 input/output 函数。有时您会想要检查是否调用了另一个方法(为此您会使用 mock/stub),但您可能不希望您测试每一行代码。
大约 2 周前我开始学习 Ruby,我使用 'open-uri' 和 'nokogiri' 制作了一个 WebParser / Page WordCounter。所以我只是 运行 使用 'ruby counter.rb http://test.com word' 和我以及那个词的匹配数量,不区分大小写,所以我可以抓住一切。
所以我在这里学习 RSpec、TDD、BDD 和所有这些东西,我想知道如何使用 RSpec 示例和期望来构造我的代码。我已经阅读了所有文档,我正在构建简单的示例进行测试等。
我想知道是否有人可以将我的代码构建到 RSpec 示例和期望中,这样我就可以研究你做了什么以及你是怎么做的。
这是我的代码:
require 'open-uri'
require 'nokogiri'
class Counter
def initialize(url)
@url = url
end
def count(word, url)
doc = Nokogiri::HTML(open(url))
doc.css('head').remove
doc.text.scan(/#{word}/i).size
end
end
url, word = ARGV
puts "Found: #{Counter.new(url).count(word, url)} matches."
希望有人能帮助我,我真的很喜欢 ruby 并且发现这个 RSpec 太棒了,
谢谢大家,我会学习等待的!
有一个 rspec --init
命令可以创建您的样板文件。
完成此操作后,打开 spec_helper.rb
并需要您的代码文件。
顺便说一下,您的初始化接受 url 并将其分配给实例变量有点奇怪,但是 count 方法将 url 作为参数。
所以假设它被重构为:
attr_reader :url
def initialize(url)
@url = url
end
def count(word)
doc = Nokogiri::HTML(open(url)) # this uses the attr_reader
doc.css('head').remove
doc.text.scan(/#{word}/i).size
end
那么你可以这样写一个测试用例(这里不是全面覆盖,只是一个例子):
describe "Counter" do
let(:url) { "http://some_url" }
let(:counter) { Counter.new url }
it "counts words" do
expect(counter.count("foo")).to(
eq("<whatever the expected result is>")
)
end
end
使用let
设置变量是可选的。您也可以在 it ... do
块内设置变量,但您必须对每种情况重复一次。
除了.to
你还有.not_to
,除了eq
还有很多有用的方法。我建议阅读 RSpec 匹配器文档以熟悉这些内容。
还值得一提的是,此测试用例将进行 HTTP 调用,有时需要,有时不需要。例如,如果您有很多案例并希望快速 运行 它们,那么删除 HTTP 调用将是有益的。但是这样做意味着您实际上不再测试 url 的状态。如果标记发生变化怎么办?除非您的测试用例实际进行了 HTTP 调用,否则您无法确定。
不过,了解如何删除 HTTP 调用还是有好处的,因为基础概念("mocking" 或 "stubbing")有很多用途。像这样:
it "counts words" do
mock_html = <<-HTML
<!doctype html>
<html lang='en'>
<head></head>
<body>foo</body>
</html>
HTML
expect(Object).to(
receive(:open).with(any_args).at_least(1).times.and_return(mock_html)
)
expect(counter.count("foo")).to eq(1)
expect(counter.count("bar")).to eq(0)
end
any_args
是一个可以在存根方法时使用的特殊术语。你也可以在这里使用 url
因为你知道传递的参数是什么。
有关更多信息,我将再次向您推荐 RSpec 的文档,这次是关于模拟/存根的文档。
通常您希望主要关注 input/output 函数。有时您会想要检查是否调用了另一个方法(为此您会使用 mock/stub),但您可能不希望您测试每一行代码。