Fetching data from an external JSON, taking items and looping on them... and filtering

Fetching data from https://social.brussels/rest/search/organisation?locatedAt=Schaerbeek
Since that url is complex, we cannot use the simplified writing (model: webservice?https://social.brussels/rest/search/organisation?locatedAt=Schaerbeek): we have to put the url in the config: url: parameter.

The list is ordered by "id" descending. We cannot order by "lastUpdate" given the format of the field (it would display 31 then 30 etc)

Adding id: [17632, 18817] in the state of the frontmatter would filter on the IDs in the array.
Adding filter: 'id gte 17000'in the state of the frontmatter would filter on id >= the given number.
Same if we add filter: in the state of the frontmatter and then add on a new line id: 'gte:17000'

Generally speaking, sorting can also be done via the url (see https://github.com/joomlatools/joomlatools-pages/wiki/Collection#state. Examples:

  • ?sort=title which is equivalent to ?sort=title,asc (since asc by default)
  • ?sort=-title which is equivalent to ?sort=title,desc (notice the '-')
  • another option for order is shuffle (useful if you want to show a list that always changes, like for example the testominials on our site)

We can also filter on the external json:

    • id: 591
    • lastUpdate: 14/11/23
    • nameOfficialFr: CPAS SCHAERBEEK - MAISON DE REPOS ET DE SOINS LA CERISAIE
    • address['districtCode']: 80
    • websiteOfficialFr[0]: https://www.lacerisaie1030.be
    • legalStatus['labelFr']: Service public - CPAS
    • address['streetFr']: Avenue Britsiers
    • id: 589
    • lastUpdate: 18/12/20
    • nameOfficialFr: CENTRE HOSPITALIER JEAN TITECA
    • address['districtCode']: 26
    • websiteOfficialFr[0]: http://www.chjt.be
    • legalStatus['labelFr']: Association sans but lucratif (ASBL)
    • address['streetFr']: Rue de la Luzerne
    • id: 251
    • lastUpdate: 12/08/20
    • nameOfficialFr: ASSOCIATION POUR LE DROIT DE MOURIR DANS LA DIGNITÉ - BELGIQUE
    • address['districtCode']: 28
    • websiteOfficialFr[0]: http://www.admd.be
    • legalStatus['labelFr']: Association sans but lucratif (ASBL)
    • address['streetFr']: Avenue Eugène Plasky
    • id: 217
    • lastUpdate: 06/03/23
    • nameOfficialFr: ASSOCIATION FRANCOPHONE DES MUTILÉS DE LA VOIX DE BELGIQUE
    • address['districtCode']: 26
    • websiteOfficialFr[0]: http://www.afmvb.be
    • legalStatus['labelFr']: Association sans but lucratif (ASBL)
    • address['streetFr']: Chaussée de Louvain
    • id: 191
    • lastUpdate: 31/08/20
    • nameOfficialFr: ASSOCIATION DU SERVICE FAMILIAL - MARGUERITE LEBLANC
    • address['districtCode']: 22
    • websiteOfficialFr[0]: http://www.centrefamilial.be
    • legalStatus['labelFr']: Association sans but lucratif (ASBL)
    • address['streetFr']: Rue des Palais
    • id: 119
    • lastUpdate: 09/02/24
    • nameOfficialFr: ASSOCIATION DU DIABÈTE
    • address['districtCode']: 30
    • websiteOfficialFr[0]: https://www.diabete.be
    • legalStatus['labelFr']: Association sans but lucratif (ASBL)
    • address['streetFr']: Avenue de Roodebeek
    • id: 77
    • lastUpdate: 16/09/20
    • nameOfficialFr: AREMIS
    • address['districtCode']: 26
    • websiteOfficialFr[0]: http://www.aremis-asbl.org
    • legalStatus['labelFr']: Association sans but lucratif (ASBL)
    • address['streetFr']: Rue de la Consolation
    • id: 50
    • lastUpdate: 17/09/20
    • nameOfficialFr: AMARNA
    • address['districtCode']: 27
    • websiteOfficialFr[0]: http://www.amarna.org
    • legalStatus['labelFr']: Association sans but lucratif (ASBL)
    • address['streetFr']: Rue des Pavots

OpenStreetMap


Caching

In Step4 of the present Demo site, we used the Data API allowing to cache the source easily like this: data('https://social.brussels/rest/organisation/13817', '1day')

In the present case, we use a Collection (in the frontmatter). In order to turn on collection caching for collection data fetched over http, simply add 'http_client_cache' => true, to config.php.

Alternatively, we could also configure that caching directly in the frontmatter but that is quite advanced. By default enabling the http_client_cache is sufficient.

config: cache: true

would enable cache, whatever is mentioned in the potential config.php

config: cache: 1month

would keep the json 1 month in cache


Comments (Object or Array)

In step4 we were using the Data API, so we could write data('https://social.brussels/rest/organisation/13817', '1day')->address->streetFr;

On the present page, we are using the Collection API so we should write $item->address['streetFr'] (and not $item->address->streetFr).

We should indeed make a difference between:

  • Data API
  • Collection API

The Data API turns a structured data file into an object and offers a very nice and simple API to work with the data. It can do that because it knows the data is simple structured data.

The Collection API is built to handle more complex data, it doesn't turn the data into objects automatically, but it servers each entity property as is. In our case: $item->address .
This works, since $item is an object and address a property of the object, however address is no longer an object. The collection doesn't turn you data into an object like the data api does, unless you tell it so, by creating a custom collection. This is why this works for ext:joomla.model.articles but not here.
address is an array and by default you need to use the array notation in PHP to access the data so $item->address['streetFr']

This explains the differences. PHP wise this is the difference between Object and Array: Object you use -> Array you use []

Sometimes the field does not exist. So $item->address['streetFr'] ?? 'unknown' would display the streetFr if available and the text 'unknown' otherwise

See the difference in practice on /ext-json-filter-data