Announcement

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

    MultiComboBoxItem case-insenstive value

    Hi Isomorphic,

    I am using the MultiComboBoxItem using an option datasource.

    The values are case-insensitive and can be modified externally through an API.

    If we end up with a value of A1, but the fetch using the option operation id returns value of a1, the form item displays no value. Doesn't seem to treat A1 as a match to a1.

    I don't want to allow unknown values, and can't seem to find another option that applies here, and I already thought everything defaulted to case-insensitive.

    Can you suggest anything here?

    Thank you


    #2
    Indeed, the default is case-insensitive match, as you can see in the sample:

    https://smartclient.com/smartclient-...tiComboBoxItem

    First step would be to look at the textMatchStyle in the request (or the "operator" property if the criteria are AdvancedCriteria). If that's right, you have a server-side rather than client-side problem.

    If the problem is server-side, we would look into any kind of criteria processing logic you might have added to the DataSource.

    Comment


      #3
      There is no criteria in this case.

      Here is the fetch that is happening for the option datasource when form is loaded, and the response that includes the properly matching value.

      The only difference is the form value has an uppercase first letter, and the response value has a lowercase first letter.

      We do use this block of code

      Code:
      pickListProperties.addFetchDataHandler(event -> {
                  if (event == null) return;
                  DSRequest request = event.getRequestProperties();
                  if (request != null) request.setTextMatchStyle(TextMatchStyle.STARTS_WITH);
              });
      properties.setPickListProperties(pickListProperties);
      Request

      Code:
      {
          xxxx
          operationType:"fetch",
          operationId:"findxxxx",
          componentId:"xxxx",
          data:{
              fieldName:"Value"
          },
          textMatchStyle:"exact",
          callback:{
              target:[MultiComboBoxItem ID:isc_xxxx:xxxx],
              methodName:"fetchMissingValueReply"
          },
          showPrompt:false,
          oldValues:{
              fieldName:"Value"
          },
          requestId:"xxxx$62717",
          internalClientContext:{
              newValue:{
                  "0":"Value",
                  Class:"Array",
                  localeStringFormatter:"toString"
              },
              filterLocally:{
              },
              targetField:"fieldName",
              fetchingMissingValues:{
              }
          },
          fallbackToEval:false,
          componentContext:"xxxx",
          lastClientEventThreadCode:"XRP6",
          bypassCache:true,
          dataProtocol:"getParams"
      }
      Response

      Code:
      {
          affectedRows:0,
          data:[
              {
                  ....
                  fieldName:"value"
              }
          ],
          endRow:1,
          invalidateCache:false,
          isDSResponse:true,
          operationType:"fetch",
          startRow:0,
          status:0,
          totalRows:1
      }

      Comment


        #4
        For more information on how this form item is configured, you can refer to this post here.

        https://forums.smartclient.com/forum...ticomboboxitem

        Comment


          #5
          I noticed that in the showcase, the same value, difference case, is treated as a different value.

          Click image for larger version

Name:	duplicate.png
Views:	107
Size:	12.0 KB
ID:	269893

          Comment


            #6
            OK, lots of problems here, we'll go one-by-one:

            1. you do have criteria - that's the "data" part of the request

            2. you can't use FetchDataHandler to try to modify an in-flight request. The main problem here is that if the component thinks the textMatchStyle is "substring" or whatever, but you actually swapped in "startsWith" on the fly, then local filtering won't match server filtering and everything breaks. This should be set via comboBoxItem.textMatchStyle instead.

            3. the request you showed is not a search request. Note how it has a callback of "fetchMissingValueReply": this is part of the FormItem.fetchMissingValues behavior, and its purpose is to get the displayValue for a given stored value (see valueField and displayField docs). So, it's correct that it has textMatchStyle:"exact", since values for the valueField must be unique - there's no way for the UI to work if this basic rule is violated

            We suspect that last comment (about valueField having to be unique) may be the problem. To understand what is supposed to happen here:

            1. the UI makes a request for matching entries using the end user's entered value (if present). This is generally "startsWith" or "substring" search. You haven't shown such a request so far, so it's not clear if there's a problem at that layer, but your attempt to change the textMatchStyle (#1) is definitely wrong and should be fixed

            2. the server's response is a set of Records which must minimally have a value for the valueField and for the displayField in each Record

            3. if the user picks something, the MultiComboBoxItem's stored value - what you get if you call getValue() or dynamicForm.getValues() - is a value for the valueField. This value must be unique (there's no other way it could work) and is case-sensitive. Generally, this is a primaryKey or other identifier.

            4. if a MultiComboBoxItem (MCBI) is created already having a value, the fetchMissIngValues subsystem will ask the server for the displayField value corresponding to the valueField values that the MCBI was created with

            Hopefully this clarifies what you're seeing. If you need some more help, it would be good to see a specific flow that is going wrong, along with the settings and the requests involved in that flow.

            Comment


              #7
              Hi Isomorphic,

              Thank you for the follow-up.

              1. you do have criteria - that's the "data" part of the request
              What I meant by no criteria was there was no default pick list criteria or server side criteria processing logic like you were inquiring about.

              2. you can't use FetchDataHandler to try to modify an in-flight request. The main problem here is that if the component thinks the textMatchStyle is "substring" or whatever, but you actually swapped in "startsWith" on the fly, then local filtering won't match server filtering and everything breaks. This should be set via comboBoxItem.textMatchStyle instead.
              OK, we have removed that in-flight request modification.

              3. the request you showed is not a search request. Note how it has a callback of "fetchMissingValueReply": this is part of the FormItem.fetchMissingValues behavior, and its purpose is to get the displayValue for a given stored value (see valueField and displayField docs). So, it's correct that it has textMatchStyle:"exact", since values for the valueField must be unique - there's no way for the UI to work if this basic rule is violated
              The problem isn't with the search request for us, the problem is with displaying an existing record with a value that matches case-insensitive.
              The value can be updated externally through an another interface, and this value is case-insensitive. The datasource may have a value of value1, so any selection from the Ux would end up with value1 in the record, however, because it can be modified externally without the use of the Ux, the record could end up with a value of Value1, which is still valid.

              We suspect that last comment (about valueField having to be unique) may be the problem. To understand what is supposed to happen here:

              1. the UI makes a request for matching entries using the end user's entered value (if present). This is generally "startsWith" or "substring" search. You haven't shown such a request so far, so it's not clear if there's a problem at that layer, but your attempt to change the textMatchStyle (#1) is definitely wrong and should be fixed

              2. the server's response is a set of Records which must minimally have a value for the valueField and for the displayField in each Record

              3. if the user picks something, the MultiComboBoxItem's stored value - what you get if you call getValue() or dynamicForm.getValues() - is a value for the valueField. This value must be unique (there's no other way it could work) and is case-sensitive. Generally, this is a primaryKey or other identifier.

              4. if a MultiComboBoxItem (MCBI) is created already having a value, the fetchMissIngValues subsystem will ask the server for the displayField value corresponding to the valueField values that the MCBI was created with

              Hopefully this clarifies what you're seeing. If you need some more help, it would be good to see a specific flow that is going wrong, along with the settings and the requests involved in that flow.
              This might explain the behavior, yes.
              The valueField we are using here is unique case-insensitive, meaning, for example, a record with valueField=Value1 cannot coexist with valueField=value1, and Value1 is considered equal to value1.
              If the existing record has a field selection value of "Value1" (modified externally) and the datasource has a record with valueField=value1, based on what you are saying, it would treat Value1 as an unknown value and not display it when the form/formitem is loaded. This is the behavior we are seeing.
              In this case, I tried setting setAddUnknownValues(Boolean.TRUE), however, this seemed to only allow the end user to add unknown values rather than allow the initially loaded record to display the unknown value.

              Is there a way to have it display the unknown values? This might also be useful if, for example, something was wrong with the existing value.

              Thank you
              Last edited by stonebranch2; 25 Mar 2023, 02:25.

              Comment


                #8
                The unknown values system allows users to add whatever values they want - the values do not have to be in the list. You don't seem to want that behavior.

                It's not really clear how you end up with stored values for this field which differ by letter case. It almost seems like you've got two different SQL tables where values are meant as kind-of foreignKeys but need to be matched case insensitivity? That would mean extremely inefficient joins.. probably better to correct that situation if you can.

                Alternatively, all the comboBox expects is that the valueField is unique and a display value can be fetched for it, and that contract is pretty easy to fulfill even in your current situation:

                1. canonically deliver the valueField in lowercase

                2. for the "fetchMissingValues" operation, do a server-side case-insensitive match even though the requested textMatchStyle is "exact". Note for this reply, you should also deliver the valueField as canonically lowercase as for other fetches

                That's it, and you should be set.

                Comment


                  #9
                  No, we do not have two different SQL tables.

                  The basic use case is as follows.

                  The form displays a list of values for selection from the MultiComboBoxItem.

                  The option datasource delivers the list of values to the MultiComboBoxItem, which can be multi-selected.

                  Users can update the record via means other than the user interface, where they can specify those values. Case is not enforced here, as the values are case-insensitive.

                  We will likely just go ahead and enforce the case on this other entry point, as that resolves the matter also. Thanks for the workaround suggestion though.


                  Comment

                  Working...
                  X