Announcement

Collapse
No announcement yet.
X
  • Filter
  • Time
Clear All
new posts

    SelectItem's checks are not persistent when using an option data source and grouping


    I've found an odd behavior that there must be a better solution for.

    I'm attempting to allow the user to select a value of a field from a list of choices. As the value of the field appears multiple times in the data base, I'm using the SelectItem.setOptionFilterContext(dsRequestProperties) to group by the field in order to get records with distinct values. When I pull down the SelectItems pick list, I can check a few items and see them displayed correctly in the SelectItem's text field. If I revisit the pull down to modify my selections, the choices are no longer checked. Instead, the very first item is checked and my original choices have dissapeared.

    A coworker, familiar with when the behavior was introduced, said I needed a DataSource with a primary key. I obviously can't group on a Primary Key... so

    Work around 1:
    For a simplified case, I was able to include the data source's primary key in a MAX summary function. See work around 1 in the code snippet.

    Work around 2:
    For a data base view, with no primary key, I was able to define a data source field that used a custom select expression to generate a unique string as a fake primary key. I put that code in the comment of "Work around 2"

    In debugging, I noticed that the SQL generated for the optionDataSource values wraps the query I create for the pick list in an other query used to generate a rowID. It would be ideal to use this as a fake primary key or what ever the smargGWT frame work is requiring as a unique vale here. I could not find a way do to so. Is there an undocumented way to do this?

    i.e.
    SELECT *
    FROM (SELECT *, ROW_NUMBER() OVER (ORDER BY someField) AS rowID
    FROM (SELECT TOP 100 PERCENT Some_Table.someField FROM SomeTable WHERE ('1'='1')
    GROUP BY Some_Table.someField
    ORDER BY Some_Table.someField)
    x) y WHERE y.rowID BETWEEN 1 AND 7


    Although the example code is simplified, my end goal is to allow the user to build a criteria from the main data base view and a hand full of other tables and smaller ds.xml defined views. The main DB defined view contains most of the fields in our entire data base definition. To complicate things further, the DataSource describing the view is created dynamically. Tables with a many to one relationship with the view have datasource fields added in dynamically. This enable us to multiply joining the source table with the view using custom server side DMI code. Custom <field> attributes allows us to efficiently use the referring table instead of the heavy weight view to construct SelectItem pick lists for picking value possibilities. Note: Doing a DISTINCT operation on such a potentially large view is very time consuming. As you can imagine going through our Data Base definition adding fake PK's, or DSField attributes for using one method vs another seems overly complicated and a bit of a kludge.

    Is there a more generic solution that I'm missing here?

    This code snippet exemplifies the disappearing check box issue.

    // to test, change the DataSource and Field to one that exists in BEER
    String someDataSource = "Some_Table";
    String someField = "someField";

    final DynamicForm form = new DynamicForm();
    form.setWidth(200);
    form.setHeight(40);
    form.setNumCols(1);

    final SelectItem selectItem = new SelectItem("dissapearingSelections");
    selectItem.setWidth(200);
    selectItem.setMultiple(true);
    selectItem.setMultipleAppearance(MultipleAppearance.PICKLIST);
    selectItem.setAutoFetchData(true);

    selectItem.setOptionDataSource(DataSource.getDataSource(someDataSource));
    selectItem.setValueField(someField);
    selectItem.setDisplayField(someField);


    // Work around 1 (small table)
    // Map<String,SummaryFunctionType> summaryFunctions = new HashMap<String,SummaryFunctionType>();
    // summaryFunctions.put("PK_Test_Bench", SummaryFunctionType.MAX);
    // dsRequestProps.setSummaryFunctions(summaryFunctions);



    // Work around 2 (Large view with no PK)
    // This requires the addition of the following fake PK definition to manufacture a unique number
    // <field name="PK_Fake" title="fake PK" type="string" primaryKey ="true"
    // customSelectExpression="NEWID()" />

    // Map<String,SummaryFunctionType> summaryFunctions = new HashMap<String,SummaryFunctionType>();
    // summaryFunctions.put("PK_Fake", SummaryFunctionType.MAX);
    // dsRequestProps.setSummaryFunctions(summaryFunctions);



    final DSRequest dsRequestProps = new DSRequest();
    dsRequestProps.setGroupBy(someField);

    // The query tries to sort by the tabl's PK if an alternate sort is not present. However the setGroupBy()
    // composes an inner query that does not expose the PK.
    SortSpecifier[] sortSpecArray;
    sortSpecArray = new SortSpecifier[] {
    new SortSpecifier(someField, SortDirection.ASCENDING)
    };
    dsRequestProps.setSortBy(sortSpecArray);

    selectItem.setOptionFilterContext(dsRequestProps);

    form.setItems(selectItem);
Working...
X