DEV: Introduces a wait_for_animation system spec helper (#20573)

This is used when calling click_message_action_mobile to wait
for the message actions menu to finish animating up before
attempting to click on it using capybara. Without this, in
the time between capybara getting the x,y position of a menu
item to click on and the click being fired, the animating menu
can move that item out of the way.

With the new helper, we constantly compare x,y client rect positions
for the animating element and wait for them to stabilise. Once they
do, it means the animation is done, and it is safe to click on
anything within the element.

Re-enables mobile system specs for chat that were ignored because
of this.
This commit is contained in:
Martin Brennan 2023-03-09 01:49:20 +10:00 committed by GitHub
parent 910bf74c2e
commit 54351e1b8a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 37 additions and 9 deletions

View File

@ -39,11 +39,8 @@ module PageObjects
end
def click_message_action_mobile(message, message_action)
i = 0.5
try_until_success(timeout: 20) do
expand_message_actions_mobile(message, delay: i)
first(".chat-message-action-item[data-id=\"#{message_action}\"]")
end
expand_message_actions_mobile(message, delay: 0.5)
wait_for_animation(find(".chat-message-actions"), timeout: 5)
find(".chat-message-action-item[data-id=\"#{message_action}\"] button").click
end

View File

@ -69,8 +69,8 @@ describe "Single thread in side panel", type: :system, js: true do
end
context "when using mobile" do
xit "opens the side panel for a single thread from the mobile message actions menu",
mobile: true do
it "opens the side panel for a single thread from the mobile message actions menu",
mobile: true do
chat_page.visit_channel(channel)
channel_page.click_message_action_mobile(thread.chat_messages.last, "openThread")
expect(side_panel).to have_open_thread(thread)

View File

@ -205,8 +205,8 @@ RSpec.describe "Quoting chat message transcripts", type: :system, js: true do
end
context "when on mobile" do
xit "first navigates to the channel's category before opening the topic composer with the quote prefilled",
mobile: true do
it "first navigates to the channel's category before opening the topic composer with the quote prefilled",
mobile: true do
chat_page.visit_channel(chat_channel_1)
chat_channel_page.click_message_action_mobile(message_1, "selectMessage")

View File

@ -53,6 +53,37 @@ module SystemHelpers
end
end
# Waits for an element to stop animating up to timeout seconds,
# then raises a Capybara error if it does not stop.
#
# This is based on getBoundingClientRect, where Y is the distance
# from the top of the element to the top of the viewport, and X
# is the distance from the leftmost edge of the element to the
# left of the viewport. The viewpoint origin (0, 0) is at the
# top left of the page.
#
# Once X and Y stop changing based on the current vs previous position,
# then we know the animation has stopped and the element is stabilised,
# at which point we can click on it without fear of Capybara mis-clicking.
#
# c.f. https://developer.mozilla.org/en-US/docs/Web/API/Element/getBoundingClientRect
def wait_for_animation(element, timeout: Capybara.default_max_wait_time)
old_element_x = nil
old_element_y = nil
try_until_success(timeout: timeout) do
current_element_x = element.rect.x
current_element_y = element.rect.y
stopped_moving = current_element_x == old_element_x && current_element_y == old_element_y
old_element_x = current_element_x
old_element_y = current_element_y
raise Capybara::ExpectationNotMet if !stopped_moving
end
end
def resize_window(width: nil, height: nil)
original_size = page.driver.browser.manage.window.size
page.driver.browser.manage.window.resize_to(