Nếu các bạn đang học về unit test với rspec trong ruby on rails, chắc hẳn sẽ không xa lạ gì với hàm subject.
Khi sử dụng subject, cần chú ý một số điều như sau:
- subject sẽ không được gọi thực thi khi khai báo, mà chỉ được thực thi khi gọi tới nó (Xem ví dụ phía dưới để hiểu cụ thể)
- hàm subject sẽ chỉ được thực thi một lần trong mỗi một block test (một example)
- hàm subject sẽ được thực thi lại trong các block test khác nếu trong block test này có gọi tới subject.
Dưới đây là ví dụ chỉ rõ 3 chú ý trên:
1. subject chỉ được thực thi khi gọi tới nó (chứ không phải khi khai báo subject)
Câu lệnh expect(@something).to eq 0 sẽ không được pass vì @something ở đây vẫn đang có gía trị nil? Vì trong block test này (block nằm giữa 2 từ khóa do … end của it) hàm subject chưa hề được gọi trước câu lệnh expect(@something).to eq 0 nên @something chưa được khởi tạo.
Để đoạn code trên pass hết, ta có thể hoán đổi 2 expect để hàm subject được gọi trước.
2. Hàm subject chỉ được thực thi một lần trong một block test
Ở vd trên, dù hàm subject có được gọi 3 lần đi chăng nữa thì cũng chỉ được thực thi một lần, đoạn code 3.times { subject } hoàn toàn giống với toán tử ||= trong ruby:
3. Hàm subject sẽ được thực thi lại trong các block test khác.
Viết thêm một block test vào ví dụ trên như sau:
Lúc này, ở block test thứ 2, hàm subject sẽ được thực thi lại (mỗi block test chỉ thực thi nhiều nhất một hàm subject).
Chú ý: Ở ví dụ trên, vì block test thứ nhất đã lấy ra phần tử 3 của element_list rồi nên block test thứ 2 chỉ còn lại [1, 2], lúc này hàm subject được thực thi lại với element_list mới này.
Nguồn tham khảo:
https://relishapp.com/rspec/rspec-core/v/3-6/docs/subject/explicit-subject