mirror of
https://github.com/opf/openproject.git
synced 2026-06-14 03:30:14 +00:00
255 lines
7.0 KiB
Ruby
255 lines
7.0 KiB
Ruby
# frozen_string_literal: true
|
|
|
|
module Components
|
|
class Datepicker
|
|
include Capybara::DSL
|
|
include Capybara::RSpecMatchers
|
|
include RSpec::Matchers
|
|
|
|
attr_reader :context_selector
|
|
|
|
##
|
|
# Open a datepicker drop field with the trigger,
|
|
# and set the date to the given date.
|
|
# @param trigger [String] Selector to click the trigger at
|
|
# @param date [Date | String] Date or ISO8601 date string to set to
|
|
def self.update_field(trigger, date)
|
|
datepicker = new
|
|
|
|
datepicker.instance_eval do
|
|
input = page.find(trigger)
|
|
input.click
|
|
end
|
|
|
|
date = Date.parse(date) unless date.is_a?(Date)
|
|
datepicker.set_date(date.strftime("%Y-%m-%d"))
|
|
datepicker.expect_current_date(date)
|
|
datepicker.save!
|
|
end
|
|
|
|
def initialize(context = "body")
|
|
@context_selector = context
|
|
end
|
|
|
|
def container
|
|
page.document.find(context_selector)
|
|
end
|
|
|
|
def flatpickr_container
|
|
container.find(".flatpickr-calendar")
|
|
end
|
|
|
|
##
|
|
# Clear all values
|
|
def clear!
|
|
set_field(container.find_field("work_package[start_date]"), "", wait_for_changes_to_be_applied: false)
|
|
set_field(container.find_field("work_package[due_date]"), "", wait_for_changes_to_be_applied: false)
|
|
wait_for_changes_to_be_applied_after_setting_field
|
|
end
|
|
|
|
def expect_visible
|
|
expect(container).to have_css(".flatpickr-calendar .flatpickr-current-month", wait: 10)
|
|
|
|
# For whatever reason, the stimulus controller in the WorkPackage Datepicker needs some time to be loaded.
|
|
# So please, do not remove this line.
|
|
wait_for_network_idle
|
|
end
|
|
|
|
def expect_not_visible
|
|
expect(container).to have_no_css(".flatpickr-calendar .flatpickr-current-month", wait: 10)
|
|
wait_for_network_idle
|
|
end
|
|
|
|
##
|
|
# Select year from input
|
|
def select_year(value)
|
|
retry_block do
|
|
flatpickr_container
|
|
.first(".numInput.cur-year")
|
|
.fill_in(with: value)
|
|
.send_keys :enter # to trigger a keyboard event to get the internal state of flatpickr updated
|
|
end
|
|
end
|
|
|
|
##
|
|
# Select month from datepicker
|
|
def select_month(month)
|
|
month_name = month.is_a?(Integer) ? I18n.t("date.month_names")[month] : month
|
|
|
|
flatpickr_container
|
|
.first(".flatpickr-monthDropdown-months option", text: month_name, visible: :all)
|
|
.select_option
|
|
end
|
|
|
|
##
|
|
# Select day from datepicker
|
|
def select_day(value)
|
|
unless (1..31).cover?(value.to_i)
|
|
raise ArgumentError, "Invalid value #{value} for day, expected 1-31"
|
|
end
|
|
|
|
expect(flatpickr_container).to have_text(value)
|
|
|
|
retry_block do
|
|
flatpickr_container
|
|
.first(".flatpickr-days .flatpickr-day:not(.nextMonthDay):not(.prevMonthDay)",
|
|
text: value)
|
|
.click
|
|
end
|
|
end
|
|
|
|
# Change the datepicker visible area.
|
|
#
|
|
# @param date the date to navigate to. Can be a Date or a String with
|
|
# ISO8601 formatted date.
|
|
def show_date(date)
|
|
date = Date.parse(date) unless date.is_a?(Date)
|
|
|
|
select_year date.year
|
|
select_month date.month
|
|
end
|
|
|
|
# Set a ISO8601 date through the datepicker
|
|
def set_date(date)
|
|
date = Date.parse(date) unless date.is_a?(Date)
|
|
|
|
show_date(date)
|
|
select_day date.day
|
|
end
|
|
|
|
def save!
|
|
container.click_button save_button_label
|
|
end
|
|
|
|
def cancel!
|
|
container.click_button cancel_button_label
|
|
end
|
|
|
|
def expect_save_button_enabled
|
|
expect(container).to have_button(save_button_label, disabled: false)
|
|
end
|
|
|
|
def expect_save_button_disabled
|
|
expect(container).to have_button(save_button_label, disabled: true)
|
|
end
|
|
|
|
def expect_cancel_button_enabled
|
|
expect(container).to have_button(cancel_button_label, disabled: false)
|
|
end
|
|
|
|
##
|
|
# Expect the selected month
|
|
def expect_month(month)
|
|
month = Date::MONTHNAMES.index(month) if month.is_a?(String)
|
|
|
|
# Month is 0-index in select
|
|
field = flatpickr_container.find(".flatpickr-monthDropdown-months")
|
|
expect(field.value.to_i).to eq(month - 1)
|
|
end
|
|
|
|
# Expect the selected day in the input
|
|
def expect_day(value)
|
|
expect(flatpickr_container).to have_css(".flatpickr-day.selected", text: value)
|
|
end
|
|
|
|
##
|
|
# Expect the selected year
|
|
def expect_year(value)
|
|
expect(flatpickr_container).to have_css(".cur-year") { |field|
|
|
field.value.to_i == value.to_i
|
|
}
|
|
end
|
|
|
|
##
|
|
# Expect the current selection to match the
|
|
# given ISO601 date
|
|
def expect_current_date(date)
|
|
date = Date.parse(date) unless date.is_a?(Date)
|
|
|
|
expect_year(date.year)
|
|
expect_month(date.month)
|
|
expect_day(date.day)
|
|
end
|
|
|
|
##
|
|
# Expect the given date to be visible
|
|
def expect_visible_day(date)
|
|
label = date.strftime("%B %-d, %Y")
|
|
expect(page).to have_css(".flatpickr-day[aria-label='#{label}']")
|
|
end
|
|
|
|
##
|
|
# Expect the given date to be visible and a non-working day
|
|
def expect_non_working(date)
|
|
label = date.strftime("%B %-d, %Y")
|
|
expect(page).to have_css(".flatpickr-day.flatpickr-non-working-day[aria-label='#{label}']")
|
|
end
|
|
|
|
##
|
|
# Expect the given date to be visible and a working day
|
|
def expect_working(date)
|
|
label = date.strftime("%B %-d, %Y")
|
|
expect(page).to have_css(".flatpickr-day:not(.flatpickr-non-working-day)[aria-label='#{label}']")
|
|
end
|
|
|
|
##
|
|
# Expect the given date to be visible and disabled
|
|
def expect_disabled(date)
|
|
label = date.strftime("%B %-d, %Y")
|
|
expect(page).to have_css(".flatpickr-day.flatpickr-disabled[aria-label='#{label}']," \
|
|
".flatpickr-day.flatpickr-non-working-day[aria-label='#{label}']")
|
|
end
|
|
|
|
##
|
|
# Expect the given date to be visible and enabled
|
|
def expect_not_disabled(date)
|
|
label = date.strftime("%B %-d, %Y")
|
|
expect(page).to have_css(".flatpickr-day:not(.flatpickr-disabled):not(.flatpickr-non-working-day)[aria-label='#{label}']")
|
|
end
|
|
|
|
def displays_date?(date)
|
|
expect_visible
|
|
label = date.strftime("%B %-d, %Y")
|
|
page.has_css?(".flatpickr-day[aria-label='#{label}']", wait: 0)
|
|
end
|
|
|
|
def has_previous_month_toggle?
|
|
expect_visible
|
|
page.has_css?(".flatpickr-prev-month", wait: 0)
|
|
end
|
|
|
|
protected
|
|
|
|
def save_button_label
|
|
I18n.t(:button_apply)
|
|
end
|
|
|
|
def cancel_button_label
|
|
I18n.t(:button_cancel)
|
|
end
|
|
|
|
def focus_field(field)
|
|
field.click
|
|
end
|
|
|
|
def set_field(field, value, wait_for_changes_to_be_applied: true)
|
|
focus_field(field)
|
|
if using_cuprite?
|
|
clear_input_field_contents(field)
|
|
field.fill_in(with: value)
|
|
else
|
|
field.fill_in(with: value, fill_options: { clear: :backspace })
|
|
end
|
|
|
|
if wait_for_changes_to_be_applied
|
|
wait_for_changes_to_be_applied_after_setting_field
|
|
end
|
|
end
|
|
|
|
def wait_for_changes_to_be_applied_after_setting_field
|
|
sleep 0.75 # input debounce
|
|
wait_for_network_idle
|
|
end
|
|
end
|
|
end
|