We are making heavy use of Kendo UI Grids in our AngularJS-based application.
In some views, we may have up to 6 different kendo grids showing data. We are using remote live scrolling in some and others we are loading all the data (when dataset size is small).
**All of our grids are READ-ONLY. In other words, users are just viewing data, not editing, modifying, etc. rows**
We have discovered that each *ROW* in each table has an angular $watcher attached to it for **each** column value.
In the example above, **TWO** angular watches will be created for "id" and "hostname" for **each row**.
If our table has 200 rows x 2 watchers = 400 angular watchers added to the angular $digest cycle (which is run 2x every time there's an "event" that triggers the digest cycle).
We understand that for **editable** grids these watches may be required to correctly perform two-way data-binding. However, since our grids are read-only we do **NOT** need these watches created (and they are impacting our application's performance).
We have tried setting "editable: false" on both the grid options as well as individual columns, but it seems to have no affect.
Is there any way to prevent Kendo from creating all these **unnecessary** AngularJS watches and scopes?
12 Answers, 1 is accepted
As a follow-up, imagine our scenario above:
- 6 Kendo Grids
- 200 rows per grid
- 5 columns per grid
= 6,000 AngularJS watches added to the $digest cycle.
AngularJS documentation suggests keeping # of watches < 2,000 for good application performance (and the fewer the better).
The Kendo UI directives create watches (call $watch manually) in the following cases:
When creating a data source - to update the widget when the developer manually adds, removes or updates items in the array which acts as a data source.
All other watches are created internally by AngularJS when compiling HTML ($compile). For example the Kendo UI grid compiles every row to allow developers to use angular directives in column templates.
If you're still interested in this, I was able to solve this by not using kendo-grid directive, but creating the grid from controller instead, i.e.:
In html: <div id="grid"></div>
In controller: $("#grid").kendoGrid(gridOptions);
As my colleague Atanas explained, this is not in control of the Kendo UI team. Most of the watchers are created internally by AngularJS when compiling HTML ($compile). And this does not change if the Grid is editable or not.
To generally improve the performance I can suggest using a Grid with virtual scrolling:
Or using the pageable Grid with a smaller pageSize:
Telerik by Progress
+1 on James comment. We actually switched to a competing product b/c Kendo's lack of one-way binding on Kendo grids made our UI unusable.
I understand on editable grids, Angular is used to watch and update the two-way binding. But on one way grids, you just need DOM elements displaying the data...no need for $compile or watches or bindings whatsoever.
If you're not sure what we mean, ask Todd Motto. He knows exactly why large Kendo Angular-based grids could kill browser performance, especially if they only need to read-only but are not.
I'm sorry to hear that this is a showstopper when using the Kendo UI Grid with Angular.
After consulting with the Lead developer of the Kendo UI Grid, I can confirm that for now, we do not plan to change the Grid behaviour because even of the Grid is not editable, its data can be changed from outside(form for example) and this will also require watchers.
If the requirement is to have a completely static data in the Grid, which cannot be changed from the Grid or outside the Grid, I can suggest submitting a feature request in our UserVoice portal describing the desired functionality. Then based on its popularity among the community we may implement it in a future release:
Apologies for the inconvenience this may cause you.
Telerik by Progress
We discovered this issue in production. We had a grid that loads all data and the grid had 37,000 watchers with 2000 rows. Fortunately there is a simple workaround that allows you to have one time binding. Just specify the column template. You can use either Angular one time binding or Telerik's data binding syntax to get rid of all of the watchers.
Thank you for sharing this with the Kendo UI community.
The workaround does not look complex and it can be easily applied which can reduce the performance issues.
We greatly appreciate it.
Telerik by Progress
Mac P -
It sounds like Marius has a valid solution to staying with Kendo if you're ok overriding templates. If you're using Kendo's other components, it may be worthwhile doing that to stay within the "ecosystem" as well as provide your users with a common look and feel (UX experience) across the UI.