HiveBrain v1.2.0
Get Started
← Back to all entries
patternrubyMinor

RSpec tests for an invoice mailer

Submitted by: @import:stackexchange-codereview··
0
Viewed 0 times
testsmailerinvoiceforrspec

Problem

How would you DRY up this RSpec code?

require "spec_helper"

describe InvoiceMailer do
  let(:user) { create(:user) }
  let(:student) { create(:student, user: user) }
  let(:body) { "And I for one will join with anyone, don't care what color you are. As long as you want change this miserable condition that exists on this earth." }
  subject(:mail) { InvoiceMailer.issue(student, body) }

  describe "issue" do
    subject(:mail) { InvoiceMailer.issue(student, body) }

    it "renders the subject" do
      expect(mail.subject).to eq "New Invoice!"
    end

    it "renders the receiver email" do
      expect(mail.to).to eq [student.user.email]
    end

    it "renders the sender email" do
      expect(mail.from).to eq ["info@test.com"]
    end
  end

  describe "rescind" do
    subject(:mail) { InvoiceMailer.rescind(student, body) }

    it "renders the subject" do
      expect(mail.subject).to eq "Invoice Rescinded!"
    end

    it "renders the receiver email" do
      expect(mail.to).to eq [student.user.email]
    end

    it "renders the sender email" do
      expect(mail.from).to eq ["info@test.com"]
    end
  end

end

Solution

You can use the its syntax:

require "spec_helper"

describe InvoiceMailer do
  let(:user) { create(:user) }
  let(:student) { create(:student, user: user) }
  let(:body) { "And I for one will join with anyone, don't care what color you are. As long as you want change this miserable condition that exists on this earth." }

  describe "issue" do
    subject { InvoiceMailer.issue(student, body) }

    its(:subject) { should eq "New Invoice!" }

    its(:to) { should eq [student.user.email] }

    its(:from) { should eq ["info@test.com"] }
  end

  describe "rescind" do
    subject { InvoiceMailer.rescind(student, body) }

    its(:subject) { should eq "Invoice Rescinded!" }

    its(:to) { should eq [student.user.email] }

    its(:from) { should eq ["info@test.com"] }
  end

end


You can further DRY it up using example groups

describe InvoiceMailer do
  let(:user) { create(:user) }
  let(:student) { create(:student, user: user) }
  let(:body) { "And I for one will join with anyone, don't care what color you are. As long as you want change this miserable condition that exists on this earth." }

  shared_examples_for "outgoing mail" do |method, mail_subject|
    subject { InvoiceMailer.send(method, student, body) }

    its(:subject) { should eq mail_subject }

    its(:to) { should eq [student.user.email] }

    its(:from) { should eq ["info@test.com"] }
  end

  describe "issue" do
    it_should_behave_like "outgoing mail", :issue, 'New Invoice!'
  end

  describe "rescind" do
    it_should_behave_like "outgoing mail", :rescind, 'Invoice Rescinded!'
  end
end

Code Snippets

require "spec_helper"

describe InvoiceMailer do
  let(:user) { create(:user) }
  let(:student) { create(:student, user: user) }
  let(:body) { "And I for one will join with anyone, don't care what color you are. As long as you want change this miserable condition that exists on this earth." }

  describe "issue" do
    subject { InvoiceMailer.issue(student, body) }

    its(:subject) { should eq "New Invoice!" }

    its(:to) { should eq [student.user.email] }

    its(:from) { should eq ["info@test.com"] }
  end

  describe "rescind" do
    subject { InvoiceMailer.rescind(student, body) }

    its(:subject) { should eq "Invoice Rescinded!" }

    its(:to) { should eq [student.user.email] }

    its(:from) { should eq ["info@test.com"] }
  end

end
describe InvoiceMailer do
  let(:user) { create(:user) }
  let(:student) { create(:student, user: user) }
  let(:body) { "And I for one will join with anyone, don't care what color you are. As long as you want change this miserable condition that exists on this earth." }

  shared_examples_for "outgoing mail" do |method, mail_subject|
    subject { InvoiceMailer.send(method, student, body) }

    its(:subject) { should eq mail_subject }

    its(:to) { should eq [student.user.email] }

    its(:from) { should eq ["info@test.com"] }
  end

  describe "issue" do
    it_should_behave_like "outgoing mail", :issue, 'New Invoice!'
  end

  describe "rescind" do
    it_should_behave_like "outgoing mail", :rescind, 'Invoice Rescinded!'
  end
end

Context

StackExchange Code Review Q#42656, answer score: 4

Revisions (0)

No revisions yet.