Assalamualaikum Warahmatullahi Wabarakatuh, lama tak jumpa, mumpung ada kesempatan, disini saya akan memberikan tutorial bagaimana caranya mengintegrasikan redis yang digunakan sebagai database cache pada aplikasi laravel.
Table of Contents
Pendahuluan
Perlu diketahui Redis adalah tools open source untuk penyimpanan struktur data dalam memori sumber terbuka. Sering digunakan untuk database dan cache. Nah, pada artikel ini kita akan menerapkan caching pada laravel.
Laravel sendiri telah mendukung penggunaan Redis, yang digunakan untuk cache sebagai penyimpan data sementara sehingga dapat mempercepat proses query database dan mendapatkan umpan balik, dengan begitu akan mengurangi jumlah waktu yang dihabiskan untuk pulling up data.
Karena kecepatan Redis ini lah, membuat Redis sesuatu yang cool yang harus kamu coba, Redis memberikan cara terstruktur untuk menyimpan data dalam memori. Oleh karena itu, Redis dapat lebih cepat daripada database tradisional yang biasa ditulis ke disk. Redis juga menawarkan lebih banyak struktur data untuk menyimpan datamu, redis menyediakan struktur data seperti string, hash, list, set, sorted sets dengan range queries, bitmaps, hyperloglogs, indeks geospasial, dan streams. Karena fitur itu, Redis sering digunakan untuk menyimpan state-state sementara. Hal ini umum terjadi pada arsitektur microservice, session stores, dan data yang tidak membutuhkan persistensi jangka panjang. [1]
Redis Method
Untuk mengetahui method apa saja yang bisa digunakan/support oleh laravel, silahkan baca dokumentasinya dihalaman official redis.
Pada tutorial ini kita hanya membutuhkan 3 method saja:
- GET
Method get ini kita akan mencari/menampilkan data berdasarkan key yang dicari. Semisal saya mempunyai key artikels lalu saya akan mendapatkan value dari key tersebut. Method Get hanya menyimpan data berupa string dan akan mengembalikan error key stores hashes atau yang lain.
- SET
Method set ini kita akan menyimpan sebuah data kedalam redis dengan menggunakan key yang sama yaitu artikels. Jika key sudah ada sebelumnya, maka akan teroverride dengan data yang baru.
- DEL
Method del ini akan menghapus data berdasarkan key yang diinputkan. Semisal saya mempunyai key artikels_tutorial-php jika kalian menjalankan method del maka akan terhapus data tersebut sesuai keynya.
Persiapan project laravel
Disini kita akan memulai projectnya, saya akan menamai projectnya yaitu blog-lara-redis, silahkan jalan perintah create-project pada terminal.
composer create-project laravel/laravel blog-lara-redis
cd blog-lara-redis
php artisan serve
Selanjutnya, kita perlu menginstal pacakge predis di aplikasi kita menggunakan composer sebelum menggunakan Redis pada aplikasi kita. Predis adalah klien Redis yang ditulis seluruhnya dalam PHP dan tidak memerlukan ekstensi tambahan. Jalankan perintah berikut di terminal untuk menginstal Predis:
composer require predis/predis
Konfigurasi database redis
Ketika sudah menginstall predis, kamu buka file database.php difolder config/database.php, Dalam file tersebut, kamu akan melihat redis array yang berisi konfigurasi redis server. Secara default, client diatur ke phpredis, dan karena predis digunakan pada tutorial ini kalian rubah menjadi predis.
'redis' => [
'client' => env('REDIS_CLIENT', 'predis'),
'options' => [
'cluster' => env('REDIS_CLUSTER', 'redis'),
'prefix' => env('REDIS_PREFIX', Str::slug(env('APP_NAME', 'laravel'), '_').'_database_'),
],
'default' => [
'url' => env('REDIS_URL'),
'host' => env('REDIS_HOST', '127.0.0.1'),
'password' => env('REDIS_PASSWORD', null),
'port' => env('REDIS_PORT', '6379'),
'database' => env('REDIS_DB', '0'),
],
],
[OPTIONAL] Jika kalian menggunakan redis socket (unix).
silahkan tambahkan didalam array default
'scheme' => env('REDIS_SCHEME','tcp')
lalu ubah host menjadi path.
sebelum
'default' => [
'url' => env('REDIS_URL'),
'host' => env('REDIS_HOST', '127.0.0.1'),
'password' => env('REDIS_PASSWORD', null),
'port' => env('REDIS_PORT', '6379'),
'database' => env('REDIS_DB', '0'),
],
sesudah
'default' => [
'url' => env('REDIS_URL'),
'path' => env('REDIS_HOST',null),
'scheme' => env('REDIS_SCHEME','tcp'),
'password' => env('REDIS_PASSWORD', null),
'port' => env('REDIS_PORT', '6379'),
'database' => env('REDIS_DB', '0'),
],
Mengapa saya menggunakan redis unix? karena pada artikel [2] menjelaskan bahwa lebih cepat responnya redis unix daripada redis tcp.
jangan lupa tambahkan REDIS_SCHEME dan REDIS_CLIENT di file .env
REDIS_HOST=/var/run/redis/redis-server.sock
REDIS_CLIENT=predis
REDIS_PASSWORD=null
REDIS_PORT=null
REDIS_SCHEME=unix
Membuat Seed data
Jika kalian sudah mengubah settingan dataabase di file .env dan sudah membuatnya diserver database, selanjutnya kita akan membuat seed data. Data ini hanyalah untuk data testing sementara, yang digunakan ujicoba untuk caching.
php artisan make:seeder ArtikelSeeder
Nantinya akan membuat file baru ArtikelSeeder didalam folder database/seeders.
Kemudian kita buat faker data, berikut adalah kodenya.
<?php
namespace Database\Seeders;
use App\Models\Posts;
use Faker\Factory as Faker;
use Illuminate\Support\Str;
use Illuminate\Database\Seeder;
class ArtikelSeeder extends Seeder
{
public function getFakeData($faker)
{
$paragraphs = rand(8, 15);
$i = 0;
$ret = "";
while ($i < $paragraphs) {
$ret .= $faker->paragraph(rand(2, 6)) ;
$i++;
}
return $ret;
}
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
$faker = Faker::create('id_ID');
for ($i=0; $i < 250 ; $i++) {
$dt = new Posts();
$dt->title = $faker->sentence();
$dt->slug = Str::slug($dt->title, '-');
$dt->html = $this->getFakeData($faker);
$dt->status = 'publish';
$dt->published_at = $faker->dateTimeBetween();
$dt->save();
}
}
}
Kemudian kita akan mengeksekusi file seeder tersebut dengan perintah
php artisan db:seed --class=ArtikelSeeder
Get Data
Untuk menampilkan data artikel dari database, kita akan membuat controller bernama BlogController dan tambahkan function GetArtikel dengan parameter slug.
Pada request pertama akan mengambil dari database terlebih dahulu dan melalukan caching ke redis. Dan jika ada request kembali, maka data akan diambil langsung dari redis.
Pertama, kita akan buat controller terlebih dahulu
php artisan make:controller BlogController
lalu, tambahkan fungsi GetArtikel() untuk mendapatkan semua postingan artikel.
use App\Models\Posts;
use Illuminate\Support\Facades\Redis;
public function GetArtikel($slug) {
$cached = Redis::get('artikel:slug:' . $slug);
if(isset($cached)) {
$blog = json_decode($cached, FALSE);
return response()->json([
'status_code' => 200,
'message' => 'mengambil data dari redis',
'data' => $blog,
]);
}else {
$blog = Posts::where('slug',$slug)->where('status','publish')->first();
Redis::set('artikel:slug:' . $slug, $blog, 'EX', 120);
return response()->json([
'status_code' => 200,
'message' => 'mengambil data dari database',
'data' => $blog,
]);
}
}
Dalam kode diatas, pertama-tama akan diperiksa terlebih dahulu oleh Redis berdasarkan key artikel:slug:_slug. Jika terdapat key yang sama maka akan mengambilnya dalam format json. Jika tidak terdapat didalam Redis, maka akan menampilkan dari database lalu akan menyimpan di Redis dengan key artikel:slug:_slug dan maximal durasi penyimpanan yaitu 120 detik caching. Silahkan rubah angka 120 sesuai keinginan kamu, Ingat! satuan detik.
Jika kamu ingin data cachenya permanent alias tanpa expired. Silahkan hapus parameter ketiga 'EX' dan parameter ke empat 120 pada method Redis::set() .
Selanjutnya kita akan membuat route di routes/web.php dimana API kita dapat berinteraksi saat digunakan.
// untuk laravel 8 kebawah
Route::get('/artikel/{slug}', 'BlogController@GetArtikel')->name('posts_slug');
// untuk laravel 8
Route::get('/artikel/{slug}', [ BlogController::class, "GetArtikel" ])->name('posts_slug');
Update Data
Pada proses ini kita akan mengambil satu data lalu mengupdate data tersebut di database. Ketika sudah terupdate kita akan mencari key dari Redis, setelah mendapatkan keynya kita hapus terlebih dahulu. Lalu kita membuat key baru berdasarkan slug.
Kita akan membuat function UpdateArtikel() dengan parameter Request dan id terlebih dahulu.
public function UpdateArtikel(Request $request, $id) {
$update = Posts::where('id',$id)->where('status','publish')
->update($request->all());
if($update) {
// Menghapus key artikel:slug:_slug dari Redis
Redis::del('artikel:slug:' . $update->slug);
$blog = Posts::where('id',$id)->where('status','publish')->first();
// Insert key yang baru
Redis::set('artikel:slug:' . $blog->slug, $blog);
return response()->json([
'status_code' => 200,
'message' => 'Artikel telah diupdate',
'data' => $blog,
]);
}
}
Mengapa data yang diredis dihapus dahulu?
Karena suatu saat kita mengubah slugnya data di redis akan ikut terhapus (jika expirednya permanen). Dengan begitu data yang tidak digunakan bisa terhapus dan tidak membebani memory server.
Dalam kode diatas, kita mendapatkan id dari blog terlebih dahulu. Lalu dicari melalui database, setelah itu akan mengupdate data. Setelah menjalankan update data di database, kita akan menghapus key lama di redis. Selanjutnya kita akan mencari data berdasarkan id yang kita cari. Lalu memasukkannya ke redis dengan key artikel:slug:_slug .
Setelah semua selesai tambahkan di routes
// jika laravel 8 kebawah
Route::post('/artikel/update/{id}', 'BlogController@UpdateArtikel');
// jika laravel 8
Route::post('/artikel/update/{id}', [ BlogController::class, "UpdateArtikel" ])->name('posts_update');
Hapus Data
Pada langkah terakhir ini, kita akan menghapus suatu artikel dari database kemudian juga akan menghapus key dari Redis.
Pertama tambahkan function deleteArtikel dengan parameter id
public function deleteArtikel($id) {
$old_data = Posts::where('id',$id)->where('status','publish');
$tmp = $old_data->first();
// Menghapus key artikel:slug:_slug di Redis
Redis::del('artikel:slug:' . $tmp->slug);
// menghapus data di database
$old_data->delete();
return response()->json([
'status_code' => 201,
'message' => 'Artikel terhapus'
]);
}
Pada kode diatas kita mencari data berdasarkan id artikel, setelah itu kita akan menghapus key pada redis berdasarkan slug yang didapatkan dari database tadi. Setelah data terhapus pada redis, kita akan menghapus datanya dari database dan akan response json.
Jangan lupa untuk menambahkan routenya
// jika laravel 8 kebawah
Route::delete('/artikel/delete/{id}', 'BlogController@deleteArtikel');
// jika laravel 8
Route::delete('/artikel/delete/{id}', [ BlogController::class, "deleteArtikel" ])->name('posts_delete');
Kesimpulan
Pada artikel ini, kita sudah mempraktekkan bagaimana caranya mengintegrasikan redis yang digunakan sebagai database cache pada aplikasi laravel. Selain itu, kita juga sudah membahas Redis dan manfaatnya, dan bagaimana menggunakan Redis di Laravel untuk menyimpan data sementara untuk mempercepat query database. Kita juga sudah melakukan langkah-langkah untuk update dan menghapus data di Redis menggunakan key dan menerapkan metode Get/Set secara efektif. Saya harap tutorial ini bermanfaat.
Terima Kasih,
Wassalamualaikum Warahmatullahi Wabarakatuh.

Comments