I have a dropdown list as one of the columns in a repeating row, the items in the dropdown list come from a table in the database. right now from every repeating row, there is a seperate call to the server to populate the dropdown list. Any ideas on how to fix this. as the rows increase the load time is getting really slow
You should create one server function that searches for the items in the database and builds a list of dictionaries (not a list of rows), then return the full list to the client. By returning all the options at once the time will be the same (one round trip), regardless of the number of items.
Here are a few more suggestions: Suggestions to optimize performance
If you need more details, please post a clone link, so we can see what you are trying to do.
This i have allready done.
The problem seems to be that for each row instantiated in the repeating panel the row template init method is called and that method makes the call the to the server function to populate the dropdown list.
If the dropdown.items
contains a list of strings, then there is no reason for more calls to the server.
Perhaps your list contains row objects rather than strings?
here is a sample app of the functionality I am using
Are you using simple objects?
This can cause the extra server calls… Try unpacking all simple objects as a list/dict element before returning them to the client…
The server function is returning a list of strings.
You seem to be doing 9 server calls somehow?
the get colours server function
Can you post a clone link, so we can look at the code (careful: we will also see the content of your tables)?
yeah each of the nine records being displayed is making a call to the server to populate the select eye color dropdown list that becomes visible when the edit row button is clicked
clone link above and here it is again
This is a link to the app, not a clone link.
You can create a clone link by clicking on the gear, then “Publish app…”, then here:
It’s those calls to get the colour
that are the additional calls. Each row makes a call to the server before it displays (because the function is in the init method. So that’s why it takes so long to load…
Consider sending that data with the first server call…
As @stefano.menci and @stucork have suggested, you could, for example, return everything you need in a single server call on the form that has the repeating panel (not its template), then set its “items” property to your list of dicts/list of simple objects.
In the template form, “item” can now be bound accordingly to your dropdown component. I hope this helps and I’m not confusing the issue.
Ok - here’s a version that reduced it to 1 server call with minimal change to your code…
def __init__(self, **properties):
# Set Form properties and Data Bindings.
self.init_components(**properties)
#colors = anvil.server.call('get_eye_colors')
#print(colors)
people, colors = anvil.server.call('get_people_and_colors')
for person in people:
person.update({"Colors": colors})
self.repeating_panel_person.items = people
self.drop_down_eye_color.items = colors
Server
@anvil.server.callable
def get_people_and_colors():
people = get_people()
colors = get_eye_colors()
return people, colors
thanks for that, my main issue is in the row template, with setting self.drop_down_edit_eye_color.items. its this call that is being made for each row in the repeating panel. i am unsure how to initialise that dropdown list only once. it seems that because each row in the repeating panel is a new instance of the template, the init method is called once for each row.
Yes you are correct. Each template row is fully repeated. I’m not aware of any way to set the items of all dropdown components in a repeating panel without dealing with each row template separately at some level (e.g., the inits).
it is not the inits thats making it slow, it the call to the server in each inits, one possibility i was thinking of is storing the list which the dropdown.items is set to in an app global variable, so i that way the inits will just be accessing client side code instead of going over the wire.
As the others mentioned, there is only one server call. Everything your dropdowns need is already in the client before the dropdowns are populated. As long as you are not returning actual database row objects, everything will be fully available in the client.