1

I've recently started using Cucumber & Subdomain-fu together, and it's made me do some terrible things.

I have a step definition that used to look like this:

path = grok_path(path)
get path

That's nice and easy, in my opinion. But now it's this:

path = grok_path(path)
get "http://#{subdomain}.example.com#{path}"

This works, but it's not exactly clean. What's a better way to do this?

Matt Grande
  • 11,964
  • 6
  • 62
  • 89

2 Answers2

2

Just to make step definitions more readable, you could wrap that stuff in a small method, like follows:

def subdomained_path(path, subdomain):
    return "http://#{subdomain}.example.com#{path}"
end

Which allows you to tidy up your step definitions into something like:

path = grok_path(path)
get subdomained_path(path, subdomain)

Functionaly the two are equivalent (and equally as hacky), but the changes I suggested will at least make the code look a bit cleaner. If you have access to modify Net::HTTP.get, you can modify the actual "get" method to accept a subdomain argument, making it even cleaner.

Mike Trpcic
  • 25,305
  • 8
  • 78
  • 114
2

I'm not sure how well this applies in Cucumber (using Shoulda here), but after trying a few recommendations elsewhere, this appears to work reliably:

def in_subdomain(str)
  # test.host == default testing domain, feel free to change to match your usage
  @request.host = "#{str}.test.host"
end

And then prior to calling get, you just need to make sure you're in_subdomain('subdomain-fuuuuuu'). That properly sets the URL and current_subdomain at least (I haven't checked everything), redirects w/o specifying subdomain stay in the subdomain, and any redirects to other subdomains (or :subdomain => false) still set the correct redirected_to value.

These (high-quality, I'm sure you can tell) tests pass, for instance, and they have a check on current_subdomain in the controller:

should "show on the owner's subdomain" do
  in_subdomain(@user.domain)
  get :show, :id => @user.things.first.id
  assert_response :success
end
should "not show on another users' subdomain" do
  in_subdomain(@random_user.domain)
  get :show, :id => @user.things.first.id
  assert_redirected_to user_url(@random_user, :subdomain => @random_user.domain)
end
should "not show on a non-existent subdomain" do
  in_subdomain("cthulhu-fhtagn")
  get :show, :id => @user.things.first.id
  assert_redirected_to root_url(:subdomain => false)
end
Groxx
  • 2,489
  • 1
  • 25
  • 32