cancel
Showing results for 
Search instead for 
Did you mean: 

SAPUI5 Expression Binding Filter

02-18-2021 11:14 PM
thbuett Explorer
3800 views 5 comments Go to solution
0 Likes
SAP Managed Tags
Subscribe

Hello experts,

I am just wondering what am I doing wrong.

Here is the link to my example

What am I trying: I have a JSON model with the following structure.

var oData = {
   "Orders":[
      {isRead : true},
      {isRead : false}
   ]
};

And a view where I want to output in a text field the number of all objects in "/Orders" that have "isRead == false". I thought this can be solved using the following expression binding....

<Text
                  text="{= ${
                    path: '/Orders',
                    filters:[
                      {
                        path: 'isRead',
                        operator: 'EQ',
                        value1: false
                      }
                    ]
                  }.length }"/>

But there is no filtering. It always outputs 2. I admit at this point, I don't understand it.

The whole thing is a very constructed example, but it represents my problem in the simplest way.

Thanks and greetings,
Thomas

=========================================================================================

[German Version, cause I thought the language selection while asking the question is for translation, but this seems not the case.]

Hallo Experten,

ich frage mich gerade, was mache ich falsch.

Hier der Link zu meinem Beispiel : Beispiel

Was versuche ich: Ich habe ein JSON-Model mit folgendem Aufbau

var oData = {
   "Orders":[
      {isRead : true},
      {isRead : false}
   ]
};

Und eine View, in der ich in einem Textfeld die Anzahl aller Objekte in "/Orders" ausgeben möchte, welche "isRead == false" haben.

Ich dachte, dies lässt sich über folgendes Expression Binding lösen...

<Text
                  text="{= ${
                    path: '/Orders',
                    filters:[
                      {
                        path: 'isRead',
                        operator: 'EQ',
                        value1: false
                      }
                    ]
                  }.length }"/>

Aber es wird nicht gefiltert. Es wird immer 2 ausgegeben. Ich gebe an der Stelle zu, ich verstehe es nicht.

Das ganze ist ein sehr konstruiertes Beispiel, aber es stellt mein Problem am einfachsten dar.

Danke und Grüße,
Thomas

0 Likes

Accepted Solutions (1)

Accepted Solutions (1)

thbuett
Explorer
0 Likes

Ok,

I find the solution. Background is, that filters could maybe only used with "Lists of Items". I tried to filter on a single value element (don't know, if it is the right wording).

What's working is a formatter 🙂

<Text
    text="{
        path : '/Orders',
        formatter : '.formatter.counter'
    }"
/>

with the following controller function

formatter : {
    counter : arr => {return arr.filter(x => x.isRead).length} 
}

It's so simple...

Here the runnable Example-Code

Greetings,
Thomas

sergei-u-niq
Active Contributor
0 Likes

I assume that filters are only applied in ListBindings, not in Property Bindings. Be aware that filters are applied differently depending on Model. For OData, for example, filters are usually sent to backend. Assume you have 10000 Orders and 4000 of them have isRead Property.

=> getting /Orders will get all 10000 items from backend, iterate over all of them, and count those that have isRead=true.

Even if you do it "right" and let the backend filter: "/Orders?$filter=IsRead eq true", you will still get 4000 items and iterate, only to get the count.

what you want to happen is "/Orders/$count?$filter=IsRead eq true"

There are various ways to achieve that in UI5, on js level (creating a ListBinding by hand), or getting an existing listBinding from a list

thbuett
Explorer
0 Likes

Thanks for the tip, Sergei.

Answers (1)

Answers (1)

Dhanasupriya
Active Participant
0 Likes

Hello Thomas

I think there is some issue in using filters in view.. so i tried this way..

onInit: function () { var oData = { "Orders": [{ isRead: true }, { isRead: false }] }; this.getView().setModel( new JSONModel(oData)); var aFilters = []; aFilters.push(new sap.ui.model.Filter("isRead", sap.ui.model.FilterOperator.EQ, false)); console.log(aFilters.length); }

thbuett
Explorer
0 Likes

Ok,

but aFilters.length returns, how many entries in the filter-array, not how many "Orders" meet this condition of the filter.

And your are right, I hade forget to say, that I am searching for a controller free solution. Cause the real code I have is running in an Dialog, for which I don't want to implement an seperate controller. But if it turns out that filtering in views is limited,as you say, I'll have to switch to a controller solution.

Thanks for your idea