Class: TypedFormModel::ModelLoader
- Inherits:
-
Object
- Object
- TypedFormModel::ModelLoader
- Defined in:
- lib/typed_form_model/model_loader.rb
Overview
Builds a form instance from one or more source objects (AR models, OpenStructs, Hashes).
Two entry points with intentionally different semantics:
from_model(record) — single-source. The source segment of `from:` is
irrelevant (no ambiguity to dispatch on). Every
prop is read from `record` using its `from:`
rename or its own name.
from_models(sources) — multi-source. A dotted `from:` is required per
prop to pick the source; props without a dotted
`from:` are skipped.
In both cases the attribute segment of from: (or the Symbol form)
renames the source attribute, and a prop is skipped if the source
doesn't have the attribute at all (lets prop defaults fire). Edit-form
semantics: a source that has the attribute with a nil value still wins —
the form reflects the source.
Instance Method Summary collapse
-
#from_model(record, persisted: true, context: {}, props: nil) ⇒ Object
Single-source loader.
-
#from_models(sources, persisted: true, context: {}, props: nil) ⇒ Object
Multi-source loader.
-
#initialize(form_class) ⇒ ModelLoader
constructor
A new instance of ModelLoader.
Constructor Details
#initialize(form_class) ⇒ ModelLoader
Returns a new instance of ModelLoader.
23 24 25 |
# File 'lib/typed_form_model/model_loader.rb', line 23 def initialize(form_class) @form_class = form_class end |
Instance Method Details
#from_model(record, persisted: true, context: {}, props: nil) ⇒ Object
Single-source loader. Iterates every prop and reads it from record,
ignoring the source segment of from:. The attribute segment (or a
Symbol-form from:) is honoured for renames. props: (Array of
Symbols) restricts which props are pulled from the source; non-listed
props are skipped so their defaults fire.
32 33 34 35 36 37 38 39 40 41 42 43 44 |
# File 'lib/typed_form_model/model_loader.rb', line 32 def from_model(record, persisted: true, context: {}, props: nil) allowed = build_allowed_set(props) attrs = {} form_class.literal_properties.each do |prop| next if allowed && !allowed.include?(prop.name) = form_class.(prop.name) attr_name = (&.model_attribute(prop.name) || prop.name).to_sym next unless attribute_present?(record, attr_name) attrs[prop.name] = read_attribute(record, attr_name) end form_class.new(persisted: persisted, context: context, **attrs) end |
#from_models(sources, persisted: true, context: {}, props: nil) ⇒ Object
Multi-source loader. Each prop's metadata.model (parsed from the
source segment of a dotted from:) picks its source from sources.
Props with no source segment (or whose source isn't in sources) are
skipped — there's no implicit fallback when the caller is explicit
about having multiple sources.
props: (Array of Symbols) restricts which props are pulled across
sources; non-listed props are skipped so their defaults fire.
53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 |
# File 'lib/typed_form_model/model_loader.rb', line 53 def from_models(sources, persisted: true, context: {}, props: nil) allowed = build_allowed_set(props) attrs = {} form_class.literal_properties.each do |prop| next if allowed && !allowed.include?(prop.name) = form_class.(prop.name) next unless source = sources[.model] next unless source attr_name = .model_attribute(prop.name).to_sym next unless attribute_present?(source, attr_name) attrs[prop.name] = read_attribute(source, attr_name) end form_class.new(persisted: persisted, context: context, **attrs) end |