Lazy loading for Ionic 5?

Hello World,

i got a question when was requested to learn lazy loading for ionic 5, i dont know that there’s lazy loading available for Ionic 5, and PHP Senior send me a link to read… i can’t understand how to do it as contents as it’s an ionic 3 although link says ionic 5… Ionic 5/Angular - Lazy Loading Modules | Techiediaries

one of the page which Get from API page contains 2000 to 3000 objects in an array, the data load is around 200kb only, but due to the long list of items to display, PHP Senior complains about slow and not responsive and suggested lazy loading… which he heard long time ago.

what is the best way to load very big amount data for a page where “they want the horse to run fast and don’t want to feed the horse with grass?”

i tried Ion Scrolling but seemed like the codes not working …

thanks for your opinions :bowing_man: :bowing_man: :bowing_man: :bowing_man: :bowing_man:

Hi
Your senior has “gehoord van de klok maar weet niet waar de klepel hangt” - as we proverbial say in my language.

Lazy loading is a concept of partial loading code chunks, as generated by the bundler. In your case, which comes with Angular. Not Ionic. Other frameworks use that too. Lazy loading does not handle data loads from APIs (nor data bundled).

In your case there seems to be a few things going on that could account for the delayed response of the UI. Such as the loading time of 200kb and the display time.

The loading time can be caused by a.o. bandwidth and slow server. In such case you will have to use a pagination mechanism where the GET only retrieves objects 1…100 and then 101…200 etc. The API should support that.

If that is resolved, then there is the question of displaying 3000 objects with the respective properties in the Angular template. Can you share the part the iterates through the array and displays? There are multiple ways to mess up performance in Angular especially if you deal with large arrays.

If by then you are out of resources, then you can choose to paginate in the display, so not showing everything at once, by showing page numbers e.g. Or you can use infinite scroll which loads a chunk on demand.

Sometimes adding a sorting feature or filtering feature helps preventing having to display 3000 objects at once.

Also knowing that most humans have issues dealing with having to mentally cope with 7±2 items in view. So showing 3000 objects seems a bit overboard, pending on your usecase

So short answer - lazy loading is likely not going to help you. Long answer - let’s look at some code, especially the template. Multiple optimisations possible.

Hello Tommertom,

i like the gehoord van de klok maar weet niet waar de klepel hangt :grinning:
this is the screenshot of the time used to load the data,

while i tidy up the codes and share with to see see,

generally, i observed that for 181kb with 2000++ objects took almost 8-9 seconds,

i have done jw pagination to display the items, its the TYPE XHR there took some time to lead…

please wait for my upload of codes for you to see see

thanks Tommertom.

:bowing_man: :bowing_man: :bowing_man:

181kB in 8-9 seconds seems steep…

if there are bandwidth restrictions or you cannot control the API speed, then you could try to load all data in early stage.

Or just tell the user to wait a bit. Show some nice animation etc.

(for the loading part)

Any issues scrolling and displaying after the load?

hello Tommertom

this is the TS code for me to http get from API for this book of id 20, with 2000+ chapters as nested array in this object

 this.http.get('https://thewebsite/api/book/view/' + this.id).subscribe(response => {    
  this.book = response;

  this.storage.set('book chapters', response['book_chapters']).then(() => {
  console.log('books saved to storage');

   this.storage.get('book chapters').then(val => {
   this.bookchapters = val;
   });
  });
  });

the html side code to display out just only the titles of the book chapters

       <div class="card-body">
        <ion-item *ngFor="let item of pageOfItems; " (click)="readbook(item.id)">
          <ion-label>
            <h2>{{item.title}}</h2>
          </ion-label>
        </ion-item>
      </div>

      <jw-pagination [items]="bookchapters" 
      (changePage)="onChangePage($event)"  
      [maxPages]="1"
      [pageSize]="10">
     </jw-pagination>

i got screen capture a video of the loading time for it, but not able to upload mov.

Ok
so for starrters, you can assign this.bookchapters after the response, not after the storage set and get. That will definitely save some time, because you are displaying the chapters and why wait for displaying until stored in storage

I have no experience with jw-paginate, so cannot judge if this is a good one

yes, i did a loading controller with 4 seconds to tell use to wait a bit, Senior PHP said time too long… :joy: its impossible… try try try lazy loading to reduce load… i told him its the api pending time which i noticed. but not able to get answers from him…

Overall, scrolling and displaying all is good,

i try to upload a screencapture video for your reference.

Ok, then the API seems more of the issue. If you can you predict upfront what data is needed to be loaded, try to load it upfront before the user looks at it. Can you load paginated, so only do a get of the first 100 chapters? (in the GET)

Can we http.get first 100 chapters from .ts page first? if yes, maybe the loading time can be faster. how can i do it? :slightly_smiling_face:

is it

   this.http.get(('https://thewebsite/api/book/view/' + this.id).subscribe(response => { 

     what can i write inside to get 100 chapter first?

    })

the jw pagination, got to wait for the data only can perform the pagination, which i display 10 chapters in 1 page.

this is the video screen capture of the loading time of this Get for your reference.

this.http.get('https://thewebsite/api/book/view/' + this.id).subscribe(response => {    
  this.book = response;
   this.bookchapters = response['book_chapters'];
  this.storage.set('book chapters', response['book_chapters']);
  });

As first optimisation.

For first chapters, you need control over the API endpoint and then add the pages you like to the GET. So something like this, as a suggestion. Cannot say this will work with this API:

this.http.get('https://thewebsite/api/book/view/' + this.id+'/'+this.startPage+'/'+this.endPage).subscribe(response => {

This will add a bit of complexity, as you will be fetching the other pages afterwards and add it to the array. Which btw, could result in some page flickering, pending how you do this. So the strategy here would be to load the first few hundreds to allow for content to show asap, and then load the rest.

noted, i give it a try, thank you very much Tommertom for your sharing, i do the first optimisation then experiment on the infinite scroll as well as modify the API side codes.

:bowing_man: :bowing_man: :bowing_man:

Good luck

Last resort: fire the senior

:smiley:

i worried i the one might be fired…

:sob:

but i am happy to learn this new phrase gehoord van de klok maar weet niet waar de klepel hangt,

:smiley:

2 Likes

Hi Tommertom,

i modified the API side codes, and split into 2 http get, it works faster. 3 secs for first 300 objects, then the balance codes following after. then i combine both of the data and stored them into storage using your First Optimisation method. it works smooth, now i try to do more testing…

1 Like

If u can limit the fields per object to load on initial load then u can move maybe even faster on first part while you load the rest

Especially if esch object is a bit big - 181kb for 2000 objects might mean each object might be relatively big

yup, have limited the fields per object only to id, chapter title and date_created, for 300 objects,
around 40kb and 2.36 secs to load, and the balance 340kb took 9 secs to load.

1 Like

Can u tell if it is bandwidth or server being the bottleneck? If it is the server u may need to add cpu/ram/better hdd to it

If it is bandwidth u could go as far as even trying to zip the content and unzip at client

i think its the server, but for server side i have no experience on how to boost it.
i only know how to make the basic PHP Api to connect the sql database with Ionic. i’m still learning :smiley:

Fyi - likely you are already using lazy loading as it is out-of-the-box working like that since a while with Ionic Angular.

Way to see this a.o. is when many pages have their own module definition, resulting in many small js files starting with a number in the build output directory.

In case you are asked - did you try lazy loading, the answer is easy to give.

As to further optimisations there is also the option to look at the content of the data and its nature. If it is fairly static, you can choose to put it als static json in the asset directory, so it gets bundled with the app. Making part of the content less dependent on a slower API endpoint.

Optimisation of the server indeed requires deep dive in the server architecture.