Class: Dry::Schema::MessageCompiler Private

Inherits:
Object
  • Object
show all
Extended by:
Initializer
Includes:
Extensions::Hints::MessageCompilerMethods
Defined in:
lib/dry/schema/message_compiler.rb,
lib/dry/schema/message_compiler/visitor_opts.rb

This class is part of a private API. You should avoid using this class if possible, as it may be removed or be changed in the future.

Defined Under Namespace

Classes: VisitorOpts

Constant Summary collapse

DEFAULT_PREDICATE_RESOLVERS =

This constant is part of a private API. You should avoid using this constant if possible, as it may be removed or be changed in the future.

Hash
.new(resolve_predicate).update(key?: resolve_key_predicate).freeze
EMPTY_OPTS =

This constant is part of a private API. You should avoid using this constant if possible, as it may be removed or be changed in the future.

VisitorOpts.new

Constants included from Extensions::Hints::MessageCompilerMethods

Extensions::Hints::MessageCompilerMethods::HINT_OTHER_EXCLUSION, Extensions::Hints::MessageCompilerMethods::HINT_TYPE_EXCLUSION

Instance Attribute Summary collapse

Attributes included from Extensions::Hints::MessageCompilerMethods

#hints

Instance Method Summary collapse

Methods included from Extensions::Hints::MessageCompilerMethods

#exclude?, #filter, #hints?, #visit_each

Constructor Details

#initialize(messages, options = EMPTY_HASH) ⇒ MessageCompiler

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Returns a new instance of MessageCompiler.



43
44
45
46
47
# File 'lib/dry/schema/message_compiler.rb', line 43

def initialize(messages, options = EMPTY_HASH)
  super
  @options = options
  @default_lookup_options = options[:locale] ? { locale: locale } : EMPTY_HASH
end

Instance Attribute Details

#default_lookup_optionsObject (readonly)

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



40
41
42
# File 'lib/dry/schema/message_compiler.rb', line 40

def default_lookup_options
  @default_lookup_options
end

#optionsObject (readonly)

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



38
39
40
# File 'lib/dry/schema/message_compiler.rb', line 38

def options
  @options
end

Instance Method Details

#call(ast) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



57
58
59
60
61
62
# File 'lib/dry/schema/message_compiler.rb', line 57

def call(ast)
  current_messages = EMPTY_ARRAY.dup
  compiled_messages = ast.map { |node| visit(node, EMPTY_OPTS.dup(current_messages)) }

  MessageSet[compiled_messages, failures: options.fetch(:failures, true)]
end

#lookup_options(arg_vals:, input:) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



166
167
168
169
170
171
# File 'lib/dry/schema/message_compiler.rb', line 166

def lookup_options(arg_vals:, input:)
  default_lookup_options.merge(
    arg_type: arg_vals.size == 1 && arg_vals[0].class,
    val_type: input.equal?(Undefined) ? NilClass : input.class
  )
end

#message_text(template, tokens, options) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



174
175
176
177
178
179
180
181
# File 'lib/dry/schema/message_compiler.rb', line 174

def message_text(template, tokens, options)
  text = template[template.data(tokens)]

  return text unless full

  rule = options[:path]
  "#{messages.rule(rule, options) || rule} #{text}"
end

#message_tokens(args) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



184
185
186
187
188
189
190
191
192
193
194
195
196
# File 'lib/dry/schema/message_compiler.rb', line 184

def message_tokens(args)
  args.each_with_object({}) do |arg, hash|
    case arg[1]
    when Array
      hash[arg[0]] = arg[1].join(LIST_SEPARATOR)
    when Range
      hash["#{arg[0]}_left".to_sym] = arg[1].first
      hash["#{arg[0]}_right".to_sym] = arg[1].last
    else
      hash[arg[0]] = arg[1]
    end
  end
end

#message_typeObject

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



138
139
140
# File 'lib/dry/schema/message_compiler.rb', line 138

def message_type(*)
  Message
end

#visit(node, opts = EMPTY_OPTS.dup) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



65
66
67
# File 'lib/dry/schema/message_compiler.rb', line 65

def visit(node, opts = EMPTY_OPTS.dup)
  __send__(:"visit_#{node[0]}", node[1], opts)
end

#visit_and(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



86
87
88
89
90
91
92
93
94
# File 'lib/dry/schema/message_compiler.rb', line 86

def visit_and(node, opts)
  left, right = node.map { |n| visit(n, opts) }

  if right
    [left, right]
  else
    left
  end
end

#visit_failure(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



70
71
72
73
# File 'lib/dry/schema/message_compiler.rb', line 70

def visit_failure(node, opts)
  rule, other = node
  visit(other, opts.(rule: rule))
end

#visit_hintObject

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



76
77
78
# File 'lib/dry/schema/message_compiler.rb', line 76

def visit_hint(*)
  nil
end

#visit_implication(node, *args) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



154
155
156
157
# File 'lib/dry/schema/message_compiler.rb', line 154

def visit_implication(node, *args)
  _, right = node
  visit(right, *args)
end

#visit_key(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



143
144
145
146
# File 'lib/dry/schema/message_compiler.rb', line 143

def visit_key(node, opts)
  name, other = node
  visit(other, opts.(path: name))
end

#visit_namespace(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



110
111
112
113
# File 'lib/dry/schema/message_compiler.rb', line 110

def visit_namespace(node, opts)
  ns, rest = node
  self.class.new(messages.namespaced(ns), options).visit(rest, opts)
end

#visit_not(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



81
82
83
# File 'lib/dry/schema/message_compiler.rb', line 81

def visit_not(node, opts)
  visit(node, opts.(not: true))
end

#visit_or(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



97
98
99
100
101
102
103
104
105
106
107
# File 'lib/dry/schema/message_compiler.rb', line 97

def visit_or(node, opts)
  left, right = node.map { |n| visit(n, opts) }

  if [left, right].flatten.map(&:path).uniq.size == 1
    Message::Or.new(left, right, proc { |k| messages.translate(k, default_lookup_options) })
  elsif right.is_a?(Array)
    right
  else
    [left, right].flatten.max
  end
end

#visit_predicate(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
# File 'lib/dry/schema/message_compiler.rb', line 116

def visit_predicate(node, opts)
  predicate, args = node

  tokens = message_tokens(args)
  path, *arg_vals, input = predicate_resolvers[predicate].(args, opts)

  options = opts.dup.update(
    path: path.last, **tokens, **lookup_options(arg_vals: arg_vals, input: input)
  ).to_h

  template = messages[predicate, options] || raise(MissingMessageError, path)

  text = message_text(template, tokens, options)

  message_type(options)[
    predicate, path, text,
    args: arg_vals,
    input: input
  ]
end

#visit_set(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



149
150
151
# File 'lib/dry/schema/message_compiler.rb', line 149

def visit_set(node, opts)
  node.map { |el| visit(el, opts) }
end

#visit_xor(node, opts) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



160
161
162
163
# File 'lib/dry/schema/message_compiler.rb', line 160

def visit_xor(node, opts)
  left, right = node
  [visit(left, opts), visit(right, opts)].uniq
end

#with(new_options) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



50
51
52
53
54
# File 'lib/dry/schema/message_compiler.rb', line 50

def with(new_options)
  return self if new_options.empty?

  self.class.new(messages, options.merge(new_options))
end