2021-03-11 07:30:15 +01:00
|
|
|
# frozen_string_literal: true
|
2020-11-26 04:05:50 +01:00
|
|
|
class CustomWizard::TemplateValidator
|
2020-11-03 01:24:20 +01:00
|
|
|
include HasErrors
|
2020-11-09 04:32:36 +01:00
|
|
|
include ActiveModel::Model
|
2021-03-11 07:30:15 +01:00
|
|
|
|
|
|
|
def initialize(data, opts = {})
|
2020-11-03 01:24:20 +01:00
|
|
|
@data = data
|
2020-04-13 14:17:22 +02:00
|
|
|
@opts = opts
|
2021-09-24 11:58:42 +02:00
|
|
|
@subscription = CustomWizard::Subscription.new
|
2020-04-13 14:17:22 +02:00
|
|
|
end
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2020-04-13 14:17:22 +02:00
|
|
|
def perform
|
2020-11-03 01:24:20 +01:00
|
|
|
data = @data
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2020-11-03 01:24:20 +01:00
|
|
|
check_id(data, :wizard)
|
|
|
|
check_required(data, :wizard)
|
2022-01-31 10:18:04 +01:00
|
|
|
validate_after_signup
|
2020-11-03 01:24:20 +01:00
|
|
|
validate_after_time
|
2021-09-24 11:58:42 +02:00
|
|
|
validate_subscription(data, :wizard)
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2022-01-31 10:18:04 +01:00
|
|
|
return false if errors.any?
|
|
|
|
|
2020-11-03 01:24:20 +01:00
|
|
|
data[:steps].each do |step|
|
|
|
|
check_required(step, :step)
|
2021-09-24 11:58:42 +02:00
|
|
|
validate_subscription(step, :step)
|
2022-01-31 10:41:14 +01:00
|
|
|
validate_liquid_template(step, :step)
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2021-09-07 14:06:13 +02:00
|
|
|
if step[:fields].present?
|
|
|
|
step[:fields].each do |field|
|
2021-09-24 11:58:42 +02:00
|
|
|
validate_subscription(field, :field)
|
2020-11-03 01:24:20 +01:00
|
|
|
check_required(field, :field)
|
2022-01-31 10:41:14 +01:00
|
|
|
validate_liquid_template(field, :field)
|
2023-02-09 14:18:25 +01:00
|
|
|
validate_guests(field, :field)
|
2020-04-13 14:17:22 +02:00
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2020-11-03 01:24:20 +01:00
|
|
|
if data[:actions].present?
|
|
|
|
data[:actions].each do |action|
|
2021-09-24 11:58:42 +02:00
|
|
|
validate_subscription(action, :action)
|
2020-11-03 01:24:20 +01:00
|
|
|
check_required(action, :action)
|
2022-01-31 10:41:14 +01:00
|
|
|
validate_liquid_template(action, :action)
|
2023-02-09 14:18:25 +01:00
|
|
|
validate_guests(action, :action)
|
2020-11-03 01:24:20 +01:00
|
|
|
end
|
|
|
|
end
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2022-01-31 10:18:04 +01:00
|
|
|
!errors.any?
|
2020-04-13 14:17:22 +02:00
|
|
|
end
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2020-04-13 14:17:22 +02:00
|
|
|
def self.required
|
|
|
|
{
|
|
|
|
wizard: ['id', 'name', 'steps'],
|
|
|
|
step: ['id'],
|
|
|
|
field: ['id', 'type'],
|
|
|
|
action: ['id', 'type']
|
|
|
|
}
|
|
|
|
end
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2020-04-13 14:17:22 +02:00
|
|
|
private
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2020-04-13 14:17:22 +02:00
|
|
|
def check_required(object, type)
|
2021-09-01 04:19:00 +02:00
|
|
|
self.class.required[type].each do |property|
|
2020-04-13 14:17:22 +02:00
|
|
|
if object[property].blank?
|
2021-03-11 07:30:15 +01:00
|
|
|
errors.add :base, I18n.t("wizard.validation.required", property: property)
|
2020-04-13 14:17:22 +02:00
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
2020-11-03 01:24:20 +01:00
|
|
|
|
2021-09-24 11:58:42 +02:00
|
|
|
def validate_subscription(object, type)
|
2022-03-25 17:08:24 +01:00
|
|
|
object.keys.each do |property|
|
|
|
|
value = object[property]
|
|
|
|
|
|
|
|
if !@subscription.includes?(type, property.to_sym, value)
|
2021-09-24 11:58:42 +02:00
|
|
|
errors.add :base, I18n.t("wizard.validation.subscription", type: type.to_s, property: property)
|
2021-08-10 11:00:42 +02:00
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2020-04-13 14:17:22 +02:00
|
|
|
def check_id(object, type)
|
2020-10-31 08:05:50 +01:00
|
|
|
if type === :wizard && @opts[:create] && CustomWizard::Template.exists?(object[:id])
|
2020-11-09 04:32:36 +01:00
|
|
|
errors.add :base, I18n.t("wizard.validation.conflict", wizard_id: object[:id])
|
2020-04-13 14:17:22 +02:00
|
|
|
end
|
|
|
|
end
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2023-02-09 14:18:25 +01:00
|
|
|
def validate_guests(object, type)
|
2023-02-07 12:46:17 +01:00
|
|
|
guests_permitted = @data[:permitted] && @data[:permitted].any? do |m|
|
2023-02-07 13:17:40 +01:00
|
|
|
m["output"].include?(CustomWizard::Wizard::GUEST_GROUP_ID)
|
2023-02-07 12:46:17 +01:00
|
|
|
end
|
2023-02-09 14:18:25 +01:00
|
|
|
return unless guests_permitted
|
2023-02-07 12:46:17 +01:00
|
|
|
|
2023-02-09 14:18:25 +01:00
|
|
|
if type === :action && CustomWizard::Action::REQUIRES_USER.include?(object[:type])
|
|
|
|
errors.add :base, I18n.t("wizard.validation.not_permitted_for_guests", object_id: object[:id])
|
|
|
|
end
|
|
|
|
|
|
|
|
if type === :field && CustomWizard::Field::REQUIRES_USER.include?(object[:type])
|
|
|
|
errors.add :base, I18n.t("wizard.validation.not_permitted_for_guests", object_id: object[:id])
|
2022-12-24 09:42:09 +01:00
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2022-01-31 10:18:04 +01:00
|
|
|
def validate_after_signup
|
|
|
|
return unless ActiveRecord::Type::Boolean.new.cast(@data[:after_signup])
|
|
|
|
|
|
|
|
other_after_signup = CustomWizard::Template.list(setting: 'after_signup')
|
|
|
|
.select { |template| template['id'] != @data[:id] }
|
|
|
|
|
|
|
|
if other_after_signup.any?
|
|
|
|
errors.add :base, I18n.t("wizard.validation.after_signup", wizard_id: other_after_signup.first['id'])
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2020-11-03 01:24:20 +01:00
|
|
|
def validate_after_time
|
2022-01-31 10:18:04 +01:00
|
|
|
return unless ActiveRecord::Type::Boolean.new.cast(@data[:after_time])
|
|
|
|
|
|
|
|
if ActiveRecord::Type::Boolean.new.cast(@data[:after_signup])
|
|
|
|
errors.add :base, I18n.t("wizard.validation.after_signup_after_time")
|
|
|
|
return
|
|
|
|
end
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2020-11-03 01:24:20 +01:00
|
|
|
wizard = CustomWizard::Wizard.create(@data[:id]) if !@opts[:create]
|
2020-04-14 01:39:21 +02:00
|
|
|
current_time = wizard.present? ? wizard.after_time_scheduled : nil
|
2020-11-03 01:24:20 +01:00
|
|
|
new_time = @data[:after_time_scheduled]
|
2021-03-11 07:30:15 +01:00
|
|
|
|
2020-04-14 07:46:06 +02:00
|
|
|
begin
|
|
|
|
active_time = Time.parse(new_time.present? ? new_time : current_time).utc
|
|
|
|
rescue ArgumentError
|
|
|
|
invalid_time = true
|
|
|
|
end
|
2020-04-13 14:17:22 +02:00
|
|
|
|
2020-04-14 07:46:06 +02:00
|
|
|
if invalid_time || active_time.blank? || active_time < Time.now.utc
|
2020-11-09 04:32:36 +01:00
|
|
|
errors.add :base, I18n.t("wizard.validation.after_time")
|
2020-04-13 14:17:22 +02:00
|
|
|
end
|
|
|
|
end
|
2021-09-14 05:33:16 +02:00
|
|
|
|
2022-01-31 10:41:14 +01:00
|
|
|
def validate_liquid_template(object, type)
|
|
|
|
%w[
|
|
|
|
description
|
|
|
|
raw_description
|
|
|
|
placeholder
|
|
|
|
preview_template
|
|
|
|
post_template
|
|
|
|
].each do |field|
|
|
|
|
if template = object[field]
|
|
|
|
result = is_liquid_template_valid?(template)
|
|
|
|
|
|
|
|
unless "valid" == result
|
|
|
|
error = I18n.t("wizard.validation.liquid_syntax_error",
|
|
|
|
attribute: "#{object[:id]}.#{field}",
|
|
|
|
message: result
|
|
|
|
)
|
|
|
|
errors.add :base, error
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
def is_liquid_template_valid?(template)
|
|
|
|
begin
|
|
|
|
Liquid::Template.parse(template)
|
|
|
|
'valid'
|
|
|
|
rescue Liquid::SyntaxError => error
|
|
|
|
error.message
|
|
|
|
end
|
|
|
|
end
|
2021-03-11 07:30:15 +01:00
|
|
|
end
|