2012-12-13 9 views
26

Użytkownicy na stronie internetowej nie rozróżniają "przycisku" i "łącza oznaczonego jako przycisk". Czy istnieje sposób na sprawdzenie, czy na stronie znajduje się "przycisk lub link"?Capybara matcher dla obecności przycisku lub łącza

Na przykład Kapibara ma krok:

page.should have_button('Click me') 

które nie znajdują się linki urządzone jako przyciski.

+0

Miałem zamiar to zrobić z powodu linków Javascript, ale potem zdecydowałem się nie: w tym przypadku to * jest * możliwe do odróżnienia. Np. Po środkowym kliknięciu otwiera się nowa karta, a po najechaniu cel linku jest wyświetlany tylko dla linku. Najlepszą praktyką jest: nie używaj w tym przypadku odnośników i nie zezwalaj na testy. –

+1

Istnieje jednak przypadek, w którym to jest tego warte: negacja. W przeciwnym razie, jeśli zmienisz linki do przycisków, testy będą zawsze milczeć. –

Odpowiedz

49

już dowiedział lepszą odpowiedź:

page.should have_selector(:link_or_button, 'Click me') 

wynikało z click_link_or_button który jest zdefiniowany tutaj: https://github.com/jnicklas/capybara/blob/master/lib/capybara/node/actions.rb#L12

def click_link_or_button(locator) 
    find(:link_or_button, locator).click 
end 
alias_method :click_on, :click_link_or_button 

wywołuje selektor :link_or_button . selektor ten zdefiniowany jest tutaj: https://github.com/jnicklas/capybara/blob/master/lib/capybara/selector.rb#L143

Capybara.add_selector(:link_or_button) do 
    label "link or button" 
    xpath { |locator| XPath::HTML.link_or_button(locator) } 
end 

To nazywa tę metodę: http://rdoc.info/github/jnicklas/xpath/XPath/HTML#link_or_button-instance_method

# File 'lib/xpath/html.rb', line 33 

def link_or_button(locator) 
    link(locator) + button(locator) 
end 

więc starałem się sprawdzić obecność selektora i to działało:

page.should have_selector(:link_or_button, 'Click me') 
1

Osobiście chciałbym dać przycisk lub łącze id i poszukać że używając

page.should have_css('#foo')

ten sposób możesz odwołać się do linku lub przycisku bez obawy o jego implementację.

zawsze znajdę tego użytecznego: https://gist.github.com/428105

1

Można również używać niestandardowego macierzy

RSpec::Matchers::define :have_link_or_button do |text| 
    match do |page| 
    Capybara.string(page.body).has_selector?(:link_or_button, text: text) 
    end 
end 

Następnie zrobić

expect(page).to have_link_or_button('Login') 
0

miałem dziwny przypadek, w którym niektóre testy dymne szli przez różne strony logowania klienta-centric, które miały niewielkie zmiany na robienie logowanie przycisk Prześlij ... Kierując tabeli Ogórek z użytkownikiem, org itp.

# A bit of a hack, org_name is normally a subdomain, but sometimes it is the complete domain 
def login(user, org_name) 
    # Use the below to automatically hit each user's org's server 
    if org_name.include? '.com' 
    Capybara.app_host = "http://#{org_name}" 
    else 
    Capybara.app_host = "http://#{org_name}.mydomain.com" 
    end 

    visit '/' 
    fill_in 'username', :with => user 
    fill_in 'userpwd', :with => '***' 
    begin 
    page.find(:link_or_button, 'submit') 
    click_on 'submit' 
    rescue Capybara::ElementNotFound 
    page.find(:link_or_button, 'Log In') 
    click_on 'Log In' 
    rescue Capybara::ElementNotFound 
     pending "Need to determine how to invoke the Login button for #{org_name} near Line ##{__LINE__} of #{__method__} in #{__FILE__} " 
    end 

    # ----------------------- 
    # Work-around for modal popup saying SSL is mismatched if you are using actual production URLs 
    # The rescue is for cases that do not exhibit the modal pop-up 
    page.driver.browser.switch_to.alert.accept rescue Selenium::WebDriver::Error::NoAlertPresentError 

    # Ensure that login was successful 
    page.should_not have_content 'Login failed' 
end 
1

Korzystanie składnię

expect(page).to have_selector(:link_or_button, 'Click me') 

to działa bez konieczności definiowania niestandardowego dopasowywania oczekiwać.

+0

^To. Składnia powinna /: powinna być przestarzała –

Powiązane problemy