2012-06-08 2 views
17

Tôi không biết mình đang làm gì sai, nhưng mỗi khi tôi thử kiểm tra chuyển hướng, tôi nhận được lỗi này: "@yquest phải là ActionDispatch :: Yêu cầu "Cách kiểm tra chuyển hướng bằng Rspec và Capybara

context "as non-signed in user" do 
    it "should redirect to the login page" do 
    expect { visit admin_account_url(account, host: get_host(account)) }.to redirect_to(signin_path) 
    end 
end 
1) AdminAccountPages Admin::Accounts#show as non-signed in user should redirect to the login page 
    Failure/Error: expect { visit admin_account_url(account, host: get_host(account)) }.to redirect_to(signin_path) 
    ArgumentError: 
     @request must be an ActionDispatch::Request 
    # ./spec/requests/admin_account_pages_spec.rb:16:in `block (4 levels) in <top (required)>' 

Tôi đang sử dụng RSpec-ray (2.9.0) với Capybara (1.1.2) và Rails 3.2. Tôi sẽ đánh giá cao nếu ai đó cũng có thể giải thích tại sao điều này xảy ra; tại sao tôi không thể sử dụng kỳ vọng theo cách như vậy?

+0

Có thể tôi đang thiếu thứ gì đó, nhưng có gì sai với 'assert_redirected_to'? –

+0

@JosephWeissman, tôi gặp lỗi tương tự! – Mohamad

Trả lời

30

Capybara không phải là giải pháp dành riêng cho đường ray nên không biết bất kỳ điều gì về logic hiển thị của đường ray.

Capybara có nghĩa là đặc biệt cho thử nghiệm tích hợp, chủ yếu chạy thử nghiệm từ quan điểm của người dùng cuối tương tác với trình duyệt. Trong các thử nghiệm này, bạn không nên khẳng định các mẫu vì người dùng cuối không thể thấy sâu vào ứng dụng của bạn. Thay vào đó, những gì bạn nên thử nghiệm là hành động đưa bạn đến đúng con đường.

current_path.should == new_user_path 
page.should have_selector('div#erro_div') 
+1

Với phiên bản mới hơn của Capybara, nó không còn hoạt động nữa. Tôi có 2.10.1 và có một phương thức 'has_current_path' mới có thể được sử dụng:' expect (page). To have_current_path (new_user_path) ' – bjnord

11

Thông báo lỗi @request must be an ActionDispatch::Request nói với bạn rằng rspec-ray Matcher redirect_to (nó đại biểu cho Rails assert_redirected_to) hy vọng nó sẽ được sử dụng trong Rails kiểm tra chức năng (nên trộn trong ActionController::TestCase). Mã bạn đăng trông giống như thông số yêu cầu rspec-ray. Vì vậy, redirect_to không khả dụng.

Kiểm tra chuyển hướng không được hỗ trợ trong thông số yêu cầu rspec-rails, nhưng được hỗ trợ trong kiểm tra tích hợp Rails.

Cho dù bạn nên kiểm tra rõ ràng cách chuyển hướng được thực hiện (đó là phản hồi 301 chứ không phải phản hồi 307 và không phải javascript) hoàn toàn tùy thuộc vào bạn.

+1

Cảm ơn bạn đã giải thích điều này. – Mohamad

10

bạn có thể làm theo cách này:

expect(current_path).to eql(new_app_user_registration_path) 
3

Đây là giải pháp hackish mà tôi tìm thấy

# spec/features/user_confirmation_feature.rb 

feature 'User confirmation' do 
    scenario 'provide confirmation and redirect' do 
    visit "https://stackoverflow.com/users/123/confirm" 

    expect(page).to have_content('Please enter the confirmation code') 
    find("input[id$='confirmation_code']").set '1234' 

    do_not_follow_redirect do 
     click_button('Verify') 
     expect(page.driver.status_code).to eq(302) 
     expect(page.driver.browser.last_response['Location']).to match(/\/en\//[^\/]+\/edit$/) 
    end 
    end 

    protected 

    # Capybara won't follow redirects 
    def do_not_follow_redirect &block 
    begin 
     options = page.driver.instance_variable_get(:@options) 
     prev_value = options[:follow_redirects] 
     options[:follow_redirects] = false 

     yield 
    ensure 
     options[:follow_redirects] = prev_value 
    end 
    end 
end 
+0

Điều này giúp nếu chuyển hướng của bạn xảy ra là một liên kết bên ngoài –

2

RSpec 3:

Cách đơn giản nhất để kiểm tra các đường dẫn hiện tại là với :

expect(page).to have_current_path('/login?status=invalid_token')

Các have_current_path có lợi thế hơn phương pháp này:

expect(current_path).to eq('/login')

vì bạn có thể bao gồm params truy vấn.

+1

đó là sự khác biệt với mong đợi (current_path) .to eq ('/ login? Status = invalid_token')? – sekmo