Testing: Mock And Stub
Tags: rails, rspec, test, ruby
Published: 2023-04-18 14:24:42

## Introduction
Testing is a method to check whether the actual software product matches the expected requirements.Testing is Important because if there are any bugs or errors in the software, they can be identified early and can be solved before the delivery of the software product.
Testing is a crucial part of software development, but it can be challenging to test code that depends on external dependencies and if you're interacting with 3rd party APIs, you don't want to make real calls every time you run a test. That's where mocks and stubs come in. In this guide, we'll take a deep dive into the world of mocks and stubs, and explore how they can help you isolate your tests and improve the reliability of your code.

## What are mocks and stubs?
Before diving into how to use mocks and stubs, it's important to understand what they are. In short, mocks and stubs are simulated objects that mimic the behavior of real objects in controlled ways. Mocks are typically more flexible and configurable, while stubs are simpler and more focused on replacing a single dependency.

![mock diagram](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/mwx8yn1cezskzxgmvab4.png)

![stub diagram](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/mwrczm15ovh5mwbz4iuj.png)

## Mock Vs Stub
The main difference between a mock and a stub is that mocks tend to be more flexible and configurable, while stubs are simpler and more focused on replacing a single dependency. Both mocks and stubs are used to isolate the code being tested from external dependencies.

## Why use mocks and stubs?

- Mocks and stubs are used to isolate the code being tested from external dependencies.

- mocks and stubs can help you to speed up your tests by eliminating the need to wait for external dependencies to respond.

## How to use RSpec-mocks
RSpec is a popular testing framework for Ruby on Rails. We can use [webmock](https://github.com/bblimke/webmock) gem to mock and stub in Ruby on Rails.
The following steps show how you might use WebMock to mock an HTTP request in a Rails application:

- add the webmock gem to your Gemfile and bundle install:
```
group :test do
  gem "webmock"
end
```
`bundle install`
or
```
gem install webmock
```

- In your test file, require the webmock gem and disable real HTTP connections:

```
require 'webmock/rspec'
WebMock.disable_net_connect!
```

- Set up the stubbed response:
  - get request
    ```
    stub_request(:get, "https://example.com/users").
    to_return(status: 200, body: '{"users": [{"id": 1, "name": "foo", email: "example@test.com"}]}')
    ``` 

   - post request
     ```
     stub_request(:post, "https://example.com/users/signup")
        .with(body: {email: "example@test.com", password: "password1234", name: "foo"}.to_json)
        .to_return(status: 200, body: {"user": {"id": 1, "name": "foo", email: "example@test.com"}})

     ```

- Trigger the code that makes the request to the external API. The stubbed response will be returned instead of a real response.

```
describe MyController do
  it "does something" do
    get :index
    expect(response.body).to eq '{"users": [{"id": 1, "name": "foo", email: 'example@test.com'}]}'
  end
end
```

## Conclusion:
Mocks and stubs are powerful tools for isolating your tests and improving the reliability of your code. With this guide, you should now have a solid understanding of what mocks and stubs are, why to use them and how to mock using webmock.