Trying on both the Cuke and FakeWeb list. Any help is appreciated...
In our app, we're trying to mock out interaction with a third-party
payment processing service (Braintree in our case). The way
Braintree's transparent redirect model works is that the user form
posts credit card and other billing data to Braintree which redirects
the user back to our app to display the result.
We use Cucumber for acceptance testing and want our Feature/Scenarios
to run without requiring a network connection, so we have:
FakeWeb.allow_net_connect=false
set. I've tried to write a scenario like this...
Scenario: Submit valid payment data using default address
Given FakeWeb will mimic a braintree success
And I am ready to transact
When I select "VISA" from "Card Type"
And I fill in "Card Number" with "4111111111111111"
And I press "Continue"
Then I should see "Woo - Billing!"
with a step like:
Given /^FakeWeb will mimic a braintree success$/ do
FakeWeb.register_uri :post,'https://
secure.braintreepaymentgateway.com/api/transact.php',
:status => ["301", "Moved Permanently"],
:location => transaction_success_url
(Transaction.last)
end
The URL in the above step of course matches the first parameter to the
form_tag in the view. However, when I try executing this, I get the
error:
No route matches "/api/transact.php" with {:method=>:post}
(ActionController::RoutingError)
(eval):2:in `click_button'
Can anyone suggest what the right way to mock out the network would be
for a case like this? I had thought the above FakeWeb call would
result in the "I press 'Continue'" step getting redirected as
mentioned above, but the error looks like it never even gets to
FakeWeb.
it may be hitting fakeweb looking for a mocked request like
"/api/transact.php" instead of "
https://secure.braintreepaymentgateway.com/api/transact.php". when fakeweb
says it doesn't have any mocks like that, it then goes to the rails app and
the router bails out saying that it doesn't match a route. try mocking
Given /^FakeWeb will mimic a braintree success$/ do
FakeWeb.register_uri
:post,'/api/transact.php<http://secure.braintreepaymentgateway.com/api/transact.php>
',
:status => ["301", "Moved Permanently"],
:location => transaction_success_url(Transaction.last)
end
On Wed, Sep 30, 2009 at 4:39 PM, Mike Doel <m...@mikedoel.com> wrote:
> Trying on both the Cuke and FakeWeb list. Any help is appreciated...
> In our app, we're trying to mock out interaction with a third-party
> payment processing service (Braintree in our case). The way
> Braintree's transparent redirect model works is that the user form
> posts credit card and other billing data to Braintree which redirects
> the user back to our app to display the result.
> We use Cucumber for acceptance testing and want our Feature/Scenarios
> to run without requiring a network connection, so we have:
> FakeWeb.allow_net_connect=false
> set. I've tried to write a scenario like this...
> Scenario: Submit valid payment data using default address
> Given FakeWeb will mimic a braintree success
> And I am ready to transact
> When I select "VISA" from "Card Type"
> And I fill in "Card Number" with "4111111111111111"
> And I press "Continue"
> Then I should see "Woo - Billing!"
> with a step like:
> Given /^FakeWeb will mimic a braintree success$/ do
> FakeWeb.register_uri :post,'https://
> secure.braintreepaymentgateway.com/api/transact.php',
> :status => ["301", "Moved Permanently"],
> :location => transaction_success_url
> (Transaction.last)
> end
> The URL in the above step of course matches the first parameter to the
> form_tag in the view. However, when I try executing this, I get the
> error:
> No route matches "/api/transact.php" with {:method=>:post}
> (ActionController::RoutingError)
> (eval):2:in `click_button'
> Can anyone suggest what the right way to mock out the network would be
> for a case like this? I had thought the above FakeWeb call would
> result in the "I press 'Continue'" step getting redirected as
> mentioned above, but the error looks like it never even gets to
> FakeWeb.
On Wed, Sep 30, 2009 at 1:39 PM, Mike Doel <m...@mikedoel.com> wrote: > In our app, we're trying to mock out interaction with a third-party > payment processing service (Braintree in our case). The way > Braintree's transparent redirect model works is that the user form > posts credit card and other billing data to Braintree which redirects > the user back to our app to display the result.
So, FakeWeb works by patching Net::HTTP. It sounds like the problem might be that submitting a form that has an external URI as the action doesn't use Net::HTTP. How that works is up to Webrat or the Rails integration testing stack (assuming you're using the usual Webrat/Rails stack and not celerity/selenium/etc.), and it looks like it might be ignoring the external domain entirely? I'm not sure where that code lives, but we could go find out.
We use Cucumber for acceptance testing and want our Feature/Scenarios
> to run without requiring a network connection
So now I'm curious, does this work without FakeWeb (i.e. hitting the external service)? If not, you'd have to fix that first. If it does work, then that's good -- we can probably figure out how to stub it. Let me know!
> On Wed, Sep 30, 2009 at 1:39 PM, Mike Doel <m...@mikedoel.com> wrote: >> In our app, we're trying to mock out interaction with a third-party >> payment processing service (Braintree in our case). The way >> Braintree's transparent redirect model works is that the user form >> posts credit card and other billing data to Braintree which redirects >> the user back to our app to display the result.
> So, FakeWeb works by patching Net::HTTP. It sounds like the problem > might be that submitting a form that has an external URI as the > action doesn't use Net::HTTP. How that works is up to Webrat or the > Rails integration testing stack (assuming you're using the usual > Webrat/Rails stack and not celerity/selenium/etc.), and it looks > like it might be ignoring the external domain entirely?
So, by default, Webrat uses Rails' integration tests, meaning any form submissions / URL fetches (with the Webrat 'visit' command) ignore the host/port entirely and just use the path part of the URL to inject URLs into the routing dispatcher, meaning that FakeWeb will never get a look-in
You could have a test-only route which does your redirect for you and change the form submission URL in the test environment.
Or, you could switch to using Mechanise to perform actual HTTP requests, in which case FakeWeb (if mechanise plays ball) will get a look-in.