2013-08-02 29 views
17

Tôi có ứng dụng Rails4 với 'PagesController'.Cách kiểm tra trạng thái hiển thị: 404 với Rails4 và RSpec khi sử dụng rescue_from

Phương thức hiển thị sẽ ném ngoại lệ tùy chỉnh 'PageNotFoundError' khi không tìm thấy Trang.

Trên bộ điều khiển tôi xác định rescue_from PageNotFoundError, with: :render_not_found

render not found là một phương pháp riêng của PagesController và trông giống như:

def render_not_found 
    flash[:alert]=t(:page_does_not_exists, title: params[:id]) 
    @pages = Page.all 
    render :index, status: :not_found #404 
end 

Các đường ray-log trong phát triển chế độ cho thấy:

Started GET "/pages/readmef" for 127.0.0.1 at 2013-08-02 23:11:35 +0200 
Processing by PagesController#show as HTML 
    Parameters: {"id"=>"readmef"} 
    .. 
    Completed 404 Not Found in 14ms (Views: 12.0ms) 

Vì vậy, nó đường nối của tôi: status =>: not_found works, cho đến nay.

Khi tôi làm curl -v http://0.0.0.0:3000/pages/readmef bản ghi curl

curl -v http://localhost:3000/pages/readmef 
* About to connect() to localhost port 3000 (#0) 
* Trying 127.0.0.1... 
* connected 
* Connected to localhost (127.0.0.1) port 3000 (#0) 
> GET /pages/readmef HTTP/1.1 
> User-Agent: curl/7.24.0 (x86_64-apple-darwin12.0) libcurl/7.24.0 OpenSSL/0.9.8x zlib/1.2.5 
> Host: localhost:3000 
> Accept: */* 
> 
< HTTP/1.1 404 Not Found 
< X-Frame-Options: SAMEORIGIN 

Nhưng cuộc thử nghiệm sau đây với RSpec thất bại:

it 'renders an error if page not found' do 
    visit page_path('not_existing_page_321') 
    expect(response.status).to eq(404) 
    within('.alert-error') do 
     page.should have_content('Page not_existing_page_321 doesn\'t exist') 
    end 
    end 

    1) PagesController renders an error if page not found 
    Failure/Error: expect(response.status).to eq(404) 

     expected: 404 
      got: 200 

Tất cả mọi thứ có vẻ tốt đẹp và thậm chí cả test.log nói 404

$ tail -f log/test.log 
Started GET "/pages/not_existing_page_321" for 127.0.0.1 at 2013-08-03 09:48:13 +0200 
Processing by PagesController#show as HTML 
    Parameters: {"id"=>"not_existing_page_321"} 
    Rendered pages/_page.haml (0.8ms) 
    Rendered layouts/_navigation.haml (0.6ms) 
    Rendered layouts/_messages.haml (0.2ms) 
    Rendered layouts/_locales.haml (0.3ms) 
    Rendered layouts/_footer.haml (0.6ms) 
Completed 404 Not Found in 6ms (Views: 4.5ms) 

Tôi đã thử các máy chủ khác nhau, WebRICK, Thin, unicorn. Mọi thứ hoạt động như mong đợi trong chế độ phát triển và sản xuất. Ngay cả test.log cũng đúng nhưng kiểm tra không thành công.

Ai đó có thể cho tôi biết tại sao bài kiểm tra nói 200 thay vì 404?

+1

Bạn cuộn tròn 'trang/readme', không phải 'trang/readmef'. Và bạn đã bao gồm mã thử nghiệm của mình. – sevenseacat

+0

_blushing_ @sevenseacat quyền của bạn Tôi đã không thấy f bị thiếu trong lệnh curl. Và thực sự curl hoạt động tốt và đáp ứng với 404. _ Tôi thực sự nên sử dụng kính của tôi:/Nhưng spec vẫn không hoạt động. Tôi đã thêm nó ở trên. – Nockenfell

+0

@sevenseacat Cảm ơn bạn đã bình luận. Nó dẫn tôi đến vấn đề thực sự. Tôi lập lại câu hỏi. – Nockenfell

Trả lời

12

Mặc dù tôi không hài lòng với giải pháp này, ít nhất đây là công việc xung quanh:

Tôi đã tách thử nghiệm thành hai thông số riêng biệt. Một để kiểm tra mã phản hồi 404 (với GET thay vì truy cập) và một giây để kiểm tra cảnh báo. Thử nghiệm thứ hai là cần thiết vì get không hiển thị chế độ xem - ngay cả khi render_views được xác định trên đầu tệp spec.

it 'response with 404 if page not found' do 
    get :show, { controller: 'pages', id: 'not_existing_page_321' } 
    expect(response.status).to eq(404) 
    end 

    it 'renders an error-message if page not found and shows index' do 
    visit page_path('page_not_found') 
    within '.alert-error' do 
     page.should have_content("Page page_not_found doesn't exist") 
    end 
    end 
7

Vấn đề ở đây là bạn đang nhầm lẫn kiểm tra tính năng Capybara và kiểm tra bộ điều khiển RSpec. visit là phương pháp được cung cấp bởi Capybara và get/response được cung cấp bởi các kiểm tra bộ điều khiển RSpec - bạn không thể sử dụng chúng cùng nhau.

Để kiểm tra điều này như một RSpec thử nghiệm điều khiển duy nhất bạn có thể làm:

it "returns a not found response" do 
    get :show, { id: 'not_existing_page_321' } 
    expect(response.status).to eq(404) 
    expect(response.text).to match(/Page page_not_found doesn't exist/) 
end 

(N.b.Dòng get là khác với những gì bạn được đăng - Tôi chưa bao gồm controller param như nếu bạn đặt này trong spec/controllers/pages_controller_spec.rb nơi nó thuộc về bạn không cần điều đó)

Hoặc như một Capybara tính năng thử nghiệm duy nhất:

it "renders a not found response" do 
    visit page_path('page_not_found') 
    expect(page.status_code).to eq(404) 
    within '.alert-error' do 
    expect(page).to have_content("Page page_not_found doesn't exist") 
    end 
end 
9

một cách tiếp cận với RSpec 3+ sẽ được thử nghiệm cho một ngoại lệ:

it 'response with 404 if page not found' do 
    expect{ get :show, :id => 'bad_id' }.to raise_error(ActionController::RoutingError) 
end 
Các vấn đề liên quan