DEV Community

Vasyl Pominchuk
Vasyl Pominchuk

Posted on

Laravel Cache: Improve performance of your application

Hi guys,
today I wanna talk about application performance improvement in terms of Caching.

Caching is a strategy where you store a copy of the data in front of the main data source.
Advantages of caching include faster response time and the ability to serve data quickly, which can improve performance of your application and user experience.

Do you really need a cache in your application? Personally, I say yes. You do need it.

If we decompose our application into blocks we get the following picture:

Image Structure of general web application

  1. DB block is an our applications main database engine, such as MySQL, PostgreSQL, MariaDB and so on.

  2. Another DataSource block is an optional datasource, like external search engine, such as ElasticSearch and so on. You may or may not have it in your application.

  3. File Storage - we always have file storage, for our resources or static files.

  4. View block, it can be either template engine, like Laravel Blade or Smarty OR it can be React, Angular or VueJS view with their own application server or prerenderer. It can be even some API client and in this case we can say that our "view" is a response to any incoming API call.

In this article, we will mainly talk about caching results from Database.

One major point: before making a decision to use Cache make sure you have optimized your SQL queries, it makes no sense to left your SQL queries not optimized and try to resolve this problem due to caching.

If we making queries to really big tables with complex where clauses, with joins and so on, it may take a while to retrieve the result. And this is a good place to cache it.

public function getProductsBlock(int $limit = 5)
{
    return Products::query()
        ->indexed()
        ->whereHas("images", function(Builder $query) {
            $query->active();
        })
        ->with("images")
        ->with("comments")
        ->with("ratings")
        ->with("attributes")
        ->orderBy('id', 'desc')
        ->limit($limit)
        ->get();
}
Enter fullscreen mode Exit fullscreen mode

For example, we have enough complicated query with a subquery, four relations, one orderBy and even "limit".
It is a dummy query it doesn't work, it just for example.
Let's see how we can cover it with a Cache.

public function getProductsBlock(int $limit = 5)
{
    $cacheKey = "products_block_" . "_" . $limit;
    $ttl = 600; // 10 minutes.

    return Cache::remember($cacheKey, $ttl, function() use ($limit) {
        return Products::query()
            ->indexed()
            ->whereHas("images", function(Builder $query) {
                $query->active();
            })
            ->with("images")
            ->with("comments")
            ->with("ratings")
            ->with("attributes")
            ->orderBy('id', 'desc')
            ->limit($limit)
            ->get();
    });
}

Enter fullscreen mode Exit fullscreen mode

Ok, now our data in a cache and we can retrieve it as fast as lightning and not bother our database.

But what if data has been changed?
If we call getProductsBlock() it returns us data from the cache and it won't be up to date now.

How to deal with this and how to choose correct TTL (Time To Live) for our cache function I told in this video.

Please like and subscribe to my channel, you will motivate me to create new videos. If you have any questions, please ask in comments on Youtube.

Discussion (0)