Day-27 特集:测试驱动开发 TDD

所谓测试驱动开发(Test-driven development, TDD),即「先写测试再开发」,写一段程序,以测试功能是否正常,确保程序依照预期行为运作。有关基本原理及JavaScript中的使用,详参延伸阅读(这里)。本文另以Ruby语言展示之。

撰写测试应吻合3A原则,即Arrange(安排好)、Act(踢他两下)、Assertion(断言/条件)。

JavaScript的测试实例

const moreThanChars = (chars, n) => /.{8,}/.test(chars)

test("应该要超过 8 个字 part 1", () => {
  let result = moreThanChars("abc", 8)
  expect(result).toBe(false)
})

test("应该要超过 8 个字 part 2", () => {
  let result = moreThanChars("abc283209138021832", 8)
  expect(result).toBe(true)
})

function test(title, callback) {
  try {
    callback() //万一上面的callback坏了
    console.log(`✓ ${title}`);  //没坏印这个
  } 
  catch(err) {
    console.error(`✗ ${title}`)  //坏了印这个
    console.error(err)  //印出来
  }
}

function expect(result) {
  return {
    toBe: (expected) => {
      if (result !== expected) {
        throw new Error(`${result} 与预期的 ${expected} 不符!`)
      }
    }
  }
}

Ruby的测试框架

在Ruby中,内建有「minitest」测试框架。特点是速度快,但难写。另一个测试框架「RSpec」比较主流,须额外安装,执行慢但语法易懂。

撰写完毕的测试档,以指令「rspec 测试档名称.rb」执行即可。

Ruby的测试实例

本文以ATM取/存款功能为例,设定测试条件及效果如下:
存钱功能

  • 可以存钱
  • 不可以存 0 元或是小於 0 元的金额(越存钱越少!)

领钱功能

  • 可以领钱
  • 不能领 0 元或是小於 0 元的金额(越领钱越多!)
  • 不能领超过本身余额
class ATM
  def initialize(balance)
    @balance = balance #初始化进实体变数
  end

  def withdraw(money)
    if money > 0 and money <= @balance
      @balance = @balance - money
    return money
    else
      return 0 #领钱小於0的话 不给领钱
    end
  end

  def deposit(money)
    @balance = @balance + money if money > 0
  end

  def balance
    @balance #剩下就是余额
  end
end

RSpec.describe ATM do
  context"领钱功能" do
    it "可以领钱" do
      atm = ATM.new(10)
      atm.withdraw(10)
      expect(atm.balance).to be 0
    end

    it "不能领0元" do
      atm = ATM.new(10)
      atm.withdraw(-50)
      expect(atm.balance).to be 10
    end

    it "不能领超过余额" do
      atm = ATM.new(20)
      money = atm.withdraw(30)
      
      expect(atm.balance).to be 20
      expect(money).to be 0
    end
  end

  context"存钱功能" do
    it "可以存钱" do
      atm = ATM.new(10)
      atm.deposit(20)
      expect(atm.balance).to be 30 #(be(30)) 这是matcher
    end
  end

  context"存钱功能的限制" do
    it "不可存0元以下数额" do
      atm = ATM.new(10)
      atm.deposit(-20)
      expect(atm.balance).to be 10 #判断余额是否10元
    end
  end
end

<<:  Day-26 事件机制(2)

>>:  爬虫怎麽爬 从零开始的爬虫自学 DAY29 python网路爬虫开爬10-从网页爬取图片

Day 28. 测试HTTP Status Code

使用SuperTest 使用SSR时,你要负责回应正确的HTTP Status Code。 因为牵涉...

[Day 15] 中场休息 pt.2-整个电脑,都是我的工作室

上一篇我们讲了如何把你的code上传到GitHub 这一篇由於我今天有突发状况所以能写的时间不多 所...

全端入门Day24_後端程序撰写之多一点点的Node.js

昨天介绍了一些名词,今天继续提Node.js Node.js一点入门 今天直接贴上程序码,再去做解释...

Day29-影像侵蚀

上章我们在进行图像轮廓增强的处理时,有用到影像膨胀函数cv2.dilate,但那时候只是稍微带过,读...

Day23 - 使用Django-allauth整合社群登入

今天的实作内容主要根据网路资源进行。 Django并没有提供官方的社群登入整合模组,在第三方套件上,...