Hoboken Rails Meetup



Hoboken Rails Meetup

0 0


2-sinatra-fake


On Github mwenger1 / 2-sinatra-fake

Hoboken Rails Meetup

Grab pizza while we're waiting to kick things off

Housekeeping Before We Start

  • Bathrooms
  • We're a new meetup. Would love your feedback
  • Tonight's Sponsor:

Tonight's Gameplan

  • Icebreaker: This Month I Learned
  • PRESENTATION: Feature Testing with a Sinatra Fake
  • Open Conversation: Ask the group anything
  • Wrap up around 8:45. Can continue the conversation at the bar downstairs

Ice Breaker Questions

  • What's your name?
  • What's your story? (job, technology stack, open source)
  • TMIL - "This Month I Learned"

External Services

Test Driven Development

Benefits of Simulating an External Service

  • No concerns about api quotas
  • Work Offline
  • Speed

Setup with Webmock

First make sure all external calls are intercepted

# spec/spec_helper.rb
require 'webmock/rspec'
WebMock.disable_net_connect!(allow_localhost: true)

Stubbing the Responses

If small number, you could manually set

config.before(:each) do
  stub_request(:get, /api.facebook.com/).
    with(headers: {'Accept'=>'*/*'}).
    to_return(status: 200, body: "payload", headers: {})
  end
end`

VCR Gem

Record real API calls as cassettes and playback responses

Sinatra Fake

  • Gave us the greatest control of configuring every call's payload
  • Really helpful to have json fixtures in the project for reference

Setting up the Fake

Use Webmock gem to intercept calls and redirect them to your Fake class

  config.before(:each) do
    stub_request(:any, /api.athenahealth.com/).to_rack(FakeAthena)
  end

Setting up the Fake

Create your sinatra app

# spec/support/fake_athena.rb

require "sinatra/base"
require "sinatra/namespace"

class FakeAthena < Sinatra::Base
  register Sinatra::Namespace
end

Fixtures

Set up endpoints and fixtures as needed by tests

    #spec/support/fake_athena.rb
    get "/providers/:provider_id" do
      json_response 200, "provider.json"
    end

    private

    def json_response(response_code, file_name)
      content_type :json
      status response_code
      File.open(File.dirname(__FILE__) + "/../fixtures/" + file_name, "rb").read
    end
    #spec/fixtures/provider.json
[{
    "firstname": "Marc",
    "specialty": "Family Medicine",
    "acceptingnewpatients": "false",
    "providertypeid": "MD",
    "billable": "true",
    "ansinamecode": "Allopathic & Osteopathic Physicians : Family Practice (207Q00000X)",
    "lastname": "Feingold",
    "providerid": "71",
    "ansispecialtycode": "207Q00000X",
    "hideinportal": "false",
    "entitytype": "Person",
    "npi": "1306805015",
    "providertype": "MD"
}]

Features Specs for Gets Are Straight Forward

  # spec/features/patient_checks_in_for_appointment_spec.rb
  expect(page).to have_content "Dr. Marc Feingold"

Put, Post, Delete Requests Require a Flag

  # spec/support/fake_athena.rb
  def self.has_updated_patient?
    updated_patient
  end

  put "/patients/:patient_id" do
    self.class.updated_patient = true
    json_response 200, "update_patient.json"
  end
  # spec/features/patient_checks_in_for_appointment_spec.rb
  expect(FakeAthena).to have_updated_patient

Clear the Flag After Each Test

# spec/support/fake_athena.rb
def self.reset
  self.updated_patient = false
end

# spec/rails_helper.rb
config.after(:each) do
  FakeAthena.reset
end

Questions???

ATGA

"Ask the Group Anything"

  • A specific bug you are stuck on
  • Tooling Questions
  • Educational Resources
  • Share what you are learning

Wrapping Up

  • Feedback. What topics/speakers would you like to see?
  • Next Meetup is April 7th
  • Thanks to Tonight's Sponsor:
  • Keep the conversation going over drinks at Wicked Wolf

Have a great night!