Class: Phlex::Reactive::Reply
- Inherits:
-
Object
- Object
- Phlex::Reactive::Reply
- Defined in:
- lib/phlex/reactive/reply.rb
Overview
A component-bound facade over Response — the surface an action body uses to control its reply. Component#reply returns one, so an action writes
reply.replace.flash(:error, msg)
instead of
Phlex::Reactive::Response.replace(self).flash(:error, msg)
Two warts disappear: there is no constant to qualify (reply is a method,
resolved on the component — so a namespaced component needs no
Response = … alias) and no self to thread (the component is bound).
Reply is NOT a Response and does NOT subclass one: each verb forwards to the Response class method, supplying the bound component as the subject, and returns the real, frozen Response value the endpoint already honors. So immutability, chaining (.flash/.stream/.also_update/.also_replace), and render_self? are inherited untouched — and there is no "verb after a chained Response" asymmetry, because the chain is plain Response all the way down.
Response remains the public value object (it's what the endpoint reads); it is simply an internal detail you rarely name directly now.
Instance Method Summary collapse
-
#append(name, model) ⇒ Object
Reactive collections (issue #35) — add/remove a row in a declared reactive_collection, emitting the row stream + the count companion + the empty-state toggle as ONE Response.
-
#initialize(component) ⇒ Reply
constructor
A new instance of Reply.
-
#morph ⇒ Object
Re-render in place via Idiomorph (method="morph") — keeps focus + caret.
- #prepend(name, model) ⇒ Object
-
#redirect(url) ⇒ Object
Client-side full navigation (Turbo.visit).
-
#remove(name = UNSET, model = UNSET) ⇒ Object
Two forms: reply.remove # remove the bound component's own element reply.remove(:items, model) # remove a collection row + count + empty.
-
#replace(morph: false) ⇒ Object
Re-render in place.
-
#streams(*strings) ⇒ Object
Self-targeting again: emit exactly these streams with a TOKEN-ONLY refresh (issue #30) — partial/per-field update, NO full-self replace, so the component's live inputs survive.
-
#update ⇒ Object
Morph only inner HTML (preserves the root element + its token attr).
-
#with(*strings) ⇒ Object
Escape hatch / multi-stream root: zero or more raw turbo-stream strings.
Constructor Details
#initialize(component) ⇒ Reply
Returns a new instance of Reply.
34 35 36 |
# File 'lib/phlex/reactive/reply.rb', line 34 def initialize(component) @component = component end |
Instance Method Details
#append(name, model) ⇒ Object
Reactive collections (issue #35) — add/remove a row in a declared reactive_collection, emitting the row stream + the count companion + the empty-state toggle as ONE Response. The bound component is the container (it carries the declaration + size resolver).
def add_item(...) = (item = @list.items.create!(...); reply.append(:items, item))
def remove_item(id:) = (@list.items.find(id).destroy!; reply.remove(:items, id))
model is the row's record; remove also accepts the row's dom-id string.
65 66 67 |
# File 'lib/phlex/reactive/reply.rb', line 65 def append(name, model) Response.collection_append(@component, name, model) end |
#morph ⇒ Object
Re-render in place via Idiomorph (method="morph") — keeps focus + caret.
47 48 49 |
# File 'lib/phlex/reactive/reply.rb', line 47 def morph Response.morph(@component) end |
#prepend(name, model) ⇒ Object
69 70 71 |
# File 'lib/phlex/reactive/reply.rb', line 69 def prepend(name, model) Response.collection_prepend(@component, name, model) end |
#redirect(url) ⇒ Object
Client-side full navigation (Turbo.visit). Pass a *_url.
85 86 87 |
# File 'lib/phlex/reactive/reply.rb', line 85 def redirect(url) Response.redirect(url) end |
#remove(name = UNSET, model = UNSET) ⇒ Object
Two forms:
reply.remove # remove the bound component's own element
reply.remove(:items, model) # remove a collection row + count + empty
76 77 78 79 80 |
# File 'lib/phlex/reactive/reply.rb', line 76 def remove(name = UNSET, model = UNSET) return Response.remove(@component) if name.equal?(UNSET) Response.collection_remove(@component, name, model) end |
#replace(morph: false) ⇒ Object
Re-render in place. morph: true morphs the subtree (preserves the
focused input + caret) instead of an outerHTML swap — see #morph.
42 43 44 |
# File 'lib/phlex/reactive/reply.rb', line 42 def replace(morph: false) Response.replace(@component, morph:) end |
#streams(*strings) ⇒ Object
Self-targeting again: emit exactly these streams with a TOKEN-ONLY refresh (issue #30) — partial/per-field update, NO full-self replace, so the component's live inputs survive. The bound component supplies the token.
97 98 99 |
# File 'lib/phlex/reactive/reply.rb', line 97 def streams(*strings) Response.streams(@component, *strings) end |