I have a working SmarGWT datasource that brings back nested JSON as follows:
{username:"tom",password:"pwd",userType:{id:1,name:"admin user type"}}
The sample DataSource looks like:
DataSourceTextField usernameField = new DataSourceTextField("username", "User Name");
DataSourceTextField passwordField = new DataSourceTextField("password", "Password");
DataSourceIntegerField userTypeIdField = new DataSourceIntegerField ("id", "User Type Id");
userTypeIdField.setValueXPath("userType/id");
I can then tie this DS to a listgrid and/or form, and that works ok to display data.
If I create a DynamicForm tied to this same DS, I want to create a new record. I have a username and password textbox which are fine, and I have a SelectItem which gives me back the id to the usertype (1 for Admin, 2 for Oher).
When we get data from this form and look at the JSON sent from the form to the DS, it looks like:
{username:"newuser",password:"newpwd",userTypeId:1}
but I would prefer:
{username:"newuser",password:"newpwd",userType:{id:1}}
because this JSON version of the data would translate nicely into the object I want to send to the controller, which would then file this object. But I do not know if this is possible with the DynamicForm, and/or the SelectItem.
One possibility which I know would work would be to look at the JSON when I send it back for an insert or update. In the transformRequest, I could manually tweak the JSON to remove userTypeId:1 and add userType:{id:1} in it's place.
Or, I could look at a Nested DataSource which I haven't done in a long time.
I am just not sure from the SmarGWT perspective which would be a better mainstream solution.
If I need any more information, let me know, and I will update the question. Thanks in advance for any help!
This was super simple. First in the datasource for UserType, I presume this is very simple. You have usertypeId, userTypeName, UserTypeDescription as follows:
private DataSourceIntegerField userTypeIdField;
private DataSourceTextField userTypeNameField;
private DataSourceTextField userTypeCodeField;
Now let's say you have a datasource for the user, you probably have fields for the userId, username, password, etc, and if UserType is part of that, then you would want to do this:
private DataSourceField userTypeField; // notice it is a DataSourcField
As for the declaration:
userTypeField = new DataSourceField();
userTypeField.setTitle("User Type");
userTypeField.setName("userType");
userTypeField.setTypeAsDataSource(UserTypeDataSource.getInstance());
This is a nice way to do it, if you know you are getting nested JSON or XML data. I have also known cases where, someone has flattened a nested JSON format to the DataSource bu using the XPath seting of a datasourcefield.
On the SmartGWT DynamicForm side, you can take fields and add an setDataPath binding also, such as the following:
userTypeField.setName("userType");
userTypeField.setPickListWidth(210);
userTypeField.setTitle("User Type");
userTypeField.setOptionDataSource(userTypeDS);
userTypeField.setRequired(true);
userTypeField.setDisplayField("userTypeName");
userTypeField.setValueField("userTypeId");
userTypeField.setDataPath("userType/userTypeId");
So, if you had a User DynamicForm, and wanted to set a UserType, the DataPath would preserve the nested JSON, so you'd have something like:
user:
{"userId":1,"username":"test","password":"password",
"userType":{"userTypeId":2}
}
This may seem like it is so simple now, but maybe this will help someone else out.