I'm struggling with an issue that appeared in our (rather large) SmartGWT application after a SmartGWT library upgrade. We upgraded from one of the first SmartGWT 4.0 releases to a recent version (v9.0p_2015-08-12/LGPL Development Only (built 2015-08-12)). Before the upgrade we did not see this issue. Also tried SmartGWT version 5.0 which shows the same behavior. GWT is version 2.5.1.
When running in Dev Mode everything works fine. However when compiling the code to JS and deploying the .war we see an issue with our TreeGrids: The very first time one is shown everything works fine, then after it has been destroyed and re-created it 'hangs' as if there are no records (The 'Loading..' message is displayed). This failure also happens when an ListGrid with DataSource has been shown previously. The log file shows both the "Destroying Treegrid" and "Destroying datasource" messages, so things seem to get cleaned up correctly. We use a TabSet to destroy (tab close) and re-create (tab open) the widget.
It starts to get really tricky when trying to reproduce this issue. When I solely add a TabSet and the below code to the rootpanel and not initialize anything else, it works. Even destroying (tab close) and re-creating (tab open) works. However when the TreeGrid has been embedded into our application it only works once, and when created for a second time the loading hangs with the above message.
Obviously I cannot post our whole application here, but it seems like something is influencing the behavior of the Treegrid. When another TreeGrid or ListGrid (both containing a datasource) have displayed the next instance of TreeGrid hangs. No further logging or exceptions (I use the UncaughtExceptionHandler) are shown either.
Its a bit of a long shot, but does anybody have any clue what might cause this behavior?
The used code is pretty much identical to the showcase example:
When running in Dev Mode everything works fine. However when compiling the code to JS and deploying the .war we see an issue with our TreeGrids: The very first time one is shown everything works fine, then after it has been destroyed and re-created it 'hangs' as if there are no records (The 'Loading..' message is displayed). This failure also happens when an ListGrid with DataSource has been shown previously. The log file shows both the "Destroying Treegrid" and "Destroying datasource" messages, so things seem to get cleaned up correctly. We use a TabSet to destroy (tab close) and re-create (tab open) the widget.
It starts to get really tricky when trying to reproduce this issue. When I solely add a TabSet and the below code to the rootpanel and not initialize anything else, it works. Even destroying (tab close) and re-creating (tab open) works. However when the TreeGrid has been embedded into our application it only works once, and when created for a second time the loading hangs with the above message.
Obviously I cannot post our whole application here, but it seems like something is influencing the behavior of the Treegrid. When another TreeGrid or ListGrid (both containing a datasource) have displayed the next instance of TreeGrid hangs. No further logging or exceptions (I use the UncaughtExceptionHandler) are shown either.
Its a bit of a long shot, but does anybody have any clue what might cause this behavior?
The used code is pretty much identical to the showcase example:
Code:
final TestDS dataSource = TestDS.getInstance(); final TreeGrid treeGrid = new TreeGrid() { @Override public void destroy() { logger.info("Destroying Treegrid"); super.destroy(); dataSource.destroy(); } }; treeGrid.setLoadDataOnDemand(false); treeGrid.setWidth(500); treeGrid.setHeight(400); treeGrid.setDataSource(dataSource); treeGrid.setNodeIcon("icons/16/person.png"); treeGrid.setFolderIcon("icons/16/person.png"); treeGrid.setAutoFetchData(true); TreeGridField nameField = new TreeGridField("Name", 150); TreeGridField jobField = new TreeGridField("Job", 150); TreeGridField salaryField = new TreeGridField("Email"); treeGrid.setFields(nameField, jobField, salaryField); treeGrid.addDataArrivedHandler(new DataArrivedHandler() { public void onDataArrived(DataArrivedEvent event) { treeGrid.getData().openAll(); } }); //load data TreeNode newRecord = new TreeNode(); newRecord.setAttribute("EmployeeId", 2); newRecord.setAttribute("ReportsTo", 1); newRecord.setAttribute("Name", "Jan"); TreeNode newRecord2 = new TreeNode(); newRecord2.setAttribute("EmployeeId", 3); newRecord2.setAttribute("ReportsTo", 2); newRecord2.setAttribute("Name", "Piet"); TreeNode newRecord3 = new TreeNode(); newRecord3.setAttribute("EmployeeId", 4); newRecord3.setAttribute("ReportsTo", 3); newRecord3.setAttribute("Name", "Klaas"); newRecord3.setAttribute("Job", "jobdescriptioooon"); newRecord3.setAttribute("Email", "jan@ns.nl"); dataSource.setCacheData(newRecord, newRecord2, newRecord3); return treeGrid;
Code:
public class TestDS extends DataSource { private Logger logger = Logger.getLogger("TestDS"); public static TestDS getInstance() { return new TestDS(); } public TestDS() { setTitleField("Name"); DataSourceTextField nameField = new DataSourceTextField("Name", "Name", 128); DataSourceIntegerField employeeIdField = new DataSourceIntegerField("EmployeeId", "Employee ID"); employeeIdField.setPrimaryKey(true); employeeIdField.setRequired(true); DataSourceIntegerField reportsToField = new DataSourceIntegerField("ReportsTo", "Manager"); reportsToField.setRequired(true); reportsToField.setForeignKey(getID() + ".EmployeeId"); reportsToField.setRootValue("1"); DataSourceTextField jobField = new DataSourceTextField("Job", "Title", 128); DataSourceTextField emailField = new DataSourceTextField("Email", "Email", 128); setFields(nameField, employeeIdField, reportsToField, jobField, emailField); setClientOnly(true); } @Override public void destroy() { logger.info("Destroying datasource"); super.destroy(); } }
Comment