ListView / Modify Values and save

I think I encountered the same issue, but after losing a loooot of time :sob:, I figured out a very simple and unintuitive solution :sweat_smile:, a bit different from the one above. Hoping it saves you some time!

Short version: don't refer to listview, refer to the component directly to use any changeset.

Long version: below is the documentation that I would have loved to read before using the component :innocent:

Using a component's changeset (inside listview's scope)

Limits

  • Listview only exposes its data source's data (initial data), it does not expose the actual data from its children (components nested inside the listview, like forms, editable text etc.)
  • When you add any editable component inside a list view, you'll likely set-it up to use Listview data source, and very very likely edit the data... But when you update the data outside of Listview data source, you'll break data consistency, because...

Listview.data[i]componentInsideListView.data :see_no_evil:

Solution
Never use Listview.data, Listview.data{{i}}, {{item}} or {{i}}, directly use child.data like form.data or editableText.value with editable components.
And don't use GUI event handlers without specifically referring to child.data or child.value.

Why? if you refer to anything from listview, you're just referring to the data source. But if you use the component.data, as it's inside the component's scope, and not in list view's scope, you'll get the right data.

Querying a component's changeset (outside listview's scope)

Limit

  • Components inside Listviews are not accessible outside of the List view scope... so you can't actually call them in other queries or components :joy:

Solution

  • Use event handler + additional scope to expose the component real data.

  • Inside your update query, refer to the additional scope key created (it will throw an error as additional scope keys are only created at runtime :smiling_face_with_tear: for now at least...)

  • Don't forget to refresh the listview data source on success...

    • I guess we could specify ~ OnSuccess: form.clear() in additionalScope, but I couldn't understand the subtilities of it in my use case... with my query also having OnSuccess feature, and a form also having OnSuccess clear form...

ie: inside a form or an editable text that is inside a listview, create an event handler, choose script, pass the form.data through additional scope.

query.trigger({
  additionalScope: {
    formChangeSet: form.data
  }
})

In your query, just refer to {{formChangeSet}} to use the form real data, and on success, trigger your data source refresh.

4 Likes