<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:dc="http://purl.org/dc/elements/1.1/">
	<channel>
		<title><![CDATA[Forums - All Forums]]></title>
		<link>https://bb.nurfachmi.com/</link>
		<description><![CDATA[Forums - https://bb.nurfachmi.com]]></description>
		<pubDate>Sat, 02 May 2026 15:47:54 +0000</pubDate>
		<generator>MyBB</generator>
		<item>
			<title><![CDATA[AI dalam Cyber Security, Onno W. Purbo]]></title>
			<link>https://bb.nurfachmi.com/thread-22.html</link>
			<pubDate>Sat, 02 May 2026 14:01:24 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-22.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, August 19, 2025</blockquote>
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/08/ebook.jpeg" loading="lazy"  width="474" height="263" alt="[Image: ebook.jpeg]" class="mycode_img" /></blockquote>
<br />
Alhamdulillah, buku ini bisa diselesaikan. Buku AI dalam <span style="font-weight: bold;" class="mycode_b"><span style="font-style: italic;" class="mycode_i">Cyber Security: Dari Teori</span></span><br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-style: italic;" class="mycode_i">Hingga Praktik Pertahanan Digital</span></span> disusun sebagai panduan singkat namun terarah bagi<br />
pembaca untuk menjembatani konsep dasar kecerdasan buatan dengan praktik pertahanan<br />
siber yang relevan di Indonesia.<br />
<br />
Terima kasih banyak pada seluruh <span style="font-weight: bold;" class="mycode_b">civitas academica di Institut Teknologi Tangerang</span><br />
<span style="font-weight: bold;" class="mycode_b">Selatan, serta Komunitas IT di Indonesia</span> atas engagement, dukungan, dan umpan balik<br />
selama ini yang memperkaya proses penulisan dan pengujian gagasan di dalam buku ini.<br />
<br />
Buku ini dirancang untuk akademisi, praktisi, dan pengambil keputusan. Isinya merentang<br />
dari fondasi AI dan keamanan siber, deteksi ancaman dan anomali (IDS/IPS, UEBA),<br />
otomasi respons insiden (SOAR), keamanan aplikasi, hingga sisi gelap pemanfaatan AI<br />
dalam serangan, etika–privasi–regulasi, serta tren masa depan dan strategi implementasi<br />
yang pragmatis di organisasi. Harapannya, buku ini dapat menjadi rujukan praktis dalam<br />
memperkuat kesiapan dan ketahanan siber nasional.<br />
<br />
Akhir kata, <span style="font-weight: bold;" class="mycode_b">mohon maaf jika ada banyak kekurangan</span> dalam penyajian materi, contoh,<br />
maupun kedalaman bahasan; segala saran dan kritik yang membangun sangat penulis<br />
nantikan untuk perbaikan edisi berikutnya.<br />
<br />
Tangerang Selatan, Agustus 2025<br />
Onno W. Purbo<br />
<br />
Download ebook-nya <a href="https://drive.google.com/file/d/1FNosdNmXQEQtsPN3jxohKvpmV--1neC_/view" target="_blank" rel="noopener" class="mycode_url">di sini</a>.<br />
<br />
Jika tautan di atas bermasalah, bisa download alternatifnya di bawah ini.<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><a href="https://nurfachmi.com/wp-content/uploads/2025/08/Onno-W.-Purbo-AI-dalam-Cyber-Security-2025.pdf" target="_blank" rel="noopener" class="mycode_url">Onno W. Purbo, AI dalam Cyber Security, 2025</a></blockquote>
]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, August 19, 2025</blockquote>
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/08/ebook.jpeg" loading="lazy"  width="474" height="263" alt="[Image: ebook.jpeg]" class="mycode_img" /></blockquote>
<br />
Alhamdulillah, buku ini bisa diselesaikan. Buku AI dalam <span style="font-weight: bold;" class="mycode_b"><span style="font-style: italic;" class="mycode_i">Cyber Security: Dari Teori</span></span><br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-style: italic;" class="mycode_i">Hingga Praktik Pertahanan Digital</span></span> disusun sebagai panduan singkat namun terarah bagi<br />
pembaca untuk menjembatani konsep dasar kecerdasan buatan dengan praktik pertahanan<br />
siber yang relevan di Indonesia.<br />
<br />
Terima kasih banyak pada seluruh <span style="font-weight: bold;" class="mycode_b">civitas academica di Institut Teknologi Tangerang</span><br />
<span style="font-weight: bold;" class="mycode_b">Selatan, serta Komunitas IT di Indonesia</span> atas engagement, dukungan, dan umpan balik<br />
selama ini yang memperkaya proses penulisan dan pengujian gagasan di dalam buku ini.<br />
<br />
Buku ini dirancang untuk akademisi, praktisi, dan pengambil keputusan. Isinya merentang<br />
dari fondasi AI dan keamanan siber, deteksi ancaman dan anomali (IDS/IPS, UEBA),<br />
otomasi respons insiden (SOAR), keamanan aplikasi, hingga sisi gelap pemanfaatan AI<br />
dalam serangan, etika–privasi–regulasi, serta tren masa depan dan strategi implementasi<br />
yang pragmatis di organisasi. Harapannya, buku ini dapat menjadi rujukan praktis dalam<br />
memperkuat kesiapan dan ketahanan siber nasional.<br />
<br />
Akhir kata, <span style="font-weight: bold;" class="mycode_b">mohon maaf jika ada banyak kekurangan</span> dalam penyajian materi, contoh,<br />
maupun kedalaman bahasan; segala saran dan kritik yang membangun sangat penulis<br />
nantikan untuk perbaikan edisi berikutnya.<br />
<br />
Tangerang Selatan, Agustus 2025<br />
Onno W. Purbo<br />
<br />
Download ebook-nya <a href="https://drive.google.com/file/d/1FNosdNmXQEQtsPN3jxohKvpmV--1neC_/view" target="_blank" rel="noopener" class="mycode_url">di sini</a>.<br />
<br />
Jika tautan di atas bermasalah, bisa download alternatifnya di bawah ini.<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><a href="https://nurfachmi.com/wp-content/uploads/2025/08/Onno-W.-Purbo-AI-dalam-Cyber-Security-2025.pdf" target="_blank" rel="noopener" class="mycode_url">Onno W. Purbo, AI dalam Cyber Security, 2025</a></blockquote>
]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Favicon Getter]]></title>
			<link>https://bb.nurfachmi.com/thread-21.html</link>
			<pubDate>Sat, 02 May 2026 13:58:54 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-21.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, June 27, 2025</blockquote>
<br />
Assalamu’alaykum warahmatullahi wabarakatuh.<br />
<br />
Singkatnya, ini adalah beberapa cara kita mendapatkan favicon sebuah website tanpa perlu mengubek-ngubek source code untuk mendapatkan url-nya, lalu mengunduh dan mengunggahnya kembali ke hosting kita untuk ditampilkan. Paham, tak? Semoga iya.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/06/tips-dan-trik.jpg" loading="lazy"  width="1120" height="630" alt="[Image: tips-dan-trik.jpg]" class="mycode_img" /></blockquote>
<br />
<br />
Cara pertama menggunakan Google API.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>https://s2.googleusercontent.com/s2/favicons?domain={nama domain}&amp;sz=32</code></div></div><br />
Contoh penggunaan:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>https://s2.googleusercontent.com/s2/favicons?domain=nurfachmi.com&amp;sz=32</code></div></div><br />
Untuk query sz (size) itu bisa diubah-ubah juga nilainya, bisa 32, 64, 128 sampai 256.<br />
<br />
Jika dibungkus dengan tag img, maka langsung menjadi seperti ini:<br />
<img src="https://s2.googleusercontent.com/s2/favicons?domain=nurfachmi.com&amp;sz=256" loading="lazy"  alt="[Image: favicons?domain=nurfachmi.com&amp;sz=256]" class="mycode_img" /><br />
<br />
---<br />
<br />
Cara kedua juga menggunakan API dari sebuah web yang bernama <a href="https://clearbit.com/" target="_blank" rel="noopener" class="mycode_url">clearbit.com</a>.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>https://logo.clearbit.com/{nama domain}</code></div></div><br />
Contoh penggunaan:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>https://logo.clearbit.com/nurfachmi.com</code></div></div><br />
Jika dibungkus dengan tag img, maka akan menjadi seperti di atas. Hanya saja otomatis akan diarahkan menjadi ukuran 128×128 pixel.<br />
<br />
---<br />
<br />
API di atas bisa kita gunakan untuk mempercantik konten web kita. Misalnya kita hanya menyimpan url website, maka kita bisa menambahkan icon/favicon-nya agar terlihat lebih menarik lagi.<br />
<br />
Begitulah kira-kira tentang Favicon Getter ini. Semoga bermanfaat.]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, June 27, 2025</blockquote>
<br />
Assalamu’alaykum warahmatullahi wabarakatuh.<br />
<br />
Singkatnya, ini adalah beberapa cara kita mendapatkan favicon sebuah website tanpa perlu mengubek-ngubek source code untuk mendapatkan url-nya, lalu mengunduh dan mengunggahnya kembali ke hosting kita untuk ditampilkan. Paham, tak? Semoga iya.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/06/tips-dan-trik.jpg" loading="lazy"  width="1120" height="630" alt="[Image: tips-dan-trik.jpg]" class="mycode_img" /></blockquote>
<br />
<br />
Cara pertama menggunakan Google API.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>https://s2.googleusercontent.com/s2/favicons?domain={nama domain}&amp;sz=32</code></div></div><br />
Contoh penggunaan:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>https://s2.googleusercontent.com/s2/favicons?domain=nurfachmi.com&amp;sz=32</code></div></div><br />
Untuk query sz (size) itu bisa diubah-ubah juga nilainya, bisa 32, 64, 128 sampai 256.<br />
<br />
Jika dibungkus dengan tag img, maka langsung menjadi seperti ini:<br />
<img src="https://s2.googleusercontent.com/s2/favicons?domain=nurfachmi.com&amp;sz=256" loading="lazy"  alt="[Image: favicons?domain=nurfachmi.com&amp;sz=256]" class="mycode_img" /><br />
<br />
---<br />
<br />
Cara kedua juga menggunakan API dari sebuah web yang bernama <a href="https://clearbit.com/" target="_blank" rel="noopener" class="mycode_url">clearbit.com</a>.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>https://logo.clearbit.com/{nama domain}</code></div></div><br />
Contoh penggunaan:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>https://logo.clearbit.com/nurfachmi.com</code></div></div><br />
Jika dibungkus dengan tag img, maka akan menjadi seperti di atas. Hanya saja otomatis akan diarahkan menjadi ukuran 128×128 pixel.<br />
<br />
---<br />
<br />
API di atas bisa kita gunakan untuk mempercantik konten web kita. Misalnya kita hanya menyimpan url website, maka kita bisa menambahkan icon/favicon-nya agar terlihat lebih menarik lagi.<br />
<br />
Begitulah kira-kira tentang Favicon Getter ini. Semoga bermanfaat.]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Update Password di Laravel]]></title>
			<link>https://bb.nurfachmi.com/thread-20.html</link>
			<pubDate>Sat, 02 May 2026 13:55:47 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-20.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, June 24, 2025</blockquote>
<br />
Assalamualaikum warahmatullahi wabarakatuh.<br />
<br />
Kembali lagi di tutorial singkat nan padat berupa tips dan trik dalam potongan kode. Kali ini tentang update password di Laravel.<br />
<br />
Bayangkan kamu memiliki halaman untuk mengubah password akun, kira-kira akan ada elemen-elemen berikut ini:<br />
<ul class="mycode_list"><li>    Password saat ini (name: current_password)<br />
</li>
<li>    Password baru (name: password)<br />
</li>
<li>    Konfirmasi password baru (name: password_confirmation)<br />
</li>
</ul>
<br />
Jika ini adalah aplikasi RESTful, maka kira-kira struktur JSON-nya seperti ini:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;&nbsp;</span><span style="color: #DD0000">"current_password"</span><span style="color: #007700">:&nbsp;</span><span style="color: #DD0000">"abcdefg"</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;&nbsp;</span><span style="color: #DD0000">"password"</span><span style="color: #007700">:&nbsp;</span><span style="color: #DD0000">"new&nbsp;password"</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;&nbsp;</span><span style="color: #DD0000">"password_confirmation"</span><span style="color: #007700">:&nbsp;</span><span style="color: #DD0000">"new&nbsp;password"<br /></span><span style="color: #007700">}&nbsp;<br /></span></code></div></div></div><br />
Lalu buat sebuah invokable controller dengan perintah:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;make</span><span style="color: #007700">:</span><span style="color: #0000BB">controller&nbsp;UpdatePasswordController&nbsp;</span><span style="color: #007700">-</span><span style="color: #0000BB">i&nbsp;<br /></span></code></div></div></div><br />
Kemudian buat sebuah form request dengan perintah:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;make</span><span style="color: #007700">:</span><span style="color: #0000BB">request&nbsp;UpdatePasswordRequest&nbsp;<br /></span></code></div></div></div><br />
Kembali ke file controller tadi, ubah isinya menjadi seperti ini:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">use&nbsp;</span><span style="color: #0000BB">App&#092;Http&#092;Requests&#092;UpdatePasswordRequest</span><span style="color: #007700">;<br />use&nbsp;</span><span style="color: #0000BB">Illuminate&#092;Support&#092;Facades&#092;Hash</span><span style="color: #007700">;<br /><br />...<br /><br />public&nbsp;function&nbsp;</span><span style="color: #0000BB">__invoke</span><span style="color: #007700">(</span><span style="color: #0000BB">UpdatePasswordRequest&nbsp;&#36;request</span><span style="color: #007700">)<br />{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;&#36;request</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">user</span><span style="color: #007700">()-&gt;</span><span style="color: #0000BB">fill</span><span style="color: #007700">([<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'password'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">Hash</span><span style="color: #007700">::</span><span style="color: #0000BB">make</span><span style="color: #007700">(</span><span style="color: #0000BB">&#36;request</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">password</span><span style="color: #007700">)<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">])-&gt;</span><span style="color: #0000BB">save</span><span style="color: #007700">();<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">....<br />}&nbsp;<br /></span></code></div></div></div><br />
Adapun isi file form request-nya sebagai berikut:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">public&nbsp;function&nbsp;</span><span style="color: #0000BB">rules</span><span style="color: #007700">():&nbsp;array<br />{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">return&nbsp;[<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'current_password'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'required|current_password|different:password'</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'password'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'required|string|min:6|confirmed'</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">];<br />}&nbsp;<br /></span></code></div></div></div><br />
Daan jadilah sebuah halaman untuk mengubah password dengan ketentuan sebagai berikut:<br />
<br />
<ol type="1" class="mycode_list"><li>    Membutuhkan password aktif yang tepat saat ini.<br />
</li>
<li>    Panjang password minimal 6 karakter.<br />
</li>
<li>    Password baru dan konfirmasi passwordnya harus sama.<br />
</li>
<li>    Password baru dan password lama harus berbeda.<br />
</li>
</ol>
<br />
Sebetulnya masih banyak yang bisa dilakukan seperti password harus berupa kombinasi huruf, angka dan simbol. Namun, itu kita bahas di lain waktu saja. Kali ini penulis ingin menekankan tentang kesederhanaan kode Laravel dalam skenario ubah password ini.<br />
<br />
Terima kasih sudah membaca sampai sini. Semoga bermanfaat. Mohon koreksi jika ada kekeliruan dan bagikan artikel ini jika memberi pengetahuan.<br />
<br />
Wassalamu’alaikum warahmatullahi wabarakatuh.]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, June 24, 2025</blockquote>
<br />
Assalamualaikum warahmatullahi wabarakatuh.<br />
<br />
Kembali lagi di tutorial singkat nan padat berupa tips dan trik dalam potongan kode. Kali ini tentang update password di Laravel.<br />
<br />
Bayangkan kamu memiliki halaman untuk mengubah password akun, kira-kira akan ada elemen-elemen berikut ini:<br />
<ul class="mycode_list"><li>    Password saat ini (name: current_password)<br />
</li>
<li>    Password baru (name: password)<br />
</li>
<li>    Konfirmasi password baru (name: password_confirmation)<br />
</li>
</ul>
<br />
Jika ini adalah aplikasi RESTful, maka kira-kira struktur JSON-nya seperti ini:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;&nbsp;</span><span style="color: #DD0000">"current_password"</span><span style="color: #007700">:&nbsp;</span><span style="color: #DD0000">"abcdefg"</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;&nbsp;</span><span style="color: #DD0000">"password"</span><span style="color: #007700">:&nbsp;</span><span style="color: #DD0000">"new&nbsp;password"</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;&nbsp;</span><span style="color: #DD0000">"password_confirmation"</span><span style="color: #007700">:&nbsp;</span><span style="color: #DD0000">"new&nbsp;password"<br /></span><span style="color: #007700">}&nbsp;<br /></span></code></div></div></div><br />
Lalu buat sebuah invokable controller dengan perintah:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;make</span><span style="color: #007700">:</span><span style="color: #0000BB">controller&nbsp;UpdatePasswordController&nbsp;</span><span style="color: #007700">-</span><span style="color: #0000BB">i&nbsp;<br /></span></code></div></div></div><br />
Kemudian buat sebuah form request dengan perintah:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;make</span><span style="color: #007700">:</span><span style="color: #0000BB">request&nbsp;UpdatePasswordRequest&nbsp;<br /></span></code></div></div></div><br />
Kembali ke file controller tadi, ubah isinya menjadi seperti ini:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">use&nbsp;</span><span style="color: #0000BB">App&#092;Http&#092;Requests&#092;UpdatePasswordRequest</span><span style="color: #007700">;<br />use&nbsp;</span><span style="color: #0000BB">Illuminate&#092;Support&#092;Facades&#092;Hash</span><span style="color: #007700">;<br /><br />...<br /><br />public&nbsp;function&nbsp;</span><span style="color: #0000BB">__invoke</span><span style="color: #007700">(</span><span style="color: #0000BB">UpdatePasswordRequest&nbsp;&#36;request</span><span style="color: #007700">)<br />{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;&#36;request</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">user</span><span style="color: #007700">()-&gt;</span><span style="color: #0000BB">fill</span><span style="color: #007700">([<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'password'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">Hash</span><span style="color: #007700">::</span><span style="color: #0000BB">make</span><span style="color: #007700">(</span><span style="color: #0000BB">&#36;request</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">password</span><span style="color: #007700">)<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">])-&gt;</span><span style="color: #0000BB">save</span><span style="color: #007700">();<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">....<br />}&nbsp;<br /></span></code></div></div></div><br />
Adapun isi file form request-nya sebagai berikut:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">public&nbsp;function&nbsp;</span><span style="color: #0000BB">rules</span><span style="color: #007700">():&nbsp;array<br />{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">return&nbsp;[<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'current_password'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'required|current_password|different:password'</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'password'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'required|string|min:6|confirmed'</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">];<br />}&nbsp;<br /></span></code></div></div></div><br />
Daan jadilah sebuah halaman untuk mengubah password dengan ketentuan sebagai berikut:<br />
<br />
<ol type="1" class="mycode_list"><li>    Membutuhkan password aktif yang tepat saat ini.<br />
</li>
<li>    Panjang password minimal 6 karakter.<br />
</li>
<li>    Password baru dan konfirmasi passwordnya harus sama.<br />
</li>
<li>    Password baru dan password lama harus berbeda.<br />
</li>
</ol>
<br />
Sebetulnya masih banyak yang bisa dilakukan seperti password harus berupa kombinasi huruf, angka dan simbol. Namun, itu kita bahas di lain waktu saja. Kali ini penulis ingin menekankan tentang kesederhanaan kode Laravel dalam skenario ubah password ini.<br />
<br />
Terima kasih sudah membaca sampai sini. Semoga bermanfaat. Mohon koreksi jika ada kekeliruan dan bagikan artikel ini jika memberi pengetahuan.<br />
<br />
Wassalamu’alaikum warahmatullahi wabarakatuh.]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[USB Multiboot]]></title>
			<link>https://bb.nurfachmi.com/thread-19.html</link>
			<pubDate>Sat, 02 May 2026 13:52:50 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-19.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, June 6, 2025</blockquote>
<br />
Kita sering mendengar atau mengetahui bahwa ada PC/Laptop yang Dualboot atau Multiboot. Maksudnya adalah dalam satu PC bisa ada lebih dari satu sistem operasi, misalnya Windows dan Linux sekaligus. Hal tersebut sudah biasa, bagaimana kalau kita memiliki USB yang Multiboot juga?<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/06/multiboot.jpg" loading="lazy"  width="1280" height="720" alt="[Image: multiboot.jpg]" class="mycode_img" /></blockquote>
<br />
<br />
Tanpa Multiboot, jika kamu memiliki 2 file ISO, misalnya, Windows dan Linux Mint, maka kamu harus memiliki dua USB untuk disiapkan satu per satu untuk kedua sistem operasi tersebut. Repot, kan?<br />
<br />
Dengan memiliki USB Multiboot, maka kamu bisa melakukan Live atau Instalasi banyak sistem operasi dengan menggunakan hanya satu USB.<br />
<br />
Kenalkan, Ventoy! Ventoy adalah alat yang menghasilkan USB yang spesial dan Ventoy bersifat open source. Mengapa spesial? Karena USB kamu bisa jadi Multiboot! Yuhuuu!<br />
<br />
Yowis tanpa panjang lebar, langsung aja ke tutorialnya.<br />
<br />
--<br />
<br />
<span style="font-size: xx-large;" class="mycode_size"><span style="font-weight: bold;" class="mycode_b">Instalasi Ventoy</span></span><br />
<br />
Colokin dulu USB stick yang ingin dijadikan Multiboot.<br />
<br />
Sila ke halaman rilis Ventoy dan download sesuai sistem operasi kamu. Penulis memakai Linux, jadinya mengunduh yang ventoy-x.x.x-linux.tar.gz.<br />
<br />
Selesai diunduh, langsung saja di-ekstrak filenya.<br />
<br />
Klik kanan folder Ventoy-nya, lalu pilih Open in Terminal.<br />
<br />
Lalu jalankan perintah ini:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo ./VentoyGUI.x86_64</code></div></div><br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Menggunakan Ventoy</span></span><br />
<br />
Cara menggunakannya gampang banget.<br />
<br />
Pastikan yang muncul adalah USB Drive kamu. Kalau baru nyolokin, kamu bisa klik dulu icon refresh yang warna hijau.<br />
<br />
Pilih USB yang dimaksud.<br />
<br />
Klik tombol Install dan tunggu.<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/06/ventoy.png?resize=480%2C370&amp;ssl=1" loading="lazy"  width="480" height="370" alt="[Image: ventoy.png?resize=480%2C370&amp;ssl=1]" class="mycode_img" /><br />
<br />
Ketika sudah selesai, maka USB kamu kini namanya sudah jadi ventoy.<br />
<br />
Tinggal salin aja file-file berekstensikan ISO ke drive USB kamu itu.<br />
<br />
Terakhir boot deh pakai USB tadi.<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/06/ventoy_boot.jpg?resize=640%2C360&amp;ssl=1" loading="lazy"  width="640" height="360" alt="[Image: ventoy_boot.jpg?resize=640%2C360&amp;ssl=1]" class="mycode_img" /><br />
<br />
Maka file-file ISO yang disalin tadi akan menjadi pilihan untuk booting.<br />
<br />
--<br />
<br />
Gimana? Mudah, kan?]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, June 6, 2025</blockquote>
<br />
Kita sering mendengar atau mengetahui bahwa ada PC/Laptop yang Dualboot atau Multiboot. Maksudnya adalah dalam satu PC bisa ada lebih dari satu sistem operasi, misalnya Windows dan Linux sekaligus. Hal tersebut sudah biasa, bagaimana kalau kita memiliki USB yang Multiboot juga?<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/06/multiboot.jpg" loading="lazy"  width="1280" height="720" alt="[Image: multiboot.jpg]" class="mycode_img" /></blockquote>
<br />
<br />
Tanpa Multiboot, jika kamu memiliki 2 file ISO, misalnya, Windows dan Linux Mint, maka kamu harus memiliki dua USB untuk disiapkan satu per satu untuk kedua sistem operasi tersebut. Repot, kan?<br />
<br />
Dengan memiliki USB Multiboot, maka kamu bisa melakukan Live atau Instalasi banyak sistem operasi dengan menggunakan hanya satu USB.<br />
<br />
Kenalkan, Ventoy! Ventoy adalah alat yang menghasilkan USB yang spesial dan Ventoy bersifat open source. Mengapa spesial? Karena USB kamu bisa jadi Multiboot! Yuhuuu!<br />
<br />
Yowis tanpa panjang lebar, langsung aja ke tutorialnya.<br />
<br />
--<br />
<br />
<span style="font-size: xx-large;" class="mycode_size"><span style="font-weight: bold;" class="mycode_b">Instalasi Ventoy</span></span><br />
<br />
Colokin dulu USB stick yang ingin dijadikan Multiboot.<br />
<br />
Sila ke halaman rilis Ventoy dan download sesuai sistem operasi kamu. Penulis memakai Linux, jadinya mengunduh yang ventoy-x.x.x-linux.tar.gz.<br />
<br />
Selesai diunduh, langsung saja di-ekstrak filenya.<br />
<br />
Klik kanan folder Ventoy-nya, lalu pilih Open in Terminal.<br />
<br />
Lalu jalankan perintah ini:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo ./VentoyGUI.x86_64</code></div></div><br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Menggunakan Ventoy</span></span><br />
<br />
Cara menggunakannya gampang banget.<br />
<br />
Pastikan yang muncul adalah USB Drive kamu. Kalau baru nyolokin, kamu bisa klik dulu icon refresh yang warna hijau.<br />
<br />
Pilih USB yang dimaksud.<br />
<br />
Klik tombol Install dan tunggu.<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/06/ventoy.png?resize=480%2C370&amp;ssl=1" loading="lazy"  width="480" height="370" alt="[Image: ventoy.png?resize=480%2C370&amp;ssl=1]" class="mycode_img" /><br />
<br />
Ketika sudah selesai, maka USB kamu kini namanya sudah jadi ventoy.<br />
<br />
Tinggal salin aja file-file berekstensikan ISO ke drive USB kamu itu.<br />
<br />
Terakhir boot deh pakai USB tadi.<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/06/ventoy_boot.jpg?resize=640%2C360&amp;ssl=1" loading="lazy"  width="640" height="360" alt="[Image: ventoy_boot.jpg?resize=640%2C360&amp;ssl=1]" class="mycode_img" /><br />
<br />
Maka file-file ISO yang disalin tadi akan menjadi pilihan untuk booting.<br />
<br />
--<br />
<br />
Gimana? Mudah, kan?]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Kustomisasi Halaman 404]]></title>
			<link>https://bb.nurfachmi.com/thread-18.html</link>
			<pubDate>Sat, 02 May 2026 13:50:24 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-18.html</guid>
			<description><![CDATA[Berangkat dari ribut-ribut di Twitter (kini X) mengenai halaman 404 yang tampilannya itu standar masih bawaan web server engine-nya itu sendiri. Kode 404 sendiri merujuk ke salah satu dari <a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Status" target="_blank" rel="noopener" class="mycode_url">HTTP response status codes</a> yang artinya Not Found atau halaman tidak ditemukan karena kesalahan pengguna dalam menuliskan alamat websitenya.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/404-NotFound.png" loading="lazy"  width="1920" height="1080" alt="[Image: 404-NotFound.png]" class="mycode_img" /></blockquote>
<br />
<br />
Berikut tampilan halaman 404 default pada beberapa web server terkenal.<br />
<br />
NGINX default 404<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/404-nginx.png?resize=640%2C409&amp;ssl=1" loading="lazy"  width="640" height="409" alt="[Image: 404-nginx.png?resize=640%2C409&amp;ssl=1]" class="mycode_img" /><br />
<br />
LiteSpeed default 404<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/404-litespeed.jpg?resize=640%2C391&amp;ssl=1" loading="lazy"  width="640" height="391" alt="[Image: 404-litespeed.jpg?resize=640%2C391&amp;ssl=1]" class="mycode_img" /><br />
<br />
Apache default 404<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/404-apache.png?resize=640%2C334&amp;ssl=1" loading="lazy"  width="640" height="334" alt="[Image: 404-apache.png?resize=640%2C334&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, namanya juga tampilan standar, pastilah agak kurang cantik terlihatnya. Jadi, bagaimana kalau kita bikin sendiri atau kustom halaman 404 tersebut? Yuk bismillah.<br />
<br />
---<br />
<br />
Daftar Isi<br />
<br />
Insyaallah kita akan membahas beberapa hal seputar kustomisasi halaman 404 ini, antara lain:<br />
<ul class="mycode_list"><li>    Shared Hosting<br />
</li>
<li>    Laravel PHP (framework)<br />
</li>
<li>    WordPress (CMS)<br />
</li>
<li>    nginx<br />
</li>
<li>    LiteSpeed<br />
</li>
<li>    Apache<br />
</li>
</ul>
<br />
Sebelum kita mulai satu per satu pembahasannya, kami ingin menyampaikan sesuatu.<br />
<br />
Blog nurfachmi.com hadir untuk berbagi ilmu dan pengalaman seputar teknologi, pemrograman, dan pengembangan karier di dunia IT. Semua konten yang ada di sini dibuat dengan penuh dedikasi agar bisa membantu lebih banyak orang memahami teknologi dengan cara yang lebih mudah dan praktis.<br />
<br />
Jika Anda merasa blog ini bermanfaat, Anda bisa mendukung operasional kami dengan memberikan donasi. Setiap kontribusi yang Anda berikan akan digunakan untuk:<br />
<br />
    ✅ Biaya server dan domain agar blog tetap online<br />
    ✅ Pengembangan fitur baru, termasuk platform LMS dengan kelas gratis dan berbayar<br />
    ✅ Pembuatan konten berkualitas yang lebih beragam<br />
<br />
Dukungan Anda, sekecil apa pun, sangat berarti bagi keberlangsungan blog ini. Mari bersama-sama membangun komunitas belajar yang lebih baik!<br />
<br />
Klik tombol donasi di bawah ini untuk berkontribusi.<br />
Terima kasih! ?<br />
<br />
Sekali lagi terima kasih atas dukungannya. Sekarang, mari kita belajar!<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Shared Hosting</span></span><br />
<br />
Pada umumnya jika kita menyewa shared hosting, biasanya sudah include dengan cPanel. Untuk memodifikasi halaman error 404, silahkan cari di menu pencarian dengan keyword Error Pages atau scroll sedikit tetikusnya sampai ketemu submenu Advanced dan klik ikon Error Pages.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-11.png?resize=640%2C174&amp;ssl=1" loading="lazy"  width="640" height="174" alt="[Image: image-11.png?resize=640%2C174&amp;ssl=1]" class="mycode_img" /><br />
<br />
Akan muncul kira-kira seperti ini pilihannya:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-12.png?resize=640%2C468&amp;ssl=1" loading="lazy"  width="640" height="468" alt="[Image: image-12.png?resize=640%2C468&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah kalau di cPanel, kita gak hanya bisa modifikasi halaman 404. Halaman error lainnya juga bisa dikustom kok.<br />
<br />
Selanjutnya kita klik saja menu 404 (Not found) dahulu dan kita akan diarahkan ke sebuah editor seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-13.png?resize=640%2C533&amp;ssl=1" loading="lazy"  width="640" height="533" alt="[Image: image-13.png?resize=640%2C533&amp;ssl=1]" class="mycode_img" /><br />
<br />
Yowis, silahkan taruh kode HTML sesuai keinginan kita sendiri di text editor tersebut. Pastikan klik tombol Save kalau sudah selesai ya.<br />
<br />
Etapi untuk memperkaya informasi mengenai error-nya, kita bisa menambahkan beberapa tag spesial, antara lain:<br />
<ul class="mycode_list"><li>    Referring URL: alamat asal sebelum sampai ke halaman 404 tersebut.<br />
</li>
<li>    Server Name: url server saat ini.<br />
</li>
<li>    Visitor's IP Address: IP Address pengunjung.<br />
</li>
<li>    Visitor's Browser: detail browser yang dipakai.<br />
</li>
<li>    Requested URL: url yang ingin diakses tetapi tidak ditemukan.<br />
</li>
<li>    Redirect Status Code: status kode redirect, biasanya sekitar 3xx.<br />
</li>
</ul>
<br />
Berikut contoh kodenya:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">&lt;!</span><span style="color: #0000BB">DOCTYPE&nbsp;html</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">html&nbsp;lang</span><span style="color: #007700">=</span><span style="color: #DD0000">"id"</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;&lt;</span><span style="color: #0000BB">meta&nbsp;charset</span><span style="color: #007700">=</span><span style="color: #DD0000">"utf-8"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;name</span><span style="color: #007700">=</span><span style="color: #DD0000">"viewport"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"width=device-width,&nbsp;initial-scale=1.0"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">404&nbsp;Not&nbsp;Found</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">link&nbsp;href</span><span style="color: #007700">=</span><span style="color: #DD0000">"https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css"&nbsp;</span><span style="color: #0000BB">rel</span><span style="color: #007700">=</span><span style="color: #DD0000">"stylesheet"</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">body&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"d-flex&nbsp;align-items-center&nbsp;justify-content-center&nbsp;vh-100&nbsp;bg-light"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">div&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"text-center"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">h1&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"display-1&nbsp;text-danger"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">404</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Halaman&nbsp;yang&nbsp;Anda&nbsp;cari&nbsp;tidak&nbsp;ditemukan</span><span style="color: #007700">.&lt;/</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Referring&nbsp;URL</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="HTTP_REFERER"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Server&nbsp;Name</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="HTTP_HOST"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Visitor&nbsp;IP&nbsp;Address</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="REMOTE_ADDR"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Browser</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="HTTP_USER_AGENT"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Requested&nbsp;URL</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="REQUEST_URI"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Redirect&nbsp;Status&nbsp;Code</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="REDIRECT_STATUS"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">a&nbsp;href</span><span style="color: #007700">=</span><span style="color: #DD0000">"/"&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"btn&nbsp;btn-primary"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Kembali&nbsp;ke&nbsp;Beranda</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">a</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">div</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">html</span><span style="color: #007700">&gt;&nbsp;<br /></span></code></div></div></div><br />
Hasilnya kira-kira seperti ini:<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-14.png?resize=640%2C386&amp;ssl=1" loading="lazy"  width="640" height="386" alt="[Image: image-14.png?resize=640%2C386&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah begitu cara mengubah atau memodifikasi atau kustomisasi halaman 404 di shared hosting alias cPanel. Gampang, kan?<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Laravel PHP (Framework)</span></span><br />
<br />
Jika kita memakai sebuah web framework, apapun itu, biasanya halaman 404 dan lainnya sudah disediakan oleh si framework itu sendiri. Tugas kita hanya melakukan modifikasi terhadap file tersebut.<br />
<br />
Nah, pada praktek kali ini kita akan belajar bagaimana melakukan kustomisasi terhadap file atau halaman 404.<br />
<br />
Pertama, kita harus mem-publish file-filenya terlebih dahulu dengan perintah ini di Terminal atau CMD.<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;vendor</span><span style="color: #007700">:</span><span style="color: #0000BB">publish&nbsp;</span><span style="color: #007700">--</span><span style="color: #0000BB">tag</span><span style="color: #007700">=</span><span style="color: #0000BB">laravel</span><span style="color: #007700">-</span><span style="color: #0000BB">errors&nbsp;<br /></span></code></div></div></div><br />
Maka akan muncul beberapa file baru di dalam folder <span style="font-weight: bold;" class="mycode_b">resources/views/errors</span> seperti berikut:<br />
<ul class="mycode_list"><li>    401.blade.php<br />
</li>
<li>    402.blade.php<br />
</li>
<li>    403.blade.php<br />
</li>
<li>    404.blade.php<br />
</li>
<li>    419.blade.php<br />
</li>
<li>    429.blade.php<br />
</li>
<li>    500.blade.php<br />
</li>
<li>    503.blade.php<br />
</li>
<li>    layout.blade.php<br />
</li>
<li>    minimal.blade.php<br />
</li>
</ul>
<br />
Bagi kamu yang belum familiar dengan framework Laravel, setiap file yang mewakili view atau yang tampil di browser akan selalu berarkhiran .blade.php agar ia support templating yang disediakan oleh Laravel.<br />
<br />
Etapi itu kan gak cuma 404, ya? Kira-kira apa aja artinya?<br />
<br />
Untuk yang format 4xx itu menandakan error karena ulah si user. Sedangkan format 5xx itu menandakan error dari server web milik kita.<br />
<br />
Keterangan:<ul class="mycode_list"><li>401 Berkenaan dengan authentication atau hanya yang memiliki akses bisa melihat halaman tersebut<br />
</li>
<li>402 Berkenaan dengan payment atau halaman ini bisa diakses jika telah melakukan pembayaran tertentu<br />
</li>
<li>403 Berkenaan dengan authorization atau halaman ini bisa diakses dengan level user tertentu<br />
</li>
<li>404 Nah ini yang dibahas, yakni halamannya tidak ditemukan karena kamu salah nulis alamat<br />
</li>
<li>419 Berkenaan dengan page expired atau biasa terjadi karena token CSRF-nya sudah tidak valid karena terlalu lama atau tidak disediakan sama sekali<br />
</li>
<li>429 Berkenaan dengan rate limiting atau kamu terlalu banyak mengakses halaman ini. Lagi war ticket, ya?<br />
</li>
<li>500 Pesan error umum ketika server tidak tau bagaimana meresponse request dari user<br />
</li>
<li>503 Pesan error dari server ketika sedang down dan ini saatnya kamu puk-puk dia sebagai web administrator<br />
</li>
</ul>
<br />
Nah silahkan deh edit masing-masing file dengan desain yang sesuai, dengan keinginan kamu maupun dengan skenarionya.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">WordPress</span></span><br />
<br />
To be or not to be<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">nginx</span></span><br />
<br />
Mulai sekarang langkah-langkahnya akan lebih sederhana karena sudah agak menyentuh low level, yakni ke layer sistem operasi yang biasanya hanya terminal seperti Ubuntu Server dan lainnya.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Buat Halaman 404 Kustom</span><br />
<br />
Langkah pertama, kita buat dulu halaman 404 yang kita inginkan. Supaya lebih enak, kita kumpulkan saja pada lokasi document root-nya, yakni di /var/www/html. Jadi kita buat dulu filenya dengan:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>nano /var/www/html/404.html</code></div></div><br />
Oh iya, silahkan ganti editor nano dengan editor favorit masing-masing ya. Kemudian silahkan isi dengan desain halaman 404 yang diinginkan. Misalnya seperti ini:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">&lt;!</span><span style="color: #0000BB">DOCTYPE&nbsp;html</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">html&nbsp;lang</span><span style="color: #007700">=</span><span style="color: #DD0000">"id"</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;charset</span><span style="color: #007700">=</span><span style="color: #DD0000">"UTF-8"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;name</span><span style="color: #007700">=</span><span style="color: #DD0000">"viewport"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"width=device-width,&nbsp;initial-scale=1.0"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Halaman&nbsp;Tidak&nbsp;Ditemukan</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">style</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;body&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">family</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">Arial</span><span style="color: #007700">,&nbsp;</span><span style="color: #0000BB">sans</span><span style="color: #007700">-</span><span style="color: #0000BB">serif</span><span style="color: #007700">;&nbsp;</span><span style="color: #0000BB">text</span><span style="color: #007700">-</span><span style="color: #0000BB">align</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">center</span><span style="color: #007700">;&nbsp;</span><span style="color: #0000BB">padding</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">50px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;h1&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">size</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">50px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;p&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">size</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">20px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">style</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">404</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Oops</span><span style="color: #007700">!&nbsp;</span><span style="color: #0000BB">Halaman&nbsp;yang&nbsp;Anda&nbsp;cari&nbsp;tidak&nbsp;ditemukan</span><span style="color: #007700">.&lt;/</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">a&nbsp;href</span><span style="color: #007700">=</span><span style="color: #DD0000">"/"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Kembali&nbsp;ke&nbsp;Beranda</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">a</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">html</span><span style="color: #007700">&gt;&nbsp;<br /></span></code></div></div></div><br />
Simpan filenya, lalu restart nginx-nya.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo systemctl restart nginx</code></div></div><br />
Begitu deh, lebih sulit atau malah lebih mudah?<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">LiteSpeed</span></span><br />
<br />
Sebenarnya saya memakai OpenLiteSpeed untuk demo ini. Karena OpenLiteSpeed adalah gratis dan open source, sedangkan LiteSpeed itu produk premium berbayar. Mohon maklum. Hehe.<br />
<br />
Namun, beda nginx, beda pula dengan OpenLiteSpeed ini.<br />
<br />
Kalau nginx belum ada file 404 sehingga harus bikin sendiri, sedangkan si OpenLiteSpeed ini sudah ada. Sehingga kita diberi pilihan ingin mengubah file 404 default atau bikin baru. Ya mending bikin baru supaya file lamanya tetap terarsip dengan baik.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Buat Halaman 404 Kustom</span><br />
<br />
Baiklah, pertama kita buat file barunya di lokasi document root standar.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo nano /usr/local/lsws/Example/html/404.html</code></div></div><br />
Kemudian silahkan isi dengan desain halaman 404 milik kamu sendiri atau pakai seperti di bawah ini.<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">&lt;!</span><span style="color: #0000BB">DOCTYPE&nbsp;html</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">html&nbsp;lang</span><span style="color: #007700">=</span><span style="color: #DD0000">"id"</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;charset</span><span style="color: #007700">=</span><span style="color: #DD0000">"UTF-8"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;name</span><span style="color: #007700">=</span><span style="color: #DD0000">"viewport"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"width=device-width,&nbsp;initial-scale=1.0"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Halaman&nbsp;Tidak&nbsp;Ditemukan</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">style</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;body&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">family</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">Arial</span><span style="color: #007700">,&nbsp;</span><span style="color: #0000BB">sans</span><span style="color: #007700">-</span><span style="color: #0000BB">serif</span><span style="color: #007700">;&nbsp;</span><span style="color: #0000BB">text</span><span style="color: #007700">-</span><span style="color: #0000BB">align</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">center</span><span style="color: #007700">;&nbsp;</span><span style="color: #0000BB">padding</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">50px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;h1&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">size</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">50px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;p&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">size</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">20px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">style</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">404</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Oops</span><span style="color: #007700">!&nbsp;</span><span style="color: #0000BB">Halaman&nbsp;yang&nbsp;Anda&nbsp;cari&nbsp;tidak&nbsp;ditemukan</span><span style="color: #007700">.&lt;/</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">a&nbsp;href</span><span style="color: #007700">=</span><span style="color: #DD0000">"/"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Kembali&nbsp;ke&nbsp;Beranda</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">a</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">html</span><span style="color: #007700">&gt;&nbsp;<br /></span></code></div></div></div><br />
<span style="font-size: x-large;" class="mycode_size">Edit Konfigurasi Virtual Host Secara Manual</span><br />
<br />
Lalu kita ubah juga file konfigurasinya agar setiap aksi 404 selalu mengarah ke halaman yang telah kita buat tadi.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo nano /usr/local/lsws/conf/vhosts/Example/vhconf.conf</code></div></div><br />
Tambahkan atau ubah bagian berikut:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>errorPage 404 /404.html</code></div></div><br />
<span style="font-size: x-large;" class="mycode_size">Restart OpenLiteSpeed</span><br />
<br />
Setelah mengedit file konfigurasi, restart OpenLiteSpeed agar perubahan diterapkan:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo systemctl restart lsws</code></div></div><br />
Silahkan tes lagi dengan alamat asal deh.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Apache</span></span><br />
<br />
to be or not to be<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Penutup</span></span><br />
<br />
Masih banyak kekurangan dan mungkin saja cara-cara di atas bukan yang terbaik, ter-efektif dan ter-efisien, tetapi semoga menjadi khazanah baru bagi manteman pembaca sekalian.<br />
<br />
Akhir kata, mohon koreksi jika ada kekeliruan dalam artikel ini.]]></description>
			<content:encoded><![CDATA[Berangkat dari ribut-ribut di Twitter (kini X) mengenai halaman 404 yang tampilannya itu standar masih bawaan web server engine-nya itu sendiri. Kode 404 sendiri merujuk ke salah satu dari <a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Status" target="_blank" rel="noopener" class="mycode_url">HTTP response status codes</a> yang artinya Not Found atau halaman tidak ditemukan karena kesalahan pengguna dalam menuliskan alamat websitenya.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/404-NotFound.png" loading="lazy"  width="1920" height="1080" alt="[Image: 404-NotFound.png]" class="mycode_img" /></blockquote>
<br />
<br />
Berikut tampilan halaman 404 default pada beberapa web server terkenal.<br />
<br />
NGINX default 404<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/404-nginx.png?resize=640%2C409&amp;ssl=1" loading="lazy"  width="640" height="409" alt="[Image: 404-nginx.png?resize=640%2C409&amp;ssl=1]" class="mycode_img" /><br />
<br />
LiteSpeed default 404<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/404-litespeed.jpg?resize=640%2C391&amp;ssl=1" loading="lazy"  width="640" height="391" alt="[Image: 404-litespeed.jpg?resize=640%2C391&amp;ssl=1]" class="mycode_img" /><br />
<br />
Apache default 404<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/404-apache.png?resize=640%2C334&amp;ssl=1" loading="lazy"  width="640" height="334" alt="[Image: 404-apache.png?resize=640%2C334&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, namanya juga tampilan standar, pastilah agak kurang cantik terlihatnya. Jadi, bagaimana kalau kita bikin sendiri atau kustom halaman 404 tersebut? Yuk bismillah.<br />
<br />
---<br />
<br />
Daftar Isi<br />
<br />
Insyaallah kita akan membahas beberapa hal seputar kustomisasi halaman 404 ini, antara lain:<br />
<ul class="mycode_list"><li>    Shared Hosting<br />
</li>
<li>    Laravel PHP (framework)<br />
</li>
<li>    WordPress (CMS)<br />
</li>
<li>    nginx<br />
</li>
<li>    LiteSpeed<br />
</li>
<li>    Apache<br />
</li>
</ul>
<br />
Sebelum kita mulai satu per satu pembahasannya, kami ingin menyampaikan sesuatu.<br />
<br />
Blog nurfachmi.com hadir untuk berbagi ilmu dan pengalaman seputar teknologi, pemrograman, dan pengembangan karier di dunia IT. Semua konten yang ada di sini dibuat dengan penuh dedikasi agar bisa membantu lebih banyak orang memahami teknologi dengan cara yang lebih mudah dan praktis.<br />
<br />
Jika Anda merasa blog ini bermanfaat, Anda bisa mendukung operasional kami dengan memberikan donasi. Setiap kontribusi yang Anda berikan akan digunakan untuk:<br />
<br />
    ✅ Biaya server dan domain agar blog tetap online<br />
    ✅ Pengembangan fitur baru, termasuk platform LMS dengan kelas gratis dan berbayar<br />
    ✅ Pembuatan konten berkualitas yang lebih beragam<br />
<br />
Dukungan Anda, sekecil apa pun, sangat berarti bagi keberlangsungan blog ini. Mari bersama-sama membangun komunitas belajar yang lebih baik!<br />
<br />
Klik tombol donasi di bawah ini untuk berkontribusi.<br />
Terima kasih! ?<br />
<br />
Sekali lagi terima kasih atas dukungannya. Sekarang, mari kita belajar!<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Shared Hosting</span></span><br />
<br />
Pada umumnya jika kita menyewa shared hosting, biasanya sudah include dengan cPanel. Untuk memodifikasi halaman error 404, silahkan cari di menu pencarian dengan keyword Error Pages atau scroll sedikit tetikusnya sampai ketemu submenu Advanced dan klik ikon Error Pages.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-11.png?resize=640%2C174&amp;ssl=1" loading="lazy"  width="640" height="174" alt="[Image: image-11.png?resize=640%2C174&amp;ssl=1]" class="mycode_img" /><br />
<br />
Akan muncul kira-kira seperti ini pilihannya:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-12.png?resize=640%2C468&amp;ssl=1" loading="lazy"  width="640" height="468" alt="[Image: image-12.png?resize=640%2C468&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah kalau di cPanel, kita gak hanya bisa modifikasi halaman 404. Halaman error lainnya juga bisa dikustom kok.<br />
<br />
Selanjutnya kita klik saja menu 404 (Not found) dahulu dan kita akan diarahkan ke sebuah editor seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-13.png?resize=640%2C533&amp;ssl=1" loading="lazy"  width="640" height="533" alt="[Image: image-13.png?resize=640%2C533&amp;ssl=1]" class="mycode_img" /><br />
<br />
Yowis, silahkan taruh kode HTML sesuai keinginan kita sendiri di text editor tersebut. Pastikan klik tombol Save kalau sudah selesai ya.<br />
<br />
Etapi untuk memperkaya informasi mengenai error-nya, kita bisa menambahkan beberapa tag spesial, antara lain:<br />
<ul class="mycode_list"><li>    Referring URL: alamat asal sebelum sampai ke halaman 404 tersebut.<br />
</li>
<li>    Server Name: url server saat ini.<br />
</li>
<li>    Visitor's IP Address: IP Address pengunjung.<br />
</li>
<li>    Visitor's Browser: detail browser yang dipakai.<br />
</li>
<li>    Requested URL: url yang ingin diakses tetapi tidak ditemukan.<br />
</li>
<li>    Redirect Status Code: status kode redirect, biasanya sekitar 3xx.<br />
</li>
</ul>
<br />
Berikut contoh kodenya:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">&lt;!</span><span style="color: #0000BB">DOCTYPE&nbsp;html</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">html&nbsp;lang</span><span style="color: #007700">=</span><span style="color: #DD0000">"id"</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;&lt;</span><span style="color: #0000BB">meta&nbsp;charset</span><span style="color: #007700">=</span><span style="color: #DD0000">"utf-8"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;name</span><span style="color: #007700">=</span><span style="color: #DD0000">"viewport"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"width=device-width,&nbsp;initial-scale=1.0"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">404&nbsp;Not&nbsp;Found</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">link&nbsp;href</span><span style="color: #007700">=</span><span style="color: #DD0000">"https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css"&nbsp;</span><span style="color: #0000BB">rel</span><span style="color: #007700">=</span><span style="color: #DD0000">"stylesheet"</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">body&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"d-flex&nbsp;align-items-center&nbsp;justify-content-center&nbsp;vh-100&nbsp;bg-light"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">div&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"text-center"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">h1&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"display-1&nbsp;text-danger"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">404</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Halaman&nbsp;yang&nbsp;Anda&nbsp;cari&nbsp;tidak&nbsp;ditemukan</span><span style="color: #007700">.&lt;/</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Referring&nbsp;URL</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="HTTP_REFERER"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Server&nbsp;Name</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="HTTP_HOST"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Visitor&nbsp;IP&nbsp;Address</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="REMOTE_ADDR"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Browser</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="HTTP_USER_AGENT"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Requested&nbsp;URL</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="REQUEST_URI"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"lead"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Redirect&nbsp;Status&nbsp;Code</span><span style="color: #007700">:&nbsp;&lt;!--</span><span style="color: #FF8000">#echo&nbsp;var="REDIRECT_STATUS"&nbsp;--&gt;&lt;/p&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">a&nbsp;href</span><span style="color: #007700">=</span><span style="color: #DD0000">"/"&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"btn&nbsp;btn-primary"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Kembali&nbsp;ke&nbsp;Beranda</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">a</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">div</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">html</span><span style="color: #007700">&gt;&nbsp;<br /></span></code></div></div></div><br />
Hasilnya kira-kira seperti ini:<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-14.png?resize=640%2C386&amp;ssl=1" loading="lazy"  width="640" height="386" alt="[Image: image-14.png?resize=640%2C386&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah begitu cara mengubah atau memodifikasi atau kustomisasi halaman 404 di shared hosting alias cPanel. Gampang, kan?<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Laravel PHP (Framework)</span></span><br />
<br />
Jika kita memakai sebuah web framework, apapun itu, biasanya halaman 404 dan lainnya sudah disediakan oleh si framework itu sendiri. Tugas kita hanya melakukan modifikasi terhadap file tersebut.<br />
<br />
Nah, pada praktek kali ini kita akan belajar bagaimana melakukan kustomisasi terhadap file atau halaman 404.<br />
<br />
Pertama, kita harus mem-publish file-filenya terlebih dahulu dengan perintah ini di Terminal atau CMD.<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;vendor</span><span style="color: #007700">:</span><span style="color: #0000BB">publish&nbsp;</span><span style="color: #007700">--</span><span style="color: #0000BB">tag</span><span style="color: #007700">=</span><span style="color: #0000BB">laravel</span><span style="color: #007700">-</span><span style="color: #0000BB">errors&nbsp;<br /></span></code></div></div></div><br />
Maka akan muncul beberapa file baru di dalam folder <span style="font-weight: bold;" class="mycode_b">resources/views/errors</span> seperti berikut:<br />
<ul class="mycode_list"><li>    401.blade.php<br />
</li>
<li>    402.blade.php<br />
</li>
<li>    403.blade.php<br />
</li>
<li>    404.blade.php<br />
</li>
<li>    419.blade.php<br />
</li>
<li>    429.blade.php<br />
</li>
<li>    500.blade.php<br />
</li>
<li>    503.blade.php<br />
</li>
<li>    layout.blade.php<br />
</li>
<li>    minimal.blade.php<br />
</li>
</ul>
<br />
Bagi kamu yang belum familiar dengan framework Laravel, setiap file yang mewakili view atau yang tampil di browser akan selalu berarkhiran .blade.php agar ia support templating yang disediakan oleh Laravel.<br />
<br />
Etapi itu kan gak cuma 404, ya? Kira-kira apa aja artinya?<br />
<br />
Untuk yang format 4xx itu menandakan error karena ulah si user. Sedangkan format 5xx itu menandakan error dari server web milik kita.<br />
<br />
Keterangan:<ul class="mycode_list"><li>401 Berkenaan dengan authentication atau hanya yang memiliki akses bisa melihat halaman tersebut<br />
</li>
<li>402 Berkenaan dengan payment atau halaman ini bisa diakses jika telah melakukan pembayaran tertentu<br />
</li>
<li>403 Berkenaan dengan authorization atau halaman ini bisa diakses dengan level user tertentu<br />
</li>
<li>404 Nah ini yang dibahas, yakni halamannya tidak ditemukan karena kamu salah nulis alamat<br />
</li>
<li>419 Berkenaan dengan page expired atau biasa terjadi karena token CSRF-nya sudah tidak valid karena terlalu lama atau tidak disediakan sama sekali<br />
</li>
<li>429 Berkenaan dengan rate limiting atau kamu terlalu banyak mengakses halaman ini. Lagi war ticket, ya?<br />
</li>
<li>500 Pesan error umum ketika server tidak tau bagaimana meresponse request dari user<br />
</li>
<li>503 Pesan error dari server ketika sedang down dan ini saatnya kamu puk-puk dia sebagai web administrator<br />
</li>
</ul>
<br />
Nah silahkan deh edit masing-masing file dengan desain yang sesuai, dengan keinginan kamu maupun dengan skenarionya.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">WordPress</span></span><br />
<br />
To be or not to be<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">nginx</span></span><br />
<br />
Mulai sekarang langkah-langkahnya akan lebih sederhana karena sudah agak menyentuh low level, yakni ke layer sistem operasi yang biasanya hanya terminal seperti Ubuntu Server dan lainnya.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Buat Halaman 404 Kustom</span><br />
<br />
Langkah pertama, kita buat dulu halaman 404 yang kita inginkan. Supaya lebih enak, kita kumpulkan saja pada lokasi document root-nya, yakni di /var/www/html. Jadi kita buat dulu filenya dengan:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>nano /var/www/html/404.html</code></div></div><br />
Oh iya, silahkan ganti editor nano dengan editor favorit masing-masing ya. Kemudian silahkan isi dengan desain halaman 404 yang diinginkan. Misalnya seperti ini:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">&lt;!</span><span style="color: #0000BB">DOCTYPE&nbsp;html</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">html&nbsp;lang</span><span style="color: #007700">=</span><span style="color: #DD0000">"id"</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;charset</span><span style="color: #007700">=</span><span style="color: #DD0000">"UTF-8"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;name</span><span style="color: #007700">=</span><span style="color: #DD0000">"viewport"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"width=device-width,&nbsp;initial-scale=1.0"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Halaman&nbsp;Tidak&nbsp;Ditemukan</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">style</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;body&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">family</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">Arial</span><span style="color: #007700">,&nbsp;</span><span style="color: #0000BB">sans</span><span style="color: #007700">-</span><span style="color: #0000BB">serif</span><span style="color: #007700">;&nbsp;</span><span style="color: #0000BB">text</span><span style="color: #007700">-</span><span style="color: #0000BB">align</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">center</span><span style="color: #007700">;&nbsp;</span><span style="color: #0000BB">padding</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">50px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;h1&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">size</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">50px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;p&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">size</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">20px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">style</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">404</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Oops</span><span style="color: #007700">!&nbsp;</span><span style="color: #0000BB">Halaman&nbsp;yang&nbsp;Anda&nbsp;cari&nbsp;tidak&nbsp;ditemukan</span><span style="color: #007700">.&lt;/</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">a&nbsp;href</span><span style="color: #007700">=</span><span style="color: #DD0000">"/"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Kembali&nbsp;ke&nbsp;Beranda</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">a</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">html</span><span style="color: #007700">&gt;&nbsp;<br /></span></code></div></div></div><br />
Simpan filenya, lalu restart nginx-nya.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo systemctl restart nginx</code></div></div><br />
Begitu deh, lebih sulit atau malah lebih mudah?<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">LiteSpeed</span></span><br />
<br />
Sebenarnya saya memakai OpenLiteSpeed untuk demo ini. Karena OpenLiteSpeed adalah gratis dan open source, sedangkan LiteSpeed itu produk premium berbayar. Mohon maklum. Hehe.<br />
<br />
Namun, beda nginx, beda pula dengan OpenLiteSpeed ini.<br />
<br />
Kalau nginx belum ada file 404 sehingga harus bikin sendiri, sedangkan si OpenLiteSpeed ini sudah ada. Sehingga kita diberi pilihan ingin mengubah file 404 default atau bikin baru. Ya mending bikin baru supaya file lamanya tetap terarsip dengan baik.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Buat Halaman 404 Kustom</span><br />
<br />
Baiklah, pertama kita buat file barunya di lokasi document root standar.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo nano /usr/local/lsws/Example/html/404.html</code></div></div><br />
Kemudian silahkan isi dengan desain halaman 404 milik kamu sendiri atau pakai seperti di bawah ini.<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">&lt;!</span><span style="color: #0000BB">DOCTYPE&nbsp;html</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">html&nbsp;lang</span><span style="color: #007700">=</span><span style="color: #DD0000">"id"</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;charset</span><span style="color: #007700">=</span><span style="color: #DD0000">"UTF-8"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;name</span><span style="color: #007700">=</span><span style="color: #DD0000">"viewport"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"width=device-width,&nbsp;initial-scale=1.0"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Halaman&nbsp;Tidak&nbsp;Ditemukan</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">style</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;body&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">family</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">Arial</span><span style="color: #007700">,&nbsp;</span><span style="color: #0000BB">sans</span><span style="color: #007700">-</span><span style="color: #0000BB">serif</span><span style="color: #007700">;&nbsp;</span><span style="color: #0000BB">text</span><span style="color: #007700">-</span><span style="color: #0000BB">align</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">center</span><span style="color: #007700">;&nbsp;</span><span style="color: #0000BB">padding</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">50px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;h1&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">size</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">50px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;p&nbsp;</span><span style="color: #007700">{&nbsp;</span><span style="color: #0000BB">font</span><span style="color: #007700">-</span><span style="color: #0000BB">size</span><span style="color: #007700">:&nbsp;</span><span style="color: #0000BB">20px</span><span style="color: #007700">;&nbsp;}<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">style</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">404</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">h1</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Oops</span><span style="color: #007700">!&nbsp;</span><span style="color: #0000BB">Halaman&nbsp;yang&nbsp;Anda&nbsp;cari&nbsp;tidak&nbsp;ditemukan</span><span style="color: #007700">.&lt;/</span><span style="color: #0000BB">p</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">a&nbsp;href</span><span style="color: #007700">=</span><span style="color: #DD0000">"/"</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Kembali&nbsp;ke&nbsp;Beranda</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">a</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">html</span><span style="color: #007700">&gt;&nbsp;<br /></span></code></div></div></div><br />
<span style="font-size: x-large;" class="mycode_size">Edit Konfigurasi Virtual Host Secara Manual</span><br />
<br />
Lalu kita ubah juga file konfigurasinya agar setiap aksi 404 selalu mengarah ke halaman yang telah kita buat tadi.<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo nano /usr/local/lsws/conf/vhosts/Example/vhconf.conf</code></div></div><br />
Tambahkan atau ubah bagian berikut:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>errorPage 404 /404.html</code></div></div><br />
<span style="font-size: x-large;" class="mycode_size">Restart OpenLiteSpeed</span><br />
<br />
Setelah mengedit file konfigurasi, restart OpenLiteSpeed agar perubahan diterapkan:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>sudo systemctl restart lsws</code></div></div><br />
Silahkan tes lagi dengan alamat asal deh.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Apache</span></span><br />
<br />
to be or not to be<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Penutup</span></span><br />
<br />
Masih banyak kekurangan dan mungkin saja cara-cara di atas bukan yang terbaik, ter-efektif dan ter-efisien, tetapi semoga menjadi khazanah baru bagi manteman pembaca sekalian.<br />
<br />
Akhir kata, mohon koreksi jika ada kekeliruan dalam artikel ini.]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Event #001 Komunitas Back-End Tangerang]]></title>
			<link>https://bb.nurfachmi.com/thread-17.html</link>
			<pubDate>Sat, 02 May 2026 13:39:01 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-17.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 21, 2025</blockquote>
<br />
Masih bingung bagaimana membangun basis data / database untuk projek / aplikasimu? Ragu ingin melakukan pisah table atau digabung aja? Bergabunglah dengan Event #001 Backend ID x Laravel ID untuk mendapatkan inspirasi dan wawasan praktis tentang bagaimana membangun sistem basis data skala production! Gratis!<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/backend.webp" loading="lazy"  width="1792" height="1024" alt="[Image: backend.webp]" class="mycode_img" /></blockquote>
<br />
<br />
? Lokasi:<br />
Nutrihub Serpong, Foresta Business Loft 2<br />
Jl. BSD Raya Utama Unit 6, Pagedangan, Tangerang Regency, Banten 15339<br />
<br />
? Tanggal:<br />
Sabtu, 1 Februari 2025<br />
⏰ Waktu:<br />
13:00 – 18.00 WIB<br />
Topik Pembicaraan<br />
<ul class="mycode_list"><li>    Normalisasi Database<br />
</li>
<li>    Belajar bagaimana menjadi database designer dan memahami normalisasi database dengan praktis.<br />
</li>
<li>    Praktek Database pada Laravel<br />
</li>
<li>    Hands-on membangun database dalam Laravel dan menguasai Migration serta Eloquent.<br />
</li>
</ul>
<br />
Kenapa Anda Harus Datang?<br />
<ul class="mycode_list"><li>    Dapatkan wawasan langsung dari pembicara berpengalaman.<br />
</li>
<li>    Bertemu dengan komunitas Backend dan Laravel Devs lokal yang mendukung.<br />
</li>
<li>    Bangun jaringan dengan sesama developer|freelancer dan pelaku industri digital.<br />
</li>
</ul>
<br />
Pendaftaran<br />
<br />
Acara ini GRATIS dan terbuka untuk umum, tetapi tempat terbatas! Pastikan Anda mendaftar melalui backend.web.id agar tidak ketinggalan.<br />
<br />
Link: <a href="https://backend.web.id/events/membangun-sistem-basis-data-skala-production" target="_blank" rel="noopener" class="mycode_url">https://backend.web.id/events/membangun-...production</a>]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 21, 2025</blockquote>
<br />
Masih bingung bagaimana membangun basis data / database untuk projek / aplikasimu? Ragu ingin melakukan pisah table atau digabung aja? Bergabunglah dengan Event #001 Backend ID x Laravel ID untuk mendapatkan inspirasi dan wawasan praktis tentang bagaimana membangun sistem basis data skala production! Gratis!<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/backend.webp" loading="lazy"  width="1792" height="1024" alt="[Image: backend.webp]" class="mycode_img" /></blockquote>
<br />
<br />
? Lokasi:<br />
Nutrihub Serpong, Foresta Business Loft 2<br />
Jl. BSD Raya Utama Unit 6, Pagedangan, Tangerang Regency, Banten 15339<br />
<br />
? Tanggal:<br />
Sabtu, 1 Februari 2025<br />
⏰ Waktu:<br />
13:00 – 18.00 WIB<br />
Topik Pembicaraan<br />
<ul class="mycode_list"><li>    Normalisasi Database<br />
</li>
<li>    Belajar bagaimana menjadi database designer dan memahami normalisasi database dengan praktis.<br />
</li>
<li>    Praktek Database pada Laravel<br />
</li>
<li>    Hands-on membangun database dalam Laravel dan menguasai Migration serta Eloquent.<br />
</li>
</ul>
<br />
Kenapa Anda Harus Datang?<br />
<ul class="mycode_list"><li>    Dapatkan wawasan langsung dari pembicara berpengalaman.<br />
</li>
<li>    Bertemu dengan komunitas Backend dan Laravel Devs lokal yang mendukung.<br />
</li>
<li>    Bangun jaringan dengan sesama developer|freelancer dan pelaku industri digital.<br />
</li>
</ul>
<br />
Pendaftaran<br />
<br />
Acara ini GRATIS dan terbuka untuk umum, tetapi tempat terbatas! Pastikan Anda mendaftar melalui backend.web.id agar tidak ketinggalan.<br />
<br />
Link: <a href="https://backend.web.id/events/membangun-sistem-basis-data-skala-production" target="_blank" rel="noopener" class="mycode_url">https://backend.web.id/events/membangun-...production</a>]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Getting Started with GraphQL]]></title>
			<link>https://bb.nurfachmi.com/thread-16.html</link>
			<pubDate>Sat, 02 May 2026 13:37:01 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-16.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 12, 2025</blockquote>
<br />
GraphQL adalah sebuah bahasa query untuk API dan sebuah runtime untuk memenuhi query tersebut dengan data yang sudah ada. GraphQL menyediakan deskripsi yang lengkap dan mudah dipahami tentang data dalam API Anda, memberikan kemampuan kepada klien untuk meminta hanya apa yang mereka butuhkan dan tidak lebih, memudahkan pengembangan API seiring waktu, serta memungkinkan penggunaan alat pengembang yang canggih.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/graphql-logo.png" loading="lazy"  width="1200" height="630" alt="[Image: graphql-logo.png]" class="mycode_img" /></blockquote>
<br />
<br />
Paragraf di atas hanyalah terjemahan bebas dari paragraf asli yang berbunyi sebagai berikut:<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite>GraphQL is a query language for APIs and a runtime for fulfilling those queries with your existing data. GraphQL provides a complete and understandable description of the data in your API, gives clients the power to ask for exactly what they need and nothing more, makes it easier to evolve APIs over time, and enables powerful developer tools.</blockquote>
<br />
Kalau dalam bahasa yang lebih santai, mungkin seperti ini:<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite>GraphQL itu semacam bahasa query buat API, plus runtime yang ngurusin gimana query-nya dipenuhi pake data yang udah ada. Intinya, GraphQL bikin kamu ngerti banget soal data yang ada di API kamu, dan klien bisa minta data yang mereka perlu aja—nggak lebih, nggak kurang. Ini juga ngebantu banget kalau kamu mau upgrade API pelan-pelan tanpa ribet, plus ada banyak tools keren buat developer yang bikin kerja jadi lebih gampang.</blockquote>
<br />
Sampai sini paham tentang GraphQL? Penulis harap sih belum ya, karena penulis belum menjelaskan apa-apa tentang GraphQL ini. Hehehe. Kalau sudah paham, mungkin kamu perlu baca artikel lain saja. Hehehe (lagi).<br />
<br />
--<br />
<br />
Untuk yang lebih sering berkutat dengan REST API, mungkin akan terasa bingung apa sih bedanya antara REST dan GraphQL?<br />
<br />
Perbedaannya adalah GraphQL menggunakan query untuk meminta data, sedangkan REST tidak.<br />
<br />
GraphQL menggunakan satu endpoint untuk meminta data (apapun), sedangkan REST tidak. REST butuh satu endpoint untuk mendapatkan data user, lalu butuh endpoint lain untuk mendapatkan data transaksi, dan sebagainya. GraphQL cukup satu endpoint, hanya saja querynya yang berbeda.<br />
<br />
Mungkin kita cukupkan teorinya saat ini, untuk lebih lengkapnya bisa baca-baca di <a href="https://graphql.org/learn/" target="_blank" rel="noopener" class="mycode_url">dokumentasi GraphQL-nya</a> sendiri. Mari kita lanjut ke praktek.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Projek Baru</span></span><br />
<br />
Untuk praktek kali ini, kita akan menggunakan JavaScript dengan NodeJS sebagai runtimenya.<br />
<br />
Buat folder baru dengan nama graphql, lalu buat folder server dan client di dalamnya. Hasilnya kurang lebih seperti ini:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>graphql (folder)<br />
├── client (folder)<br />
└── server (folder)</code></div></div><br />
Lalu buat sebuah file server.js dan package.json di dalam folder server.<br />
<br />
--<br />
<br />
Isi dari package.json cukup seperti ini dulu:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>{<br />
  "name": "belajar-graphql",<br />
  "private": true,<br />
  "type": "module"<br />
}</code></div></div><br />
<br />
Apa artinya?<br />
<br />
Artinya kita akan membuat sebuah projek baru dengan nama belajar-graphql. Lalu projeknya bersifat private, belum ada rencana untuk menempatkannya ke package manager seperti npmjs atau lainnya. Terakhir, kita akan memanfaatkan teknologi javascript terbaru, yakni <span style="font-style: italic;" class="mycode_i"><span style="font-weight: bold;" class="mycode_b"><a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Modules" target="_blank" rel="noopener" class="mycode_url">JavaScript modules</a></span></span>.<br />
<br />
--<br />
<br />
Lalu kita isi file server.js dengan kode sederhana berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>const typeDefs = `<br />
  type Query {<br />
    greeting: String<br />
  }<br />
`;<br />
<br />
const resolvers = {<br />
  Query: {<br />
    greeting: () =&gt; 'Hello world!'<br />
  },<br />
}</code></div></div><br />
<br />
Apa artinya?<br />
<br />
Pada baris 1-5 kita mendeklarasikan sebuah variabel/konstanta dengan nama typeDefs yang isinya adalah sebuah SDL atau Schema Definition Language yang dapat dipanggil oleh klien/client.<br />
<br />
Mengapa typeDefs? Karena ingin menyatakan bahwa di sini lah kita menuliskan seluruh type definitions dari query-nya.<br />
<br />
type Query<br />
<br />
Baris ini mendeklarasikan bahwa kita akan membuat daftar query yang dapat diakses oleh klien. Semua query yang ingin disediakan API didefinisikan di dalam type Query.<br />
<br />
greeting: String<br />
<br />
Baris ini menandakan bahwa kita memiliki sebuah field dengan nama greeting yang tipe datanya adalah String. Field ini harus memiliki resolver atau sebuah fungsi yang mengembalikan nilai saat field ini dipanggil dalam sebuah query.<br />
<br />
Kemudian pada baris 7-11 disebut sebagai resolver yang dibungkus dalam variabel/konstanta dengan nama resolvers. Ini adalah sebuah objek JavaScript yang berisi implementasi fungsi untuk setiap field yang ada di dalam schema GraphQL.<br />
<br />
Objek ini digunakan untuk “menghubungkan” field di schema (typeDefs) dengan logika yang menyediakan data untuk field tersebut.<br />
<br />
Semua field di dalam Query harus memiliki resolver, kecuali jika data bisa diambil secara default (misalnya, dari field dalam objek yang sudah ada).<br />
<br />
Adapun greeting: () =&gt; 'Hello world!' adalah resolver untuk field greeting yang didefinisikan di schema sebelumnya.<br />
<br />
--<br />
<br />
Contoh singkat jika ingin melakukan operasi asinkron pada resolver adalah sebagai berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>const resolvers = {<br />
  Query: {<br />
    greeting: async () =&gt; {<br />
      try {<br />
        // Memanggil API eksternal untuk mendapatkan pesan<br />
        const response = await fetch("https://api.example.com/greeting");<br />
<br />
        // Periksa jika respons gagal<br />
        if (!response.ok) {<br />
          throw new Error(`HTTP error! Status: &#36;{response.status}`);<br />
        }<br />
<br />
        // Parse body respons ke JSON<br />
        const data = await response.json();<br />
<br />
        // Mengembalikan field `message` dari data<br />
        return data.message;<br />
      } catch (error) {<br />
        console.error("Error fetching data from API:", error);<br />
        throw new Error("Failed to fetch greeting from API.");<br />
      }<br />
    },<br />
  },<br />
};</code></div></div><br />
Silahkan lanjut ke halaman selanjutnya jika sudah memahami seluruh penjelasan di atas, ya! Kalau ada pertanyaan, coba layangkan di kolom komentar. Pertanyaanmu, insyaallah, tidak akan pernah dengan sengaja tidak dijawab.<br />
<br />
---<br />
<br />
Thoyyib, sebelumnya kita sudah mendefinisikan query dan resolver-nya, lalu bagaimana cara menjalankan kode sebelumnya itu? Caranya ialah menggunakan server, sebagaimana projek kita saat ini sedang ditulis dalam folder, namanya, server.<br />
<br />
Salah satu server yang populer untuk menjalankan GraphQL ialah Apollo. Mari kita install Apollo serta GraphQL-nya terlebih dahulu.<br />
<br />
Silahkan buka terminal dengan lokasi di dalam folder server ini, dan jalankan perintah berikut:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>npm install @apollo/server graphql</code></div></div><br />
Maka, otomatis akan muncul file baru package-lock.json dan folder node_modules. Jika kita buka file package.json, seharusnya kodenya telah update menjadi seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>{<br />
  "name": "belajar-graphql",<br />
  "private": true,<br />
  "type": "module",<br />
  "dependencies": {<br />
    "@apollo/server": "^4.11.3",<br />
    "graphql": "^16.10.0"<br />
  }<br />
}</code></div></div><br />
Jika instalasinya berhasil tanpa ada anu-anu, maka selanjutnya kita harus update file server.js-nya pula.<br />
<br />
Kita butuh ApolloServer dan startStandaloneServer untuk menjalankan ini, maka kita tambahkan dua baris ini di awal file.<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>import { ApolloServer } from "@apollo/server";<br />
import { startStandaloneServer } from "@apollo/server/standalone";</code></div></div><br />
Lalu pada akhir file, tambahkan ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>const server = new ApolloServer({ typeDefs, resolvers });<br />
const { url } = await startStandaloneServer(server, { listen: { port: 9000 } });<br />
console.log(`Server running at &#36;{url}`);</code></div></div><br />
Selengkapnya menjadi seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>import { ApolloServer } from "@apollo/server";<br />
import { startStandaloneServer } from "@apollo/server/standalone";<br />
<br />
const typeDefs = `<br />
  type Query {<br />
    greeting: String<br />
  }<br />
`;<br />
<br />
const resolvers = {<br />
  Query: {<br />
    greeting: () =&gt; 'Hello world!'<br />
  },<br />
}<br />
<br />
const server = new ApolloServer({ typeDefs, resolvers });<br />
const { url } = await startStandaloneServer(server, { listen: { port: 9000 } });<br />
console.log(`Server running at &#36;{url}`);</code></div></div><br />
Selanjutnya kita coba jalankan server ini dengan perintah:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>node server.js</code></div></div><blockquote class="mycode_quote"><cite>Quote:</cite>Server running at <a href="http://localhost:9000/" target="_blank" rel="noopener" class="mycode_url">http://localhost:9000/</a></blockquote>
<br />
Demikian harusnya yang tercetak di terminal setelah menjalankan perintah sebelumnya. Jika tidak demikian, maka periksa kembali kode kamu ya.<br />
<br />
Selanjutnya buka alamat tersebut di browser dan akan terbuka seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-7.png?resize=640%2C312&amp;ssl=1" loading="lazy"  width="640" height="312" alt="[Image: image-7.png?resize=640%2C312&amp;ssl=1]" class="mycode_img" /><br />
<br />
Halaman di atas adalah halaman sandbox dari Apollo untuk kita dapat menuliskan query GraphQL, menjalankannya, serta melihat hasilnya.<br />
<br />
Mari kita klik tombol dengan ikon play itu dan lihat apa yang terjadi.<br />
<br />
---<br />
<br />
Error dong? Iya, kan? Error?<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-9.png?resize=640%2C435&amp;ssl=1" loading="lazy"  width="640" height="435" alt="[Image: image-9.png?resize=640%2C435&amp;ssl=1]" class="mycode_img" /><br />
<br />
Mengapa error?<br />
<br />
Satu, kita tidak mendefinisikan type ExampleQuery, melainkan Query.<br />
<br />
Dua, kita tidak memiliki field id, melainkan greeting.<br />
<br />
So, mari ubah dua keyword tersebut dan jalankan lagi hasilnya.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-10.png?resize=640%2C166&amp;ssl=1" loading="lazy"  width="640" height="166" alt="[Image: image-10.png?resize=640%2C166&amp;ssl=1]" class="mycode_img" /><br />
<br />
Alhamdulillah muncul hasilnya.<br />
<br />
Sekarang, mari kita coba kasus nyata sederhana.<br />
<br />
---<br />
<br />
Kita akan membuat kasus tentang Buku saja, sederhana.<br />
<br />
Sesederhana kita membuat definisinya sebagai berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>type Buku {<br />
  id: ID!<br />
  judul: String!<br />
  penulis: String!<br />
  tahunTerbit: Int!<br />
  genre: String<br />
}</code></div></div><br />
Nah lho, apa artinya tanda seru (!) di sana? Artinya kolom atau field tersebut harus disertakan saat klien memanggil atau server memberikan respons.<br />
<br />
Terlihat di sana, selain field genre, seluruhnya wajib disertakan oleh client maupun server dalam request atau response-nya.<br />
<br />
Selanjutnya kita buat Query-nya seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>type Query {<br />
  semuaBuku: [Buku!]!<br />
}</code></div></div><br />
Maka jika diubah pada file server.js sebelumnya menjadi seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>const typeDefs = `<br />
  type Buku {<br />
    id: ID!<br />
    judul: String!<br />
    penulis: String!<br />
    tahunTerbit: Int!<br />
    genre: String<br />
  }<br />
<br />
  type Query {<br />
    semuaBuku: [Buku!]!<br />
  }<br />
`;</code></div></div><br />
Lalu kita ubah juga sisi resolver-nya menjadi begini:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>let bukuDatabase = [<br />
  { id: "1", judul: "Buku Satu", penulis: "Penulis A", tahunTerbit: 2024, genre: "Fiksi" },<br />
  { id: "2", judul: "Buku Dua", penulis: "Penulis B", tahunTerbit: 2025, genre: "Non-Fiksi" },<br />
];<br />
<br />
const resolvers = {<br />
  Query: {<br />
    semuaBuku: () =&gt; bukuDatabase,<br />
  },<br />
};</code></div></div><br />
Jika digabungkan, maka keseluruhan file server.js kali ini adalah sebagai berikut:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>import { ApolloServer } from "@apollo/server";<br />
import { startStandaloneServer } from "@apollo/server/standalone";<br />
<br />
const typeDefs = `<br />
  type Buku {<br />
    id: ID!<br />
    judul: String!<br />
    penulis: String!<br />
    tahunTerbit: Int!<br />
    genre: String<br />
  }<br />
<br />
  type Query {<br />
    semuaBuku: [Buku!]!<br />
  }<br />
`;<br />
<br />
let bukuDatabase = [<br />
  { id: "1", judul: "Buku Satu", penulis: "Penulis A", tahunTerbit: 2024, genre: "Fiksi" },<br />
  { id: "2", judul: "Buku Dua", penulis: "Penulis B", tahunTerbit: 2025, genre: "Non-Fiksi" },<br />
];<br />
<br />
const resolvers = {<br />
  Query: {<br />
    semuaBuku: () =&gt; bukuDatabase,<br />
  },<br />
};<br />
<br />
const server = new ApolloServer({ typeDefs, resolvers });<br />
const { url } = await startStandaloneServer(server, { listen: { port: 9000 } });<br />
console.log(`Server running at &#36;{url}`);</code></div></div><br />
Sekarang restart perintah node server.js di terminalnya dan refresh lagi halaman Apollo Servernya, lalu jalankan query berikut:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>query  {<br />
  semuaBuku {<br />
    id<br />
    judul<br />
    penulis<br />
    tahunTerbit<br />
    genre<br />
  }<br />
}</code></div></div><br />
Nah demikianlah Getting Started with GraphQL ini. Kalau diperhatikan, ini baru konsep “R” dalam “CRUD”. Juga kita baru sampai di folder server, belum ke folder client.<br />
<br />
Apakah artikel ini harus dilanjutkan lagi? Jawab di kolom komentar ya!]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 12, 2025</blockquote>
<br />
GraphQL adalah sebuah bahasa query untuk API dan sebuah runtime untuk memenuhi query tersebut dengan data yang sudah ada. GraphQL menyediakan deskripsi yang lengkap dan mudah dipahami tentang data dalam API Anda, memberikan kemampuan kepada klien untuk meminta hanya apa yang mereka butuhkan dan tidak lebih, memudahkan pengembangan API seiring waktu, serta memungkinkan penggunaan alat pengembang yang canggih.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/graphql-logo.png" loading="lazy"  width="1200" height="630" alt="[Image: graphql-logo.png]" class="mycode_img" /></blockquote>
<br />
<br />
Paragraf di atas hanyalah terjemahan bebas dari paragraf asli yang berbunyi sebagai berikut:<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite>GraphQL is a query language for APIs and a runtime for fulfilling those queries with your existing data. GraphQL provides a complete and understandable description of the data in your API, gives clients the power to ask for exactly what they need and nothing more, makes it easier to evolve APIs over time, and enables powerful developer tools.</blockquote>
<br />
Kalau dalam bahasa yang lebih santai, mungkin seperti ini:<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite>GraphQL itu semacam bahasa query buat API, plus runtime yang ngurusin gimana query-nya dipenuhi pake data yang udah ada. Intinya, GraphQL bikin kamu ngerti banget soal data yang ada di API kamu, dan klien bisa minta data yang mereka perlu aja—nggak lebih, nggak kurang. Ini juga ngebantu banget kalau kamu mau upgrade API pelan-pelan tanpa ribet, plus ada banyak tools keren buat developer yang bikin kerja jadi lebih gampang.</blockquote>
<br />
Sampai sini paham tentang GraphQL? Penulis harap sih belum ya, karena penulis belum menjelaskan apa-apa tentang GraphQL ini. Hehehe. Kalau sudah paham, mungkin kamu perlu baca artikel lain saja. Hehehe (lagi).<br />
<br />
--<br />
<br />
Untuk yang lebih sering berkutat dengan REST API, mungkin akan terasa bingung apa sih bedanya antara REST dan GraphQL?<br />
<br />
Perbedaannya adalah GraphQL menggunakan query untuk meminta data, sedangkan REST tidak.<br />
<br />
GraphQL menggunakan satu endpoint untuk meminta data (apapun), sedangkan REST tidak. REST butuh satu endpoint untuk mendapatkan data user, lalu butuh endpoint lain untuk mendapatkan data transaksi, dan sebagainya. GraphQL cukup satu endpoint, hanya saja querynya yang berbeda.<br />
<br />
Mungkin kita cukupkan teorinya saat ini, untuk lebih lengkapnya bisa baca-baca di <a href="https://graphql.org/learn/" target="_blank" rel="noopener" class="mycode_url">dokumentasi GraphQL-nya</a> sendiri. Mari kita lanjut ke praktek.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Projek Baru</span></span><br />
<br />
Untuk praktek kali ini, kita akan menggunakan JavaScript dengan NodeJS sebagai runtimenya.<br />
<br />
Buat folder baru dengan nama graphql, lalu buat folder server dan client di dalamnya. Hasilnya kurang lebih seperti ini:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>graphql (folder)<br />
├── client (folder)<br />
└── server (folder)</code></div></div><br />
Lalu buat sebuah file server.js dan package.json di dalam folder server.<br />
<br />
--<br />
<br />
Isi dari package.json cukup seperti ini dulu:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>{<br />
  "name": "belajar-graphql",<br />
  "private": true,<br />
  "type": "module"<br />
}</code></div></div><br />
<br />
Apa artinya?<br />
<br />
Artinya kita akan membuat sebuah projek baru dengan nama belajar-graphql. Lalu projeknya bersifat private, belum ada rencana untuk menempatkannya ke package manager seperti npmjs atau lainnya. Terakhir, kita akan memanfaatkan teknologi javascript terbaru, yakni <span style="font-style: italic;" class="mycode_i"><span style="font-weight: bold;" class="mycode_b"><a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Modules" target="_blank" rel="noopener" class="mycode_url">JavaScript modules</a></span></span>.<br />
<br />
--<br />
<br />
Lalu kita isi file server.js dengan kode sederhana berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>const typeDefs = `<br />
  type Query {<br />
    greeting: String<br />
  }<br />
`;<br />
<br />
const resolvers = {<br />
  Query: {<br />
    greeting: () =&gt; 'Hello world!'<br />
  },<br />
}</code></div></div><br />
<br />
Apa artinya?<br />
<br />
Pada baris 1-5 kita mendeklarasikan sebuah variabel/konstanta dengan nama typeDefs yang isinya adalah sebuah SDL atau Schema Definition Language yang dapat dipanggil oleh klien/client.<br />
<br />
Mengapa typeDefs? Karena ingin menyatakan bahwa di sini lah kita menuliskan seluruh type definitions dari query-nya.<br />
<br />
type Query<br />
<br />
Baris ini mendeklarasikan bahwa kita akan membuat daftar query yang dapat diakses oleh klien. Semua query yang ingin disediakan API didefinisikan di dalam type Query.<br />
<br />
greeting: String<br />
<br />
Baris ini menandakan bahwa kita memiliki sebuah field dengan nama greeting yang tipe datanya adalah String. Field ini harus memiliki resolver atau sebuah fungsi yang mengembalikan nilai saat field ini dipanggil dalam sebuah query.<br />
<br />
Kemudian pada baris 7-11 disebut sebagai resolver yang dibungkus dalam variabel/konstanta dengan nama resolvers. Ini adalah sebuah objek JavaScript yang berisi implementasi fungsi untuk setiap field yang ada di dalam schema GraphQL.<br />
<br />
Objek ini digunakan untuk “menghubungkan” field di schema (typeDefs) dengan logika yang menyediakan data untuk field tersebut.<br />
<br />
Semua field di dalam Query harus memiliki resolver, kecuali jika data bisa diambil secara default (misalnya, dari field dalam objek yang sudah ada).<br />
<br />
Adapun greeting: () =&gt; 'Hello world!' adalah resolver untuk field greeting yang didefinisikan di schema sebelumnya.<br />
<br />
--<br />
<br />
Contoh singkat jika ingin melakukan operasi asinkron pada resolver adalah sebagai berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>const resolvers = {<br />
  Query: {<br />
    greeting: async () =&gt; {<br />
      try {<br />
        // Memanggil API eksternal untuk mendapatkan pesan<br />
        const response = await fetch("https://api.example.com/greeting");<br />
<br />
        // Periksa jika respons gagal<br />
        if (!response.ok) {<br />
          throw new Error(`HTTP error! Status: &#36;{response.status}`);<br />
        }<br />
<br />
        // Parse body respons ke JSON<br />
        const data = await response.json();<br />
<br />
        // Mengembalikan field `message` dari data<br />
        return data.message;<br />
      } catch (error) {<br />
        console.error("Error fetching data from API:", error);<br />
        throw new Error("Failed to fetch greeting from API.");<br />
      }<br />
    },<br />
  },<br />
};</code></div></div><br />
Silahkan lanjut ke halaman selanjutnya jika sudah memahami seluruh penjelasan di atas, ya! Kalau ada pertanyaan, coba layangkan di kolom komentar. Pertanyaanmu, insyaallah, tidak akan pernah dengan sengaja tidak dijawab.<br />
<br />
---<br />
<br />
Thoyyib, sebelumnya kita sudah mendefinisikan query dan resolver-nya, lalu bagaimana cara menjalankan kode sebelumnya itu? Caranya ialah menggunakan server, sebagaimana projek kita saat ini sedang ditulis dalam folder, namanya, server.<br />
<br />
Salah satu server yang populer untuk menjalankan GraphQL ialah Apollo. Mari kita install Apollo serta GraphQL-nya terlebih dahulu.<br />
<br />
Silahkan buka terminal dengan lokasi di dalam folder server ini, dan jalankan perintah berikut:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>npm install @apollo/server graphql</code></div></div><br />
Maka, otomatis akan muncul file baru package-lock.json dan folder node_modules. Jika kita buka file package.json, seharusnya kodenya telah update menjadi seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>{<br />
  "name": "belajar-graphql",<br />
  "private": true,<br />
  "type": "module",<br />
  "dependencies": {<br />
    "@apollo/server": "^4.11.3",<br />
    "graphql": "^16.10.0"<br />
  }<br />
}</code></div></div><br />
Jika instalasinya berhasil tanpa ada anu-anu, maka selanjutnya kita harus update file server.js-nya pula.<br />
<br />
Kita butuh ApolloServer dan startStandaloneServer untuk menjalankan ini, maka kita tambahkan dua baris ini di awal file.<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>import { ApolloServer } from "@apollo/server";<br />
import { startStandaloneServer } from "@apollo/server/standalone";</code></div></div><br />
Lalu pada akhir file, tambahkan ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>const server = new ApolloServer({ typeDefs, resolvers });<br />
const { url } = await startStandaloneServer(server, { listen: { port: 9000 } });<br />
console.log(`Server running at &#36;{url}`);</code></div></div><br />
Selengkapnya menjadi seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>import { ApolloServer } from "@apollo/server";<br />
import { startStandaloneServer } from "@apollo/server/standalone";<br />
<br />
const typeDefs = `<br />
  type Query {<br />
    greeting: String<br />
  }<br />
`;<br />
<br />
const resolvers = {<br />
  Query: {<br />
    greeting: () =&gt; 'Hello world!'<br />
  },<br />
}<br />
<br />
const server = new ApolloServer({ typeDefs, resolvers });<br />
const { url } = await startStandaloneServer(server, { listen: { port: 9000 } });<br />
console.log(`Server running at &#36;{url}`);</code></div></div><br />
Selanjutnya kita coba jalankan server ini dengan perintah:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>node server.js</code></div></div><blockquote class="mycode_quote"><cite>Quote:</cite>Server running at <a href="http://localhost:9000/" target="_blank" rel="noopener" class="mycode_url">http://localhost:9000/</a></blockquote>
<br />
Demikian harusnya yang tercetak di terminal setelah menjalankan perintah sebelumnya. Jika tidak demikian, maka periksa kembali kode kamu ya.<br />
<br />
Selanjutnya buka alamat tersebut di browser dan akan terbuka seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-7.png?resize=640%2C312&amp;ssl=1" loading="lazy"  width="640" height="312" alt="[Image: image-7.png?resize=640%2C312&amp;ssl=1]" class="mycode_img" /><br />
<br />
Halaman di atas adalah halaman sandbox dari Apollo untuk kita dapat menuliskan query GraphQL, menjalankannya, serta melihat hasilnya.<br />
<br />
Mari kita klik tombol dengan ikon play itu dan lihat apa yang terjadi.<br />
<br />
---<br />
<br />
Error dong? Iya, kan? Error?<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-9.png?resize=640%2C435&amp;ssl=1" loading="lazy"  width="640" height="435" alt="[Image: image-9.png?resize=640%2C435&amp;ssl=1]" class="mycode_img" /><br />
<br />
Mengapa error?<br />
<br />
Satu, kita tidak mendefinisikan type ExampleQuery, melainkan Query.<br />
<br />
Dua, kita tidak memiliki field id, melainkan greeting.<br />
<br />
So, mari ubah dua keyword tersebut dan jalankan lagi hasilnya.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-10.png?resize=640%2C166&amp;ssl=1" loading="lazy"  width="640" height="166" alt="[Image: image-10.png?resize=640%2C166&amp;ssl=1]" class="mycode_img" /><br />
<br />
Alhamdulillah muncul hasilnya.<br />
<br />
Sekarang, mari kita coba kasus nyata sederhana.<br />
<br />
---<br />
<br />
Kita akan membuat kasus tentang Buku saja, sederhana.<br />
<br />
Sesederhana kita membuat definisinya sebagai berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>type Buku {<br />
  id: ID!<br />
  judul: String!<br />
  penulis: String!<br />
  tahunTerbit: Int!<br />
  genre: String<br />
}</code></div></div><br />
Nah lho, apa artinya tanda seru (!) di sana? Artinya kolom atau field tersebut harus disertakan saat klien memanggil atau server memberikan respons.<br />
<br />
Terlihat di sana, selain field genre, seluruhnya wajib disertakan oleh client maupun server dalam request atau response-nya.<br />
<br />
Selanjutnya kita buat Query-nya seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>type Query {<br />
  semuaBuku: [Buku!]!<br />
}</code></div></div><br />
Maka jika diubah pada file server.js sebelumnya menjadi seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>const typeDefs = `<br />
  type Buku {<br />
    id: ID!<br />
    judul: String!<br />
    penulis: String!<br />
    tahunTerbit: Int!<br />
    genre: String<br />
  }<br />
<br />
  type Query {<br />
    semuaBuku: [Buku!]!<br />
  }<br />
`;</code></div></div><br />
Lalu kita ubah juga sisi resolver-nya menjadi begini:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>let bukuDatabase = [<br />
  { id: "1", judul: "Buku Satu", penulis: "Penulis A", tahunTerbit: 2024, genre: "Fiksi" },<br />
  { id: "2", judul: "Buku Dua", penulis: "Penulis B", tahunTerbit: 2025, genre: "Non-Fiksi" },<br />
];<br />
<br />
const resolvers = {<br />
  Query: {<br />
    semuaBuku: () =&gt; bukuDatabase,<br />
  },<br />
};</code></div></div><br />
Jika digabungkan, maka keseluruhan file server.js kali ini adalah sebagai berikut:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>import { ApolloServer } from "@apollo/server";<br />
import { startStandaloneServer } from "@apollo/server/standalone";<br />
<br />
const typeDefs = `<br />
  type Buku {<br />
    id: ID!<br />
    judul: String!<br />
    penulis: String!<br />
    tahunTerbit: Int!<br />
    genre: String<br />
  }<br />
<br />
  type Query {<br />
    semuaBuku: [Buku!]!<br />
  }<br />
`;<br />
<br />
let bukuDatabase = [<br />
  { id: "1", judul: "Buku Satu", penulis: "Penulis A", tahunTerbit: 2024, genre: "Fiksi" },<br />
  { id: "2", judul: "Buku Dua", penulis: "Penulis B", tahunTerbit: 2025, genre: "Non-Fiksi" },<br />
];<br />
<br />
const resolvers = {<br />
  Query: {<br />
    semuaBuku: () =&gt; bukuDatabase,<br />
  },<br />
};<br />
<br />
const server = new ApolloServer({ typeDefs, resolvers });<br />
const { url } = await startStandaloneServer(server, { listen: { port: 9000 } });<br />
console.log(`Server running at &#36;{url}`);</code></div></div><br />
Sekarang restart perintah node server.js di terminalnya dan refresh lagi halaman Apollo Servernya, lalu jalankan query berikut:<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>query  {<br />
  semuaBuku {<br />
    id<br />
    judul<br />
    penulis<br />
    tahunTerbit<br />
    genre<br />
  }<br />
}</code></div></div><br />
Nah demikianlah Getting Started with GraphQL ini. Kalau diperhatikan, ini baru konsep “R” dalam “CRUD”. Juga kita baru sampai di folder server, belum ke folder client.<br />
<br />
Apakah artikel ini harus dilanjutkan lagi? Jawab di kolom komentar ya!]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Private: ElysiaJS Basic]]></title>
			<link>https://bb.nurfachmi.com/thread-15.html</link>
			<pubDate>Sat, 02 May 2026 13:27:33 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-15.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 11, 2025</blockquote>
<br />
<img src="https://nurfachmi.com/wp-content/uploads/2025/01/elysia_v.webp" loading="lazy"  width="1918" height="1068" alt="[Image: elysia_v.webp]" class="mycode_img" /><br />
<br />
<span style="font-weight: bold;" class="mycode_b">Basic ElysiaJS</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=DHEflULuLJo" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=DHEflULuLJo</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Router</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=bmfUTd9_gwc" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=bmfUTd9_gwc</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">JSON Response</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=JRcgw84m8RQ" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=JRcgw84m8RQ</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">HTML Response</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=EkOD9shz9xU" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=EkOD9shz9xU</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Handling Request Body and Schema Guard</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=c__STXlRLFs" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=c__STXlRLFs</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Handling Headers</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=IvOOtqgZuq0" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=IvOOtqgZuq0</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Handling Query</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=7oE6XIclA74" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=7oE6XIclA74</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Handling Dynamic Route</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=nbtPkSiH8AA" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=nbtPkSiH8AA</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Global Hooks</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=EAs9tcHRwqs" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=EAs9tcHRwqs</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Local Hooks</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=Ik-yExgNxec" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=Ik-yExgNxec</a><br />
</li>
</ul>
]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 11, 2025</blockquote>
<br />
<img src="https://nurfachmi.com/wp-content/uploads/2025/01/elysia_v.webp" loading="lazy"  width="1918" height="1068" alt="[Image: elysia_v.webp]" class="mycode_img" /><br />
<br />
<span style="font-weight: bold;" class="mycode_b">Basic ElysiaJS</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=DHEflULuLJo" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=DHEflULuLJo</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Router</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=bmfUTd9_gwc" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=bmfUTd9_gwc</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">JSON Response</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=JRcgw84m8RQ" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=JRcgw84m8RQ</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">HTML Response</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=EkOD9shz9xU" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=EkOD9shz9xU</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Handling Request Body and Schema Guard</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=c__STXlRLFs" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=c__STXlRLFs</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Handling Headers</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=IvOOtqgZuq0" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=IvOOtqgZuq0</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Handling Query</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=7oE6XIclA74" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=7oE6XIclA74</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Handling Dynamic Route</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=nbtPkSiH8AA" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=nbtPkSiH8AA</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Global Hooks</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=EAs9tcHRwqs" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=EAs9tcHRwqs</a><br />
</li>
</ul>
<br />
<span style="font-weight: bold;" class="mycode_b">Local Hooks</span><br />
<ul class="mycode_list"><li><a href="https://www.youtube.com/watch?v=Ik-yExgNxec" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=Ik-yExgNxec</a><br />
</li>
</ul>
]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Private: Bexlite Course Introduction]]></title>
			<link>https://bb.nurfachmi.com/thread-14.html</link>
			<pubDate>Sat, 02 May 2026 13:23:37 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-14.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 10, 2025</blockquote>
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Bun.js</span></span><br />
<br />
<span style="font-weight: bold;" class="mycode_b"><a href="https://bun.sh/blog/bun-v1.1" target="_blank" rel="noopener" class="mycode_url">Bun.js</a> all-in-one toolkit</span>, untuk menjalankan aplikasi javascript dan typescript, mulai dari single script hingga fullstack application. Bagi kamu yang pernah menggunakan nodejs, pada dasarnya bun memiliki fungsi yang sama. Yaitu untuk menjalankan javascript di luar browser.<br />
<br />
Mungkin sampai hari ini kita belum melihat company atau startup yang mengadopsi Bun untuk production di aplikasi yang memiliki scale yang besar. Hanya saja, melihat Bunjs dan komunitasnya. Sangat tidak menutup kemungkinan Bunjs akan di adopsi di masa mendatang.<br />
<br />
Bexlite sendiri menggunakan Bunjs karena performanya yang baik, dan yang paling penting, bunjs bisa menjalankan typescript secara native. Tanpa bantuan library apapun.<br />
<br />
Bun sendiri sebagai package manager memiliki performa yang sangat cepat. Dalam Benchmarknya menginstall react dengan vite, bun bisa <span style="font-weight: bold;" class="mycode_b">18x lebih cepat dari yarn dan pnpm</span> dan <span style="font-weight: bold;" class="mycode_b">30x lebih cepat daripada npm</span>.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-6.png?resize=640%2C234&amp;ssl=1" loading="lazy"  width="640" height="234" alt="[Image: image-6.png?resize=640%2C234&amp;ssl=1]" class="mycode_img" /><br />
<br />
Kamu bisa menggunakan bun.js dengan windows, linux, wsl ataupun mac.<br />
<br />
Kamu bisa lihat cara menginstall bun.js <a href="https://bun.sh/docs/installation" target="_blank" rel="noopener" class="mycode_url">di sini</a>.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">ElysiaJS</span></span><br />
<br />
<span style="font-weight: bold;" class="mycode_b">ElysiaJS</span>, sebuah framework yang di jalankan di atas bunjs runtime. Menggunakan banyak API dari bun, memanfaatkan kecepatan bun hingga bisa menghandle request hingga lebih dari 2jt request per second.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-8.png?resize=640%2C256&amp;ssl=1" loading="lazy"  width="640" height="256" alt="[Image: image-8.png?resize=640%2C256&amp;ssl=1]" class="mycode_img" /><br />
<br />
Bexlite menggunakan ElysiaJS karena kemudahan dan kecepatannya, tidak hanya dibandingkan dengan Express, atau javascript framework yang lain. Tetapi juga dengan framework dan bahasa yang lain.<br />
<br />
Terlebih bagi pengguna typescript, Elysia memiliki type-safety secara default. Dan ini akan memudahkan kamu untuk membangun aplikasi yang safe jika di-implementasikan dengan benar.<br />
<br />
Elysia juga memiliki beberapa fitur menarik yang bisa kita gunakan untuk membangun project dengan bexlite. Seperti CRON, Auto handling format including JSON dan FormData. Ditambah lagi dengan official plugin seperti HTML, JSX, JWT, dll, akan sangat memudahkan dalam menggunakan Bexlite.<br />
<br />
Kamu bisa baca lebih lanjut tentang elysia <a href="https://elysiajs.com/" target="_blank" rel="noopener" class="mycode_url">di sini</a>.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">HTMX</span></span><br />
<br />
So, pasti temen-temen sudah ga asing lagi dengan yang namanya HTMX, yang tiap hari MEMEnya melintas di timeline kita.<br />
<br />
Tapi, apa sih sebenernya HTMX ?<br />
Is it good ? bad ? Lalu apa bedanya HTMX dengan framework umum seperti React, Vue atau yang lain ?<br />
<br />
Okey, mari kita kenalan dengan HTMX.<br />
<br />
HTMX, adalah sebuah javascript frontend library yang memberikan alternative yang make sense bagi developer untuk develop web app dengan metode yang berbeda dari kebanyakan framework pada umumnya.<br />
<br />
Javascript SPA Framework, berkomunikasi dengan REST API. Yang mana client akan melakukan request kepada server, dan server merespon dengan JSON. yang kemudian client harus menjalankan logic untuk menerjemahkan JSON kedalam bentuk UI.<br />
<br />
HTMX, menempuh jalur yang berbeda dari kebanyakan frontend framework. HTMX menggunakan hypermedia sebagai format komunikasinya dibandingkan REST API yang berbentuk Text.<br />
<br />
Maksudnya adalah ketika klien melakukan request kepada server, server tidak lagi memberikan response dalam bentuk JSON, tetapi dalam bentuk HTML.<br />
<br />
Hypermedia sebagai response komunikasi server kepada client, bukanlah hal baru. Ini sebagaimana kita mengakses sebuah URL, kemudian server merespon dengan HTML yang sudah di render. Yang menjadi problem dari Hypermedia sebelumnya adalah response harus diberikan dalam bentuk keseluruhan laman.<br />
<br />
Karena memang keterbatasan dari html yang hanya bisa melakukan request hanya dengan anchor tag dan form yang kemudian harus di reload secara keseluruhan setelah mendapatkan respons.<br />
<br />
Dengan HTMX, melakukan http request dengan HTML tidak lagi terbatas pada anchor dan juga form. Dan juga tidak harus pada level full page, tapi pada level parsialnya.<br />
<br />
Salah satu motivasi munculnya HTMX adalah untuk mempersimple pembuatan web application. Yaitu dengan melakukan centralisasi logic pada server. Yang mana ini sangat make sense, karena server adalah tempat dimana permanent state berada.<br />
<br />
Ini juga yang dilakukan oleh banyak SPA framework akhir-akhir ini seperti react, nextjs yang mencoba untuk menempuh approach yang sama dengan mengenalkan React Server Component dan Server Action.<br />
<br />
But, pertanyaannya adalah aplikasi yang bagaimana yang mungkin cocok untuk kita gunakan HTMX di dalamnya.<br />
<br />
Sebagai jawaban dari pertanyaan ini, Saya akan berikan 2 kriteria.<br />
<ul class="mycode_list"><li>    Dimana developer mau meletakkan state aplikasinya ?<br />
</li>
<li>    Dan bagaimana developer memposisikan dirinya<br />
</li>
</ul>
<br />
Mari kita bahas kriteria ini.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Yang pertama, adalah dimana state diletakkan ?</span><br />
<br />
Spektrum web app ini cukup luas, tetapi kalo tarik secara horizontal. Hanya ada 2 jenis, yang fokus pada interaktivity dan fokus kepada server logic.<br />
<br />
Kita bisa melihat aplikasi game di web yang tentu statenya akan cepat dan seringkali berubah, dan tentu saja state aplikasi lebih baik diletakkan pada client untuk efisiensi komunikasi, yang kemudian dengan interval waktu tertentu transient state ini di kirimkan ke server.<br />
<br />
Ini sedikit berbeda dengan High Risk Application seperti Bank atau Finance App, yang state dan logicnya diletakkan di dalam server. Kenapa ? Yes, karena high risk application can’t trust the user.<br />
<br />
Maka sekarang kita bisa tahu, jika aplikasi kita sangat memerlukan interaktivity yang terus-terusan berubah, mungkin SPA framework seperti React lebih cocok. Adapun jika aplikasinya tidak memerlukan state yang terlalu sering berubah. HTMX akan jauh lebih simple untuk digunakan.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Yang kedua, adalah bagimana developer memposisikan dirinya.</span><br />
<br />
Jika kamu seorang developer entah frontend ataupun backend yang fokus dengan server-side logic, maka HTMX bisa jadi pilihan yang paling baik. Karena HTMX tidak membatasi developer pada bahasa pemrogramannya. Apapun bahasa yang kamu gunakan selama frontend menggunakan HTML, CSS dan Javascript, kamu bisa menggunakan HTMX.<br />
<br />
Namun jika kamu seorang developer yang fokus pada client-side logic, dan fokus pada bahasa javascript, mungkin react atau nextjs menjadi pilihan yang lebih baik.<br />
<br />
---<br />
<br />
Penggunaan HTMX di dalam Bexlite selaras dengan tujuan awal dibuatnya Tech Stack ini yaitu Simplicity. Dengan menggunakan HTMX library, kita bisa menggunakan HTML, bahasa yang diketahui oleh semua developer untuk membuat aplikasi dengan SPA Experience tanpa harus menggunakan bloated-features framework, tanpa harus belajar lagi framework-framework baru.<br />
<br />
Kita cukup tambahkan HTMX attribute di dalam HTML and done.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">JSX</span></span><br />
<br />
Seperti yang kita tahu, JSX adalah format umum yang digunakan di dalam frontend-framework. JSX secara khusus bukan templating Engine. Tetapi JSX kita gunakan di dalam Bexlite untuk memanfaatkan apa yang sudah kita pahami.<br />
<br />
JSX kita gunakan di dalam Bexlite sebagai templating model. Dan memudahkan kita dalam membuat UI components. Dengan menggunakan JSX, kita bisa dengan mudah mimic React dalam membuat reusable components.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">SQLite</span></span><br />
<br />
<span style="font-weight: bold;" class="mycode_b">Sqlite, the underdog database.</span><br />
<br />
Sedikit hiperbola, but yes. Sqlite sepertinya yang banyak diragukan di dalam tech stack ini. Sqlite seperti menjadi database yang tidak layak untuk production. Jika kita bicara tentang model big-scale apps dengan arsitektur yang rumit, maka iya. Mungkin sqlite tidak cocok digunakan. But untuk aplikasi small-mid sqlite lebih dari cukup untuk digunakan.<br />
<br />
Sqlite memiliki performa yang sangat cepat, embedded, dan dengan memanfaatkan teknologi embedded kamu tidak lagi perlu untuk mengalami “network io” dalam melakukan query kepada database. Silahkan baca post saya dibawah.<br />
<br />
<a href="https://x.com/indrazulfi/status/1790286534895415804" target="_blank" rel="noopener" class="mycode_url">https://x.com/indrazulfi/status/1790286534895415804</a><br />
<br />
Jika kamu merasa cocok dengan Bexlite secara umum, namun tidak cocok dengan menggunakan Sqlite, kamu bisa dengan mudah menggantikan SQLite dengan Database yang lain semisal PostgreSQL, atau Mongo. Saya tidak menyarankan kamu menggunakan ORM yang menggunakan query engine agar tidak memperparah latency seperti Prisma ORM untuk production.<br />
<br />
Jika kamu mau menggunakan ORM, kamu bisa menggunakan Drizzle ORM atau Query builder seperti Kisely. Dengan begitu ini akan mengurangi latency query disebabkan engine ORM seperti yang dimiliki Prisma.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">TursoDB</span></span><br />
<br />
Turso DB adalah Provider Sqlite untuk production. Turso memberikan kemudahan untuk melakukan Scale dari aplikasi yang menggunakan Sqlite.<br />
<br />
Turso juga memiliki free-tier yang super generous dibandingkan dengan provider yang lain. Turso memberikan free-tier user untuk bisa membuat hinggal 500 Database, 9GB Storage, 3 Replication untuk edge location.<br />
<br />
Kamu akan dengan mudah melakukan scale bexlite dengan extending Sqlite yang digunakan dengan <a href="https://turso.tech/" target="_blank" rel="noopener" class="mycode_url">TursoDB</a>.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/elysia_v.webp" loading="lazy"  width="1918" height="1068" alt="[Image: elysia_v.webp]" class="mycode_img" /></blockquote>
]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 10, 2025</blockquote>
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">Bun.js</span></span><br />
<br />
<span style="font-weight: bold;" class="mycode_b"><a href="https://bun.sh/blog/bun-v1.1" target="_blank" rel="noopener" class="mycode_url">Bun.js</a> all-in-one toolkit</span>, untuk menjalankan aplikasi javascript dan typescript, mulai dari single script hingga fullstack application. Bagi kamu yang pernah menggunakan nodejs, pada dasarnya bun memiliki fungsi yang sama. Yaitu untuk menjalankan javascript di luar browser.<br />
<br />
Mungkin sampai hari ini kita belum melihat company atau startup yang mengadopsi Bun untuk production di aplikasi yang memiliki scale yang besar. Hanya saja, melihat Bunjs dan komunitasnya. Sangat tidak menutup kemungkinan Bunjs akan di adopsi di masa mendatang.<br />
<br />
Bexlite sendiri menggunakan Bunjs karena performanya yang baik, dan yang paling penting, bunjs bisa menjalankan typescript secara native. Tanpa bantuan library apapun.<br />
<br />
Bun sendiri sebagai package manager memiliki performa yang sangat cepat. Dalam Benchmarknya menginstall react dengan vite, bun bisa <span style="font-weight: bold;" class="mycode_b">18x lebih cepat dari yarn dan pnpm</span> dan <span style="font-weight: bold;" class="mycode_b">30x lebih cepat daripada npm</span>.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-6.png?resize=640%2C234&amp;ssl=1" loading="lazy"  width="640" height="234" alt="[Image: image-6.png?resize=640%2C234&amp;ssl=1]" class="mycode_img" /><br />
<br />
Kamu bisa menggunakan bun.js dengan windows, linux, wsl ataupun mac.<br />
<br />
Kamu bisa lihat cara menginstall bun.js <a href="https://bun.sh/docs/installation" target="_blank" rel="noopener" class="mycode_url">di sini</a>.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">ElysiaJS</span></span><br />
<br />
<span style="font-weight: bold;" class="mycode_b">ElysiaJS</span>, sebuah framework yang di jalankan di atas bunjs runtime. Menggunakan banyak API dari bun, memanfaatkan kecepatan bun hingga bisa menghandle request hingga lebih dari 2jt request per second.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-8.png?resize=640%2C256&amp;ssl=1" loading="lazy"  width="640" height="256" alt="[Image: image-8.png?resize=640%2C256&amp;ssl=1]" class="mycode_img" /><br />
<br />
Bexlite menggunakan ElysiaJS karena kemudahan dan kecepatannya, tidak hanya dibandingkan dengan Express, atau javascript framework yang lain. Tetapi juga dengan framework dan bahasa yang lain.<br />
<br />
Terlebih bagi pengguna typescript, Elysia memiliki type-safety secara default. Dan ini akan memudahkan kamu untuk membangun aplikasi yang safe jika di-implementasikan dengan benar.<br />
<br />
Elysia juga memiliki beberapa fitur menarik yang bisa kita gunakan untuk membangun project dengan bexlite. Seperti CRON, Auto handling format including JSON dan FormData. Ditambah lagi dengan official plugin seperti HTML, JSX, JWT, dll, akan sangat memudahkan dalam menggunakan Bexlite.<br />
<br />
Kamu bisa baca lebih lanjut tentang elysia <a href="https://elysiajs.com/" target="_blank" rel="noopener" class="mycode_url">di sini</a>.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">HTMX</span></span><br />
<br />
So, pasti temen-temen sudah ga asing lagi dengan yang namanya HTMX, yang tiap hari MEMEnya melintas di timeline kita.<br />
<br />
Tapi, apa sih sebenernya HTMX ?<br />
Is it good ? bad ? Lalu apa bedanya HTMX dengan framework umum seperti React, Vue atau yang lain ?<br />
<br />
Okey, mari kita kenalan dengan HTMX.<br />
<br />
HTMX, adalah sebuah javascript frontend library yang memberikan alternative yang make sense bagi developer untuk develop web app dengan metode yang berbeda dari kebanyakan framework pada umumnya.<br />
<br />
Javascript SPA Framework, berkomunikasi dengan REST API. Yang mana client akan melakukan request kepada server, dan server merespon dengan JSON. yang kemudian client harus menjalankan logic untuk menerjemahkan JSON kedalam bentuk UI.<br />
<br />
HTMX, menempuh jalur yang berbeda dari kebanyakan frontend framework. HTMX menggunakan hypermedia sebagai format komunikasinya dibandingkan REST API yang berbentuk Text.<br />
<br />
Maksudnya adalah ketika klien melakukan request kepada server, server tidak lagi memberikan response dalam bentuk JSON, tetapi dalam bentuk HTML.<br />
<br />
Hypermedia sebagai response komunikasi server kepada client, bukanlah hal baru. Ini sebagaimana kita mengakses sebuah URL, kemudian server merespon dengan HTML yang sudah di render. Yang menjadi problem dari Hypermedia sebelumnya adalah response harus diberikan dalam bentuk keseluruhan laman.<br />
<br />
Karena memang keterbatasan dari html yang hanya bisa melakukan request hanya dengan anchor tag dan form yang kemudian harus di reload secara keseluruhan setelah mendapatkan respons.<br />
<br />
Dengan HTMX, melakukan http request dengan HTML tidak lagi terbatas pada anchor dan juga form. Dan juga tidak harus pada level full page, tapi pada level parsialnya.<br />
<br />
Salah satu motivasi munculnya HTMX adalah untuk mempersimple pembuatan web application. Yaitu dengan melakukan centralisasi logic pada server. Yang mana ini sangat make sense, karena server adalah tempat dimana permanent state berada.<br />
<br />
Ini juga yang dilakukan oleh banyak SPA framework akhir-akhir ini seperti react, nextjs yang mencoba untuk menempuh approach yang sama dengan mengenalkan React Server Component dan Server Action.<br />
<br />
But, pertanyaannya adalah aplikasi yang bagaimana yang mungkin cocok untuk kita gunakan HTMX di dalamnya.<br />
<br />
Sebagai jawaban dari pertanyaan ini, Saya akan berikan 2 kriteria.<br />
<ul class="mycode_list"><li>    Dimana developer mau meletakkan state aplikasinya ?<br />
</li>
<li>    Dan bagaimana developer memposisikan dirinya<br />
</li>
</ul>
<br />
Mari kita bahas kriteria ini.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Yang pertama, adalah dimana state diletakkan ?</span><br />
<br />
Spektrum web app ini cukup luas, tetapi kalo tarik secara horizontal. Hanya ada 2 jenis, yang fokus pada interaktivity dan fokus kepada server logic.<br />
<br />
Kita bisa melihat aplikasi game di web yang tentu statenya akan cepat dan seringkali berubah, dan tentu saja state aplikasi lebih baik diletakkan pada client untuk efisiensi komunikasi, yang kemudian dengan interval waktu tertentu transient state ini di kirimkan ke server.<br />
<br />
Ini sedikit berbeda dengan High Risk Application seperti Bank atau Finance App, yang state dan logicnya diletakkan di dalam server. Kenapa ? Yes, karena high risk application can’t trust the user.<br />
<br />
Maka sekarang kita bisa tahu, jika aplikasi kita sangat memerlukan interaktivity yang terus-terusan berubah, mungkin SPA framework seperti React lebih cocok. Adapun jika aplikasinya tidak memerlukan state yang terlalu sering berubah. HTMX akan jauh lebih simple untuk digunakan.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Yang kedua, adalah bagimana developer memposisikan dirinya.</span><br />
<br />
Jika kamu seorang developer entah frontend ataupun backend yang fokus dengan server-side logic, maka HTMX bisa jadi pilihan yang paling baik. Karena HTMX tidak membatasi developer pada bahasa pemrogramannya. Apapun bahasa yang kamu gunakan selama frontend menggunakan HTML, CSS dan Javascript, kamu bisa menggunakan HTMX.<br />
<br />
Namun jika kamu seorang developer yang fokus pada client-side logic, dan fokus pada bahasa javascript, mungkin react atau nextjs menjadi pilihan yang lebih baik.<br />
<br />
---<br />
<br />
Penggunaan HTMX di dalam Bexlite selaras dengan tujuan awal dibuatnya Tech Stack ini yaitu Simplicity. Dengan menggunakan HTMX library, kita bisa menggunakan HTML, bahasa yang diketahui oleh semua developer untuk membuat aplikasi dengan SPA Experience tanpa harus menggunakan bloated-features framework, tanpa harus belajar lagi framework-framework baru.<br />
<br />
Kita cukup tambahkan HTMX attribute di dalam HTML and done.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">JSX</span></span><br />
<br />
Seperti yang kita tahu, JSX adalah format umum yang digunakan di dalam frontend-framework. JSX secara khusus bukan templating Engine. Tetapi JSX kita gunakan di dalam Bexlite untuk memanfaatkan apa yang sudah kita pahami.<br />
<br />
JSX kita gunakan di dalam Bexlite sebagai templating model. Dan memudahkan kita dalam membuat UI components. Dengan menggunakan JSX, kita bisa dengan mudah mimic React dalam membuat reusable components.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">SQLite</span></span><br />
<br />
<span style="font-weight: bold;" class="mycode_b">Sqlite, the underdog database.</span><br />
<br />
Sedikit hiperbola, but yes. Sqlite sepertinya yang banyak diragukan di dalam tech stack ini. Sqlite seperti menjadi database yang tidak layak untuk production. Jika kita bicara tentang model big-scale apps dengan arsitektur yang rumit, maka iya. Mungkin sqlite tidak cocok digunakan. But untuk aplikasi small-mid sqlite lebih dari cukup untuk digunakan.<br />
<br />
Sqlite memiliki performa yang sangat cepat, embedded, dan dengan memanfaatkan teknologi embedded kamu tidak lagi perlu untuk mengalami “network io” dalam melakukan query kepada database. Silahkan baca post saya dibawah.<br />
<br />
<a href="https://x.com/indrazulfi/status/1790286534895415804" target="_blank" rel="noopener" class="mycode_url">https://x.com/indrazulfi/status/1790286534895415804</a><br />
<br />
Jika kamu merasa cocok dengan Bexlite secara umum, namun tidak cocok dengan menggunakan Sqlite, kamu bisa dengan mudah menggantikan SQLite dengan Database yang lain semisal PostgreSQL, atau Mongo. Saya tidak menyarankan kamu menggunakan ORM yang menggunakan query engine agar tidak memperparah latency seperti Prisma ORM untuk production.<br />
<br />
Jika kamu mau menggunakan ORM, kamu bisa menggunakan Drizzle ORM atau Query builder seperti Kisely. Dengan begitu ini akan mengurangi latency query disebabkan engine ORM seperti yang dimiliki Prisma.<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: xx-large;" class="mycode_size">TursoDB</span></span><br />
<br />
Turso DB adalah Provider Sqlite untuk production. Turso memberikan kemudahan untuk melakukan Scale dari aplikasi yang menggunakan Sqlite.<br />
<br />
Turso juga memiliki free-tier yang super generous dibandingkan dengan provider yang lain. Turso memberikan free-tier user untuk bisa membuat hinggal 500 Database, 9GB Storage, 3 Replication untuk edge location.<br />
<br />
Kamu akan dengan mudah melakukan scale bexlite dengan extending Sqlite yang digunakan dengan <a href="https://turso.tech/" target="_blank" rel="noopener" class="mycode_url">TursoDB</a>.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/elysia_v.webp" loading="lazy"  width="1918" height="1068" alt="[Image: elysia_v.webp]" class="mycode_img" /></blockquote>
]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Stop Piracy]]></title>
			<link>https://bb.nurfachmi.com/thread-13.html</link>
			<pubDate>Sat, 02 May 2026 13:15:48 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-13.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 8, 2025</blockquote>
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/stop-piracy.jpg" loading="lazy"  width="1600" height="1157" alt="[Image: stop-piracy.jpg]" class="mycode_img" /></blockquote>
<br />
Saya, Reza Nurfachmi, tidak mendukung aksi pembajakan atau perjual-belian kode sumber perangkat lunak (open source software) apapun dan tidak pula menjadi salah satu pelakunya.]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 8, 2025</blockquote>
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/stop-piracy.jpg" loading="lazy"  width="1600" height="1157" alt="[Image: stop-piracy.jpg]" class="mycode_img" /></blockquote>
<br />
Saya, Reza Nurfachmi, tidak mendukung aksi pembajakan atau perjual-belian kode sumber perangkat lunak (open source software) apapun dan tidak pula menjadi salah satu pelakunya.]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Getting Started with Jenkins]]></title>
			<link>https://bb.nurfachmi.com/thread-12.html</link>
			<pubDate>Sat, 02 May 2026 13:12:34 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-12.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 5, 2025</blockquote>
<br />
Jenkins, sebelumnya bernama Hudson, adalah salah satu Open Source Automation Server yang populer sampai saat ini. Jenkins sangat memiliki banyak plugins yang membantu proses building, deploying, serta automating banyak jenis projek.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/jenkins.jpg" loading="lazy"  width="866" height="650" alt="[Image: jenkins.jpg]" class="mycode_img" /></blockquote>
<br />
<br />
Jenkins dibangun menggunakan Java, pastikan kamu sudah menginstall SDK Java yang versi LTS. Untuk menginstall-nya, silahkan googling sendiri ya.<br />
Prerequisites<br />
<br />
Konfigurasi hardware yang direkomendasikan adalah:<br />
<br />
    4 GB+ of RAM<br />
    50 GB+ of drive space<br />
<br />
Adapun software yang harus ada untuk menjalankan Jenkins, antara lain:<br />
<br />
    Java: versi 11, 17, atau 21<br />
    Browser: Google Chrome, Mozilla Firefox, Microsoft Edge, atau Apple Safari<br />
    Git<br />
<br />
Berikut adalah spesifikasi komputer yang penulis pakai:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>git --version<br />
git version 2.34.1<br />
<br />
java --version<br />
openjdk 21.0.5 2024-10-15<br />
OpenJDK Runtime Environment (build 21.0.5+11-Ubuntu-1ubuntu122.04)<br />
OpenJDK 64-Bit Server VM (build 21.0.5+11-Ubuntu-1ubuntu122.04, mixed mode, sharing)</code></div></div><br />
Adapun Jenkins-nya penulis pakai versi 2.479.2 yang bisa diunduh di sini. Kalau versi lainnya, bisa diunduh di sini. Jika versi Java-mu berbeda, maka silahkan lihat halaman ini ya untuk menyesuaikan versi Jenkins-nya.<br />
<br />
Setelah mengunduh file jenkins.war, silahkan jalankan perintah ini di path terletaknya file tersebut.<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>java -jar jenkins.war --httpPort=9090 &amp;</code></div></div><br />
Port-nya penulis ubah menjadi 9090 supaya beda aja. Defaultnya ia menggunakan port 8080.<br />
<br />
Pastikan nanti muncul teks seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>Jenkins initial setup is required. An admin user has been created and a password generated.<br />
Please use the following password to proceed to installation:<br />
<br />
e0b2e5478******4ecd6a18a050<br />
<br />
This may also be found at: /home/reza/.jenkins/secrets/initialAdminPassword</code></div></div><br />
Kalau sudah muncul, maka buka browser dan arahkan ke alamat localhost:9090 atau sesuaikan saja jika kamu menginstall di cloud atau virtual machine.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-install.jpg?w=1007&amp;ssl=1" loading="lazy"  width="967" height="873" alt="[Image: jenkins-install.jpg?w=1007&amp;ssl=1]" class="mycode_img" /><br />
<br />
Isi dengan password yang diberikan, lalu klik tombol Continue.<br />
<br />
---<br />
<br />
Pada Costumize Jenkins, pilih Select plugins to install karena kita gak begitu butuh banyak plugin juga sih.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-plugins-selection.jpg?resize=640%2C343&amp;ssl=1" loading="lazy"  width="640" height="343" alt="[Image: jenkins-plugins-selection.jpg?resize=640%2C343&amp;ssl=1]" class="mycode_img" /><br />
<br />
Pilih none lalu klik tombol Install.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-plugins-options.jpg?resize=640%2C578&amp;ssl=1" loading="lazy"  width="640" height="578" alt="[Image: jenkins-plugins-options.jpg?resize=640%2C578&amp;ssl=1]" class="mycode_img" /><br />
<br />
Selanjutnya adalah buat kredensial Administrator untuk Jenkins kamu. Jangan lupa klik tombol Save and Continue.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-admin-user.jpg?resize=640%2C584&amp;ssl=1" loading="lazy"  width="640" height="584" alt="[Image: jenkins-admin-user.jpg?resize=640%2C584&amp;ssl=1]" class="mycode_img" /><br />
<br />
Terakhir pastikan instalasi Jenkins-nya. Lalu klik tombol Save and Finish.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-instance-config.jpg?resize=640%2C579&amp;ssl=1" loading="lazy"  width="640" height="579" alt="[Image: jenkins-instance-config.jpg?resize=640%2C579&amp;ssl=1]" class="mycode_img" /><br />
<br />
Terakhir, klik tombol Start using Jenkins.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-is-ready.jpg?resize=640%2C577&amp;ssl=1" loading="lazy"  width="640" height="577" alt="[Image: jenkins-is-ready.jpg?resize=640%2C577&amp;ssl=1]" class="mycode_img" /><br />
<br />
---<br />
<br />
Daaan inilah tampilan Dashboard awalnya.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-dashboard.png?resize=640%2C549&amp;ssl=1" loading="lazy"  width="640" height="549" alt="[Image: jenkins-dashboard.png?resize=640%2C549&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, apa saja yang ada di dashboard ini?<br />
<br />
Perhatikan sidebar paling bawah (Build Executor Status), di sana terdapat 2 worker yang nantinya akan menjalankan seluruh job yang kita tentukan untuk si Jenkins ini.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite>Karena satu dan lain hal, khususnya karena banyak issue teknis, pada praktik selanjutnya, tangkapan layar akan menggunakan Jenkins versi 2.479.2</blockquote>
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-dashboard-2.png?resize=640%2C549&amp;ssl=1" loading="lazy"  width="640" height="549" alt="[Image: jenkins-dashboard-2.png?resize=640%2C549&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, barulah kita akan membuat Job baru setelah ini.<br />
<br />
---<br />
<br />
Membuat Job pada Jenkins<br />
<br />
Klik pada menu Create a job atau New Item pada dashboard, selanjutnya kita harus mengisi nama jobnya.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-new-job.jpg?resize=640%2C278&amp;ssl=1" loading="lazy"  width="640" height="278" alt="[Image: jenkins-new-job.jpg?resize=640%2C278&amp;ssl=1]" class="mycode_img" /><br />
<br />
Setelah itu akan muncul halaman dengan banyak opsi yang bisa kita utak-atik. Kurang lebih tampilannya seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-config-new-job.png?resize=640%2C814&amp;ssl=1" loading="lazy"  width="640" height="814" alt="[Image: jenkins-config-new-job.png?resize=640%2C814&amp;ssl=1]" class="mycode_img" /><br />
<br />
Silahkan isi deskripsinya lalu klik tombol Save.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-new-job.png?resize=640%2C549&amp;ssl=1" loading="lazy"  width="640" height="549" alt="[Image: jenkins-new-job.png?resize=640%2C549&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, selesai tahap instalasi awal Job di Jenkins, selanjutnya kita akan mengintegrasikan projek kita yang ada di GitHub ke Jenkins ini.<br />
<br />
---<br />
<br />
Kalau kita kembali ke Dashboard lagi, maka halamannya sudah ada perubahan. Kini sudah ada Job yang telah kita buat tadi.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-dashboard-new-item.png?resize=640%2C368&amp;ssl=1" loading="lazy"  width="640" height="368" alt="[Image: jenkins-dashboard-new-item.png?resize=640%2C368&amp;ssl=1]" class="mycode_img" /><br />
<br />
Pada tabel tersebut, tertulis N/A pada kolom Last Success, Last Failure dan Last Duration. Hal tersebut menandakan bahwa job kita belum pernah dijalankan sama sekali. Maka untuk menjalankannya, tinggal klik saja tombol ikon play warna hijau itu dan tunggu beberapa saat.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-first-build.png?resize=640%2C333&amp;ssl=1" loading="lazy"  width="640" height="333" alt="[Image: jenkins-first-build.png?resize=640%2C333&amp;ssl=1]" class="mycode_img" /><br />
<br />
Silahkan kamu klik Jobnya tersebut dan perhatikan ada perubahan apa saja yang terjadi ya. Harus mandiri. Hahaha.<br />
<br />
Baik, kembali lagi ke urusan GitHub.<br />
<br />
Pada awalnya, Jenkins tidak tau bagaimana caranya mengambil dan mengelola projek kita yang ada di GitHub. Maka dari itu kita harus menginstall plugin Git terlebih dahulu.<br />
<br />
Kembali ke Dashboard, kemudian klik menu Manage Jenkins.<br />
<br />
Lalu klik menu Plugins.<br />
<br />
Klik menu Available plugins lalu ketikkan git sebagai keyword pencariannya.<br />
<br />
Centang pada plugin Git, lalu pilih tombol Install after restart.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-install-plugin-git.png?resize=640%2C333&amp;ssl=1" loading="lazy"  width="640" height="333" alt="[Image: jenkins-install-plugin-git.png?resize=640%2C333&amp;ssl=1]" class="mycode_img" /><br />
<br />
Lalu halaman akan berpindah dan scroll ke paling bawah, centang opsi Restart Jenkins when installation is complete and no jobs are running dan tunggu hingga selesai instalasinya.<br />
<br />
Pastikan kamu sudah setting SSH-nya ya. Kalau belum, bisa lihat video berikut.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><a href="https://www.youtube.com/watch?v=Fl91ObvW8tY" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=Fl91ObvW8tY</a></blockquote>
<br />
Oke, sampai sini penulis anggap kamu sudah selesai tahap SSH-nya. Karena selanjutnya ialah menghubungkan Jenkins dengan SSH.<br />
<br />
Kembali lagi ke Dashboard, lalu klik Manage Jenkins. Cari menu Credentials. Kemudian klik menu (global).<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-global-cred.jpg?resize=640%2C365&amp;ssl=1" loading="lazy"  width="640" height="365" alt="[Image: jenkins-global-cred.jpg?resize=640%2C365&amp;ssl=1]" class="mycode_img" /><br />
<br />
Lalu klik tombol Add Credentials.<br />
<br />
Berikut adalah pengaturan yang saya isi.<br />
<br />
Kind: SSH Username with private key.<br />
<br />
Scope: Global<br />
<br />
ID: github-aaezha<br />
<br />
Description: Credential GitHub AaEzha<br />
<br />
Username: AaEzha<br />
<br />
Private Key: Enter directly<br />
<br />
Jika berhasil, maka muncul seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-credential-success.png?resize=640%2C333&amp;ssl=1" loading="lazy"  width="640" height="333" alt="[Image: jenkins-credential-success.png?resize=640%2C333&amp;ssl=1]" class="mycode_img" /><br />
<br />
Sampai di sini, kita seharusnya berhasil menyambungkan Jenkins dengan GitHub. Mari kita buktikan!<br />
<br />
---<br />
<br />
Kembali lagi ke Dashboard, pilih Job yang telah dibuat, pada kasus saya namanya Belajar Jenkins, lalu pilih menu Configure.<br />
<br />
Pada opsi Source Code Management, pilih Git dan isi Repository URL projek kalian dan pastikan Credentials-nya adalah yang barusan dipilih serta tulis branch utama di opsi Branches to build.<br />
Agar meyakinkan, coba dengan repositori privat yang kamu punya.<br />
<br />
Misalnya seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image.png?resize=640%2C627&amp;ssl=1" loading="lazy"  width="640" height="627" alt="[Image: image.png?resize=640%2C627&amp;ssl=1]" class="mycode_img" /><br />
<br />
Lalu pada opsi Build Steps, klik dropdown Add build step, pilih Execute shell dan silahkan isi dengan perintah-perintah yang ingin dijalankan saat telah berhasil meng-clone repositori tersebut.<br />
<br />
Karena repositori contoh saya adalah projek Laravel, maka saya ingin coba menambahkan satu perintah dahulu, yakni composer install dan ingin lihat hasilnya.<br />
<br />
Lalu klik dulu tombol Save untuk memastikan bahwa kita telah berhasil dan tak ada error sampai sini.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-1.png?resize=640%2C403&amp;ssl=1" loading="lazy"  width="640" height="403" alt="[Image: image-1.png?resize=640%2C403&amp;ssl=1]" class="mycode_img" /><br />
<br />
Terakhir klik menu Build Now untuk testing konfigurasi di atas. Tunggu sebentar akan ada progress di pojok kiri bawah.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-2.png?resize=394%2C319&amp;ssl=1" loading="lazy"  width="394" height="319" alt="[Image: image-2.png?resize=394%2C319&amp;ssl=1]" class="mycode_img" /><br />
<br />
Silahkan klik pada angka #4 atau berapapun yang ada di layar kamu lalu klik menu Console Output untuk melihat proses yang terjadi.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-3.png?resize=640%2C359&amp;ssl=1" loading="lazy"  width="640" height="359" alt="[Image: image-3.png?resize=640%2C359&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nampak pada punya saya lancar jaya, terlihat di sana ada tulisan composer install dan selanjutnya berjalan sebagaimana seharusnya.<br />
<br />
Kalau kita klik kembali nama jobnya, lalu pilih menu Workspace, maka akan muncul direktori projek kita.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-4.png?resize=640%2C532&amp;ssl=1" loading="lazy"  width="640" height="532" alt="[Image: image-4.png?resize=640%2C532&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, sampai sini kita sudah berhasil melakukan cloning dan menjalankan build steps. Silahkan tambahkan sendiri script atau command lainnya sesuai kebutuhan ya.<br />
<br />
Etapipaaak, itu buildnya masih manual. Bagaimana caranya agar otomatis saat ada perubahan kode di repository, maka si build step ini berjalan sendiri tanpa bantuan kita? <br />
<br />
---<br />
<br />
Mungkin ini tahap terakhir, yaitu membuat build step-nya berjalan otomatis saat ada perubahan pada branch yang kita set pada konfigurasi sebelumnya. Let’s go!<br />
<br />
Kembali lagi ke halaman Job, kemudian pilih menu Configure.<br />
<br />
Pada opsi Build Triggers, pilih opsi Poll SCM yang artinya si Jenkins akan melakukan build jika ada perubahan kode pada branch terpilih dalam rentang waktu yang ditentukan. Adapun rentang waktu yang paling minimal ialah setiap satu menit.<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>* * * * *</code></div></div><br />
Kamu bisa isi dengan konfigurasi lainnya seperti mengatur cron. Lebih lengkapnya bisa <a href="https://crontab.guru/" target="_blank" rel="noopener" class="mycode_url">baca di sini</a>.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-5.png?resize=640%2C234&amp;ssl=1" loading="lazy"  width="640" height="234" alt="[Image: image-5.png?resize=640%2C234&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jangan lupa klik tombol Save jika sudah selesai<br />
<br />
Untuk membuktikannya, coba lakukan perubahan kode dan push ke repositori dan tunggu apakah Jenkins akan otomatis melakukan build? Jika iya, selamat kamu berhasil menamatkan Jenkins Level 1. Alhamdulillah.<br />
<br />
Jangan sungkan untuk bertanya via komen ya kalau ada pertanyaan atau koreksi. Syukron udah mau baca sampai sini.]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 5, 2025</blockquote>
<br />
Jenkins, sebelumnya bernama Hudson, adalah salah satu Open Source Automation Server yang populer sampai saat ini. Jenkins sangat memiliki banyak plugins yang membantu proses building, deploying, serta automating banyak jenis projek.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://nurfachmi.com/wp-content/uploads/2025/01/jenkins.jpg" loading="lazy"  width="866" height="650" alt="[Image: jenkins.jpg]" class="mycode_img" /></blockquote>
<br />
<br />
Jenkins dibangun menggunakan Java, pastikan kamu sudah menginstall SDK Java yang versi LTS. Untuk menginstall-nya, silahkan googling sendiri ya.<br />
Prerequisites<br />
<br />
Konfigurasi hardware yang direkomendasikan adalah:<br />
<br />
    4 GB+ of RAM<br />
    50 GB+ of drive space<br />
<br />
Adapun software yang harus ada untuk menjalankan Jenkins, antara lain:<br />
<br />
    Java: versi 11, 17, atau 21<br />
    Browser: Google Chrome, Mozilla Firefox, Microsoft Edge, atau Apple Safari<br />
    Git<br />
<br />
Berikut adalah spesifikasi komputer yang penulis pakai:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>git --version<br />
git version 2.34.1<br />
<br />
java --version<br />
openjdk 21.0.5 2024-10-15<br />
OpenJDK Runtime Environment (build 21.0.5+11-Ubuntu-1ubuntu122.04)<br />
OpenJDK 64-Bit Server VM (build 21.0.5+11-Ubuntu-1ubuntu122.04, mixed mode, sharing)</code></div></div><br />
Adapun Jenkins-nya penulis pakai versi 2.479.2 yang bisa diunduh di sini. Kalau versi lainnya, bisa diunduh di sini. Jika versi Java-mu berbeda, maka silahkan lihat halaman ini ya untuk menyesuaikan versi Jenkins-nya.<br />
<br />
Setelah mengunduh file jenkins.war, silahkan jalankan perintah ini di path terletaknya file tersebut.<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>java -jar jenkins.war --httpPort=9090 &amp;</code></div></div><br />
Port-nya penulis ubah menjadi 9090 supaya beda aja. Defaultnya ia menggunakan port 8080.<br />
<br />
Pastikan nanti muncul teks seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>Jenkins initial setup is required. An admin user has been created and a password generated.<br />
Please use the following password to proceed to installation:<br />
<br />
e0b2e5478******4ecd6a18a050<br />
<br />
This may also be found at: /home/reza/.jenkins/secrets/initialAdminPassword</code></div></div><br />
Kalau sudah muncul, maka buka browser dan arahkan ke alamat localhost:9090 atau sesuaikan saja jika kamu menginstall di cloud atau virtual machine.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-install.jpg?w=1007&amp;ssl=1" loading="lazy"  width="967" height="873" alt="[Image: jenkins-install.jpg?w=1007&amp;ssl=1]" class="mycode_img" /><br />
<br />
Isi dengan password yang diberikan, lalu klik tombol Continue.<br />
<br />
---<br />
<br />
Pada Costumize Jenkins, pilih Select plugins to install karena kita gak begitu butuh banyak plugin juga sih.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-plugins-selection.jpg?resize=640%2C343&amp;ssl=1" loading="lazy"  width="640" height="343" alt="[Image: jenkins-plugins-selection.jpg?resize=640%2C343&amp;ssl=1]" class="mycode_img" /><br />
<br />
Pilih none lalu klik tombol Install.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-plugins-options.jpg?resize=640%2C578&amp;ssl=1" loading="lazy"  width="640" height="578" alt="[Image: jenkins-plugins-options.jpg?resize=640%2C578&amp;ssl=1]" class="mycode_img" /><br />
<br />
Selanjutnya adalah buat kredensial Administrator untuk Jenkins kamu. Jangan lupa klik tombol Save and Continue.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-admin-user.jpg?resize=640%2C584&amp;ssl=1" loading="lazy"  width="640" height="584" alt="[Image: jenkins-admin-user.jpg?resize=640%2C584&amp;ssl=1]" class="mycode_img" /><br />
<br />
Terakhir pastikan instalasi Jenkins-nya. Lalu klik tombol Save and Finish.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-instance-config.jpg?resize=640%2C579&amp;ssl=1" loading="lazy"  width="640" height="579" alt="[Image: jenkins-instance-config.jpg?resize=640%2C579&amp;ssl=1]" class="mycode_img" /><br />
<br />
Terakhir, klik tombol Start using Jenkins.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-is-ready.jpg?resize=640%2C577&amp;ssl=1" loading="lazy"  width="640" height="577" alt="[Image: jenkins-is-ready.jpg?resize=640%2C577&amp;ssl=1]" class="mycode_img" /><br />
<br />
---<br />
<br />
Daaan inilah tampilan Dashboard awalnya.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-dashboard.png?resize=640%2C549&amp;ssl=1" loading="lazy"  width="640" height="549" alt="[Image: jenkins-dashboard.png?resize=640%2C549&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, apa saja yang ada di dashboard ini?<br />
<br />
Perhatikan sidebar paling bawah (Build Executor Status), di sana terdapat 2 worker yang nantinya akan menjalankan seluruh job yang kita tentukan untuk si Jenkins ini.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite>Karena satu dan lain hal, khususnya karena banyak issue teknis, pada praktik selanjutnya, tangkapan layar akan menggunakan Jenkins versi 2.479.2</blockquote>
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-dashboard-2.png?resize=640%2C549&amp;ssl=1" loading="lazy"  width="640" height="549" alt="[Image: jenkins-dashboard-2.png?resize=640%2C549&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, barulah kita akan membuat Job baru setelah ini.<br />
<br />
---<br />
<br />
Membuat Job pada Jenkins<br />
<br />
Klik pada menu Create a job atau New Item pada dashboard, selanjutnya kita harus mengisi nama jobnya.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-new-job.jpg?resize=640%2C278&amp;ssl=1" loading="lazy"  width="640" height="278" alt="[Image: jenkins-new-job.jpg?resize=640%2C278&amp;ssl=1]" class="mycode_img" /><br />
<br />
Setelah itu akan muncul halaman dengan banyak opsi yang bisa kita utak-atik. Kurang lebih tampilannya seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-config-new-job.png?resize=640%2C814&amp;ssl=1" loading="lazy"  width="640" height="814" alt="[Image: jenkins-config-new-job.png?resize=640%2C814&amp;ssl=1]" class="mycode_img" /><br />
<br />
Silahkan isi deskripsinya lalu klik tombol Save.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-new-job.png?resize=640%2C549&amp;ssl=1" loading="lazy"  width="640" height="549" alt="[Image: jenkins-new-job.png?resize=640%2C549&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, selesai tahap instalasi awal Job di Jenkins, selanjutnya kita akan mengintegrasikan projek kita yang ada di GitHub ke Jenkins ini.<br />
<br />
---<br />
<br />
Kalau kita kembali ke Dashboard lagi, maka halamannya sudah ada perubahan. Kini sudah ada Job yang telah kita buat tadi.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-dashboard-new-item.png?resize=640%2C368&amp;ssl=1" loading="lazy"  width="640" height="368" alt="[Image: jenkins-dashboard-new-item.png?resize=640%2C368&amp;ssl=1]" class="mycode_img" /><br />
<br />
Pada tabel tersebut, tertulis N/A pada kolom Last Success, Last Failure dan Last Duration. Hal tersebut menandakan bahwa job kita belum pernah dijalankan sama sekali. Maka untuk menjalankannya, tinggal klik saja tombol ikon play warna hijau itu dan tunggu beberapa saat.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-first-build.png?resize=640%2C333&amp;ssl=1" loading="lazy"  width="640" height="333" alt="[Image: jenkins-first-build.png?resize=640%2C333&amp;ssl=1]" class="mycode_img" /><br />
<br />
Silahkan kamu klik Jobnya tersebut dan perhatikan ada perubahan apa saja yang terjadi ya. Harus mandiri. Hahaha.<br />
<br />
Baik, kembali lagi ke urusan GitHub.<br />
<br />
Pada awalnya, Jenkins tidak tau bagaimana caranya mengambil dan mengelola projek kita yang ada di GitHub. Maka dari itu kita harus menginstall plugin Git terlebih dahulu.<br />
<br />
Kembali ke Dashboard, kemudian klik menu Manage Jenkins.<br />
<br />
Lalu klik menu Plugins.<br />
<br />
Klik menu Available plugins lalu ketikkan git sebagai keyword pencariannya.<br />
<br />
Centang pada plugin Git, lalu pilih tombol Install after restart.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-install-plugin-git.png?resize=640%2C333&amp;ssl=1" loading="lazy"  width="640" height="333" alt="[Image: jenkins-install-plugin-git.png?resize=640%2C333&amp;ssl=1]" class="mycode_img" /><br />
<br />
Lalu halaman akan berpindah dan scroll ke paling bawah, centang opsi Restart Jenkins when installation is complete and no jobs are running dan tunggu hingga selesai instalasinya.<br />
<br />
Pastikan kamu sudah setting SSH-nya ya. Kalau belum, bisa lihat video berikut.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><a href="https://www.youtube.com/watch?v=Fl91ObvW8tY" target="_blank" rel="noopener" class="mycode_url">https://www.youtube.com/watch?v=Fl91ObvW8tY</a></blockquote>
<br />
Oke, sampai sini penulis anggap kamu sudah selesai tahap SSH-nya. Karena selanjutnya ialah menghubungkan Jenkins dengan SSH.<br />
<br />
Kembali lagi ke Dashboard, lalu klik Manage Jenkins. Cari menu Credentials. Kemudian klik menu (global).<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-global-cred.jpg?resize=640%2C365&amp;ssl=1" loading="lazy"  width="640" height="365" alt="[Image: jenkins-global-cred.jpg?resize=640%2C365&amp;ssl=1]" class="mycode_img" /><br />
<br />
Lalu klik tombol Add Credentials.<br />
<br />
Berikut adalah pengaturan yang saya isi.<br />
<br />
Kind: SSH Username with private key.<br />
<br />
Scope: Global<br />
<br />
ID: github-aaezha<br />
<br />
Description: Credential GitHub AaEzha<br />
<br />
Username: AaEzha<br />
<br />
Private Key: Enter directly<br />
<br />
Jika berhasil, maka muncul seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/jenkins-credential-success.png?resize=640%2C333&amp;ssl=1" loading="lazy"  width="640" height="333" alt="[Image: jenkins-credential-success.png?resize=640%2C333&amp;ssl=1]" class="mycode_img" /><br />
<br />
Sampai di sini, kita seharusnya berhasil menyambungkan Jenkins dengan GitHub. Mari kita buktikan!<br />
<br />
---<br />
<br />
Kembali lagi ke Dashboard, pilih Job yang telah dibuat, pada kasus saya namanya Belajar Jenkins, lalu pilih menu Configure.<br />
<br />
Pada opsi Source Code Management, pilih Git dan isi Repository URL projek kalian dan pastikan Credentials-nya adalah yang barusan dipilih serta tulis branch utama di opsi Branches to build.<br />
Agar meyakinkan, coba dengan repositori privat yang kamu punya.<br />
<br />
Misalnya seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image.png?resize=640%2C627&amp;ssl=1" loading="lazy"  width="640" height="627" alt="[Image: image.png?resize=640%2C627&amp;ssl=1]" class="mycode_img" /><br />
<br />
Lalu pada opsi Build Steps, klik dropdown Add build step, pilih Execute shell dan silahkan isi dengan perintah-perintah yang ingin dijalankan saat telah berhasil meng-clone repositori tersebut.<br />
<br />
Karena repositori contoh saya adalah projek Laravel, maka saya ingin coba menambahkan satu perintah dahulu, yakni composer install dan ingin lihat hasilnya.<br />
<br />
Lalu klik dulu tombol Save untuk memastikan bahwa kita telah berhasil dan tak ada error sampai sini.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-1.png?resize=640%2C403&amp;ssl=1" loading="lazy"  width="640" height="403" alt="[Image: image-1.png?resize=640%2C403&amp;ssl=1]" class="mycode_img" /><br />
<br />
Terakhir klik menu Build Now untuk testing konfigurasi di atas. Tunggu sebentar akan ada progress di pojok kiri bawah.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-2.png?resize=394%2C319&amp;ssl=1" loading="lazy"  width="394" height="319" alt="[Image: image-2.png?resize=394%2C319&amp;ssl=1]" class="mycode_img" /><br />
<br />
Silahkan klik pada angka #4 atau berapapun yang ada di layar kamu lalu klik menu Console Output untuk melihat proses yang terjadi.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-3.png?resize=640%2C359&amp;ssl=1" loading="lazy"  width="640" height="359" alt="[Image: image-3.png?resize=640%2C359&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nampak pada punya saya lancar jaya, terlihat di sana ada tulisan composer install dan selanjutnya berjalan sebagaimana seharusnya.<br />
<br />
Kalau kita klik kembali nama jobnya, lalu pilih menu Workspace, maka akan muncul direktori projek kita.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-4.png?resize=640%2C532&amp;ssl=1" loading="lazy"  width="640" height="532" alt="[Image: image-4.png?resize=640%2C532&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, sampai sini kita sudah berhasil melakukan cloning dan menjalankan build steps. Silahkan tambahkan sendiri script atau command lainnya sesuai kebutuhan ya.<br />
<br />
Etapipaaak, itu buildnya masih manual. Bagaimana caranya agar otomatis saat ada perubahan kode di repository, maka si build step ini berjalan sendiri tanpa bantuan kita? <br />
<br />
---<br />
<br />
Mungkin ini tahap terakhir, yaitu membuat build step-nya berjalan otomatis saat ada perubahan pada branch yang kita set pada konfigurasi sebelumnya. Let’s go!<br />
<br />
Kembali lagi ke halaman Job, kemudian pilih menu Configure.<br />
<br />
Pada opsi Build Triggers, pilih opsi Poll SCM yang artinya si Jenkins akan melakukan build jika ada perubahan kode pada branch terpilih dalam rentang waktu yang ditentukan. Adapun rentang waktu yang paling minimal ialah setiap satu menit.<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>* * * * *</code></div></div><br />
Kamu bisa isi dengan konfigurasi lainnya seperti mengatur cron. Lebih lengkapnya bisa <a href="https://crontab.guru/" target="_blank" rel="noopener" class="mycode_url">baca di sini</a>.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/image-5.png?resize=640%2C234&amp;ssl=1" loading="lazy"  width="640" height="234" alt="[Image: image-5.png?resize=640%2C234&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jangan lupa klik tombol Save jika sudah selesai<br />
<br />
Untuk membuktikannya, coba lakukan perubahan kode dan push ke repositori dan tunggu apakah Jenkins akan otomatis melakukan build? Jika iya, selamat kamu berhasil menamatkan Jenkins Level 1. Alhamdulillah.<br />
<br />
Jangan sungkan untuk bertanya via komen ya kalau ada pertanyaan atau koreksi. Syukron udah mau baca sampai sini.]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Getting Started with Cloudflare R2]]></title>
			<link>https://bb.nurfachmi.com/thread-11.html</link>
			<pubDate>Sat, 02 May 2026 13:01:10 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-11.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 4, 2025</blockquote>
<br />
<span style="font-weight: bold;" class="mycode_b">Cloudflare R2 Storage</span> adalah layanan penyimpanan objek (object storage) yang dirancang sebagai alternatif dari solusi penyimpanan cloud tradisional seperti Amazon S3. R2 menawarkan cara untuk menyimpan data tidak terstruktur dalam jumlah besar, seperti file, gambar, video, atau dokumen, dengan fokus pada efisiensi biaya dan kinerja.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/cloudflare.png?resize=381%2C376&amp;ssl=1" loading="lazy"  width="381" height="376" alt="[Image: cloudflare.png?resize=381%2C376&amp;ssl=1]" class="mycode_img" /></blockquote>
<br />
Keunggulan Utama Cloudflare R2<br />
<ul class="mycode_list"><li>Tanpa Biaya Egress<br />
</li>
</ul>
Salah satu fitur paling menarik dari R2 adalah penghapusan biaya egress (bandwidth keluar), yang biasanya menjadi komponen mahal dalam layanan penyimpanan cloud lainnya.<ul class="mycode_list"><li>Kompatibilitas dengan S3 API<br />
</li>
</ul>
R2 kompatibel dengan API Amazon S3, sehingga memudahkan pengembang untuk memigrasikan aplikasi atau integrasi yang sudah ada ke R2 tanpa banyak perubahan kode.<ul class="mycode_list"><li>Skalabilitas Tinggi<br />
</li>
</ul>
R2 dirancang untuk menyimpan data dalam jumlah besar dengan ketersediaan dan skalabilitas tinggi.<ul class="mycode_list"><li>Kinerja Optimal di Edge<br />
</li>
</ul>
Dengan jaringan edge Cloudflare yang luas, R2 memungkinkan pengiriman data yang cepat ke seluruh dunia, sehingga cocok untuk aplikasi yang memerlukan distribusi konten global.<ul class="mycode_list"><li>Harga Kompetitif<br />
</li>
</ul>
Biaya penyimpanan dan operasional R2 sangat kompetitif dibandingkan dengan layanan serupa, menjadikannya solusi ekonomis untuk berbagai kasus penggunaan.<br />
<br />
Bagaimana Cloudflare R2 Bekerja?<br />
<br />
R2 menyimpan data dalam bentuk objek, mirip dengan layanan object storage lainnya. Setiap objek diidentifikasi dengan kunci unik, dan metadata dapat ditambahkan untuk mempermudah pengelolaan data. Dengan integrasi yang mendalam ke dalam jaringan Cloudflare, data yang disimpan di R2 dapat diakses dengan cepat melalui jaringan edge Cloudflare.<br />
<br />
Jika kamu tertarik untuk mencoba Cloudflare R2, penulis akan menjelaskan langkah-langkah untuk mengintegrasikan R2 ke aplikasimu. ?<br />
<br />
---<br />
<br />
Berikut adalah langkah-langkah untuk mengintegrasikan Cloudflare R2 Storage ke aplikasi kamu, khususnya jika sudah familiar dengan Amazon S3 atau ingin memanfaatkan kompatibilitas S3 API:<br />
<br />
<span style="font-size: x-large;" class="mycode_size"><span style="font-weight: bold;" class="mycode_b">Langkah 1: Siapkan Bucket di Cloudflare R2</span></span><br />
<br />
Pertama, login ke akun Cloudflare kamu di Cloudflare Dashboard. Kalau belum punya akun, maka register dahulu.<br />
<br />
Kedua, akses menu R2 Object Storage dari sidebar. Jika ini adalah pertama kali, seharusnya muncul halaman register R2 seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/register-r2.png?resize=640%2C465&amp;ssl=1" loading="lazy"  width="640" height="465" alt="[Image: register-r2.png?resize=640%2C465&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jika seperti di atas, maka isi dulu formulir yang dibutuhkan. Tenang saja, kamu hanya akan ditagih jika melebihi batas pemakaian gratisannya kok.<br />
<br />
Lalu bagaimana soal tarif Cloudflare R2 ini? Apa maksudnya Storage, Class A operations dan Class B operations?<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/free-tier-r2.jpg?resize=640%2C401&amp;ssl=1" loading="lazy"  width="640" height="401" alt="[Image: free-tier-r2.jpg?resize=640%2C401&amp;ssl=1]" class="mycode_img" /><br />
<br />
Pada versi gratis, storage yang diberikan ialah sampai 10 GB per bulan. Jika lebih, maka akan kena biaya sebesar &#36;0.015 per GB dari kuota berlebihnya. Jika ukuran storage kamu 15 GB, maka akan kena biaya sekitar &#36;0.015 x 5 GB, yakni &#36;0.075 atau setara dengan IDR 1.125 jika kurs di angka IDR 15.000.<br />
<br />
Class A Operations, pada dasarnya adalah operasi yang cenderung mengubah status data, seperti menulis/upload atau memodifikasi objek, seperti PutObject (mengupload objek), CopyObject (menyalin objek), dan CompleteMultipartUpload (menyelesaikan upload multipart).<br />
<br />
Adapun Class B Operations adalah operasi yang biasanya membaca status data yang ada tanpa mengubahnya. Contohnya ialah GetObject (mengambil objek) dan HeadObject (memeriksa metadata objek).<br />
<br />
Baik, kembali lagi ke proses registrasi. Jika sudah berhasil memasukkan kredensial kartu kredit atau debit, maka akan muncul halaman seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-dashboard.png?resize=640%2C299&amp;ssl=1" loading="lazy"  width="640" height="299" alt="[Image: r2-dashboard.png?resize=640%2C299&amp;ssl=1]" class="mycode_img" /><br />
<br />
Selanjutnya adalah membuat Bucket. Apa itu Bucket? Bucket adalah keranjang yang isinya adalah objek-objek yang akan kita upload nanti.<br />
<br />
Silahkan isi nama bucket-mu.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/create-bucket.jpg?resize=640%2C574&amp;ssl=1" loading="lazy"  width="640" height="574" alt="[Image: create-bucket.jpg?resize=640%2C574&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jika berhasil, maka halamannya akan beralih seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/bucket-success.jpg?resize=640%2C345&amp;ssl=1" loading="lazy"  width="640" height="345" alt="[Image: bucket-success.jpg?resize=640%2C345&amp;ssl=1]" class="mycode_img" /><br />
<br />
Cobalah upload satu file dulu. Jika berhasil, maka tampilannya sebagai berikut:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-upload-success.jpg?resize=640%2C296&amp;ssl=1" loading="lazy"  width="640" height="296" alt="[Image: r2-upload-success.jpg?resize=640%2C296&amp;ssl=1]" class="mycode_img" /><br />
<br />
Saat ini, R2 kita hanya berlaku seperti flashdisk saja. Hanya bisa menyimpan data, tetapi belum bisa mengakses datanya secara online. Perhatikan pada bagian Public URL Access, di sana tertera Not allowed. Agar objek-objek yang kita upload bisa diakses, maka bagian tersebut harus berubah menjadi Allowed terlebih dahulu.<br />
<br />
Caranya adalah klik menu Settings, lalu cari bagian Public Access sebagai berikut, kemudian klik tombol Allow Access.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-go-public.jpg?resize=640%2C115&amp;ssl=1" loading="lazy"  width="640" height="115" alt="[Image: r2-go-public.jpg?resize=640%2C115&amp;ssl=1]" class="mycode_img" /><br />
<br />
Lalu ikuti arahannya sampai berubah menjadi seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-public-domain.jpg?resize=640%2C138&amp;ssl=1" loading="lazy"  width="640" height="138" alt="[Image: r2-public-domain.jpg?resize=640%2C138&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jika berhasil, maka saat masuk ke dalam objeknya, maka akan muncul URL publiknya sebagai berikut:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-public-url.jpg?resize=640%2C376&amp;ssl=1" loading="lazy"  width="640" height="376" alt="[Image: r2-public-url.jpg?resize=640%2C376&amp;ssl=1]" class="mycode_img" /><br />
<br />
Sampai sini, maka saatnya lanjut ke langkah berikutnya.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: x-large;" class="mycode_size">Langkah 2: Instalasi SDK atau Library</span></span><br />
<br />
Gunakan library yang mendukung Amazon S3 untuk mengintegrasikan aplikasi kita dengan R2. Contoh library populer:<br />
<br />
    PHP: AWS SDK for PHP<br />
    Node.js: AWS SDK for JavaScript<br />
    Python: Boto3<br />
    Go: Minio Go SDK<br />
<br />
Etapipaak, sebelum itu kita harus punya token API untuk dapat melakukan operasi menggunakan library di atas. Bagaimana caranya? Begini.<br />
<br />
Arahkan kembali ke halaman Overview R2 Object Storage, kemudian arahkan seperti gambar di bawah. Pilih Manage API tokens.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-menu-create-token.jpg?resize=640%2C244&amp;ssl=1" loading="lazy"  width="640" height="244" alt="[Image: r2-menu-create-token.jpg?resize=640%2C244&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jika masih kosong, maka tampilannya sebagai berikut:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-token-empty-1024x228.jpg?resize=640%2C143&amp;ssl=1" loading="lazy"  width="640" height="143" alt="[Image: r2-token-empty-1024x228.jpg?resize=640%2C143&amp;ssl=1]" class="mycode_img" /><br />
<br />
Maka klik tombol <span style="font-weight: bold;" class="mycode_b">Create API token</span> untuk membuat satu. Berikut pengaturan penulis saat membuat token.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Token name</span>: <span style="text-decoration: underline;" class="mycode_u">token-r2-read-write</span><br />
<br />
<span style="font-weight: bold;" class="mycode_b">Permissions</span>: <span style="text-decoration: underline;" class="mycode_u">Object Read &amp; Write</span>: Allows the ability to read, write, and list objects in specific buckets.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Specify bucket(s)</span>: <span style="text-decoration: underline;" class="mycode_u">Apply to all buckets</span> in this account (including newly created buckets)<br />
<br />
<span style="font-weight: bold;" class="mycode_b">TTL</span>: <span style="text-decoration: underline;" class="mycode_u">Forever</span><br />
<br />
Jika telah berhasil, maka silahkan simpan kredensial yang diberikan, antara lain:<br />
<ul class="mycode_list"><li>    Token value<br />
</li>
<li>    Access Key ID<br />
</li>
<li>    Secret Access Key<br />
</li>
<li>    Default endpoint<br />
</li>
<li>    EU endpoint<br />
</li>
</ul>
<br />
Maka halamannya akan berubah menjadi seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-token-exists-1024x206.jpg?resize=640%2C129&amp;ssl=1" loading="lazy"  width="640" height="129" alt="[Image: r2-token-exists-1024x206.jpg?resize=640%2C129&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, selanjutnya kita akan mulai sedikit ngoding. Pada kali ini, saya contohkan pakai Laravel PHP ya.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: x-large;" class="mycode_size">Langkah 3: Contoh Kode Implementasi</span></span><br />
<br />
Silahkan install Laravel fresh atau gunakan projek kamu yang ingin mengemplementasikan R2 ini.<br />
<br />
Selanjutnya install package S3<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">composer&nbsp;</span><span style="color: #007700">require&nbsp;</span><span style="color: #0000BB">league</span><span style="color: #007700">/</span><span style="color: #0000BB">flysystem</span><span style="color: #007700">-</span><span style="color: #0000BB">aws</span><span style="color: #007700">-</span><span style="color: #0000BB">s3</span><span style="color: #007700">-</span><span style="color: #0000BB">v3&nbsp;</span><span style="color: #DD0000">"^3.0"&nbsp;</span><span style="color: #007700">--</span><span style="color: #0000BB">with</span><span style="color: #007700">-</span><span style="color: #0000BB">all</span><span style="color: #007700">-</span><span style="color: #0000BB">dependencies&nbsp;<br /></span></code></div></div></div><br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>./composer.json has been updated<br />
Running composer update league/flysystem-aws-s3-v3 --with-all-dependencies<br />
Loading composer repositories with package information<br />
Updating dependencies<br />
Lock file operations: 4 installs, 3 updates, 0 removals<br />
  - Locking aws/aws-crt-php (v1.2.7)<br />
  - Locking aws/aws-sdk-php (3.336.7)<br />
  - Upgrading guzzlehttp/promises (2.0.3 =&gt; 2.0.4)<br />
  - Upgrading league/flysystem (3.29.0 =&gt; 3.29.1)<br />
  - Locking league/flysystem-aws-s3-v3 (3.29.0)<br />
  - Locking mtdowling/jmespath.php (2.8.0)<br />
  - Upgrading symfony/deprecation-contracts (v3.5.0 =&gt; v3.5.1)<br />
Writing lock file<br />
Installing dependencies from lock file (including require-dev)<br />
Package operations: 4 installs, 3 updates, 0 removals<br />
  - Downloading aws/aws-crt-php (v1.2.7)<br />
  - Downloading mtdowling/jmespath.php (2.8.0)<br />
  - Downloading aws/aws-sdk-php (3.336.7)<br />
  - Downloading league/flysystem-aws-s3-v3 (3.29.0)<br />
  - Installing aws/aws-crt-php (v1.2.7): Extracting archive<br />
  - Upgrading symfony/deprecation-contracts (v3.5.0 =&gt; v3.5.1): Extracting archive<br />
  - Upgrading guzzlehttp/promises (2.0.3 =&gt; 2.0.4): Extracting archive<br />
  - Upgrading league/flysystem (3.29.0 =&gt; 3.29.1): Extracting archive<br />
  - Installing mtdowling/jmespath.php (2.8.0): Extracting archive<br />
  - Installing aws/aws-sdk-php (3.336.7): Extracting archive<br />
  - Installing league/flysystem-aws-s3-v3 (3.29.0): Extracting archive<br />
3 package suggestions were added by new dependencies, use `composer suggest` to see details.<br />
Generating optimized autoload files<br />
&gt; Illuminate&#92;Foundation&#92;ComposerScripts::postAutoloadDump<br />
&gt; @php artisan package:discover --ansi<br />
<br />
   INFO  Discovering packages.  <br />
<br />
  laravel/sail .............................................................................. DONE<br />
  laravel/tinker ............................................................................ DONE<br />
  nesbot/carbon ............................................................................. DONE<br />
  nunomaduro/collision ...................................................................... DONE<br />
  nunomaduro/termwind ....................................................................... DONE<br />
<br />
78 packages you are using are looking for funding.<br />
Use the `composer fund` command to find out more!<br />
&gt; @php artisan vendor:publish --tag=laravel-assets --ansi --force<br />
<br />
   INFO  No publishable resources for tag [laravel-assets].  <br />
<br />
Found 4 security vulnerability advisories affecting 4 packages.<br />
Run "composer audit" for a full list of advisories.</code></div></div><br />
Oke, selanjutnya adalah tambahkan baris berikut ke file <span style="font-weight: bold;" class="mycode_b">.env</span> kita.<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>R2_ACCESS_KEY_ID=YOUR_ACCESS_KEY<br />
R2_SECRET_ACCESS_KEY=YOUR_SECRET_KEY<br />
R2_BUCKET=YOUR_BUCKET_NAME<br />
R2_ENDPOINT=XXXXXXX.r2.cloudflarestorage.com</code></div></div><br />
Lalu cari key <span style="font-weight: bold;" class="mycode_b">FILESYSTEM_DISK</span> dan ubah nilainya menjadi r2 seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>FILESYSTEM_DISK=r2</code></div></div><br />
Kira-kira lengkapnya menjadi seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>FILESYSTEM_DISK=r2<br />
<br />
// ...<br />
<br />
R2_ACCESS_KEY_ID=17c995******b72dec******87976<br />
R2_SECRET_ACCESS_KEY=fa55efa680d******5ecd898f06ae37761807f******b3bae36643f<br />
R2_BUCKET=nurfachmi-academy<br />
R2_ENDPOINT=https://9deccd0505******7560976cb3ff6.r2.cloudflarestorage.com</code></div></div><br />
Beberapa value di atas sudah disensor dengan karakter *.<br />
<br />
Selanjutnya tambahkan pengaturan disk di filesystem yang ada di <span style="font-weight: bold;" class="mycode_b">config/filesystem.php</span>.<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #007700">return&nbsp;[<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #FF8000">//&nbsp;...<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">'disks'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;[<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #FF8000">//&nbsp;...<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;  &nbsp;</span><span style="color: #DD0000">'r2'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;[<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'driver'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'s3'</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'key'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_ACCESS_KEY_ID'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'secret'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_SECRET_ACCESS_KEY'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'region'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'auto'</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'bucket'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_BUCKET'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'url'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_URL'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'endpoint'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_ENDPOINT'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'use_path_style_endpoint'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_USE_PATH_STYLE_ENDPOINT'</span><span style="color: #007700">,&nbsp;</span><span style="color: #0000BB">false</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'throw'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">false</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">],<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">],<br />];&nbsp;<br /></span></code></div></div></div><br />
Sip, sekarang kita beralih ke MVC-nya. Model, View, dan Controller. Let’s go!<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: x-large;" class="mycode_size">Langkah 4: Model, View, dan Controller</span></span><br />
<br />
Kita buat ketiganya dalam satu perintah.<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;make</span><span style="color: #007700">:</span><span style="color: #0000BB">model&nbsp;Storage&nbsp;</span><span style="color: #007700">-</span><span style="color: #0000BB">mcr&nbsp;<br /></span></code></div></div></div><br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>INFO  Model [app/Models/Storage.php] created successfully.  <br />
<br />
   INFO  Migration [database/migrations/2025_01_04_005141_create_storages_table.php] created successfully.  <br />
<br />
   INFO  Controller [app/Http/Controllers/StorageController.php] created successfully.</code></div></div><br />
Dengan perintah di atas, kita membuat model Storage sekaligus migration dan resource controller.<br />
<br />
---<br />
<br />
Untuk migration, kita buat sederhana dulu saja seperti ini:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #FF8000">//&nbsp;...<br /><br /></span><span style="color: #007700">return&nbsp;new&nbsp;class&nbsp;extends&nbsp;</span><span style="color: #0000BB">Migration<br /></span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">public&nbsp;function&nbsp;</span><span style="color: #0000BB">up</span><span style="color: #007700">():&nbsp;</span><span style="color: #0000BB">void<br /> &nbsp; &nbsp;</span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;Schema</span><span style="color: #007700">::</span><span style="color: #0000BB">create</span><span style="color: #007700">(</span><span style="color: #DD0000">'storages'</span><span style="color: #007700">,&nbsp;function&nbsp;(</span><span style="color: #0000BB">Blueprint&nbsp;&#36;table</span><span style="color: #007700">)&nbsp;{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;table</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">id</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;table</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">string</span><span style="color: #007700">(</span><span style="color: #DD0000">'path'</span><span style="color: #007700">);<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;table</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">timestamps</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">});<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">}<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #FF8000">//&nbsp;...<br /></span><span style="color: #007700">}&nbsp;<br /></span></code></div></div></div><br />
Jalankan migratenya<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;migrate&nbsp;<br /></span></code></div></div></div><br />
File migration di atas setara dengan SQL command berikut:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">create&nbsp;table&nbsp;</span><span style="color: #DD0000">"storages"&nbsp;</span><span style="color: #007700">(<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">"id"&nbsp;</span><span style="color: #0000BB">integer&nbsp;primary&nbsp;key&nbsp;autoincrement&nbsp;not&nbsp;null</span><span style="color: #007700">,&nbsp;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">"path"&nbsp;</span><span style="color: #0000BB">varchar&nbsp;not&nbsp;null</span><span style="color: #007700">,&nbsp;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">"created_at"&nbsp;</span><span style="color: #0000BB">datetime</span><span style="color: #007700">,&nbsp;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">"updated_at"&nbsp;</span><span style="color: #0000BB">datetime<br /></span><span style="color: #007700">);&nbsp;<br /></span></code></div></div></div><br />
---<br />
<br />
Selanjutnya kita modifikasi file controllernya seperti ini:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #007700">namespace&nbsp;</span><span style="color: #0000BB">App&#092;Http&#092;Controllers</span><span style="color: #007700">;<br /><br />use&nbsp;</span><span style="color: #0000BB">Illuminate&#092;Http&#092;Request</span><span style="color: #007700">;<br /><br />class&nbsp;</span><span style="color: #0000BB">StorageController&nbsp;</span><span style="color: #007700">extends&nbsp;</span><span style="color: #0000BB">Controller<br /></span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">public&nbsp;function&nbsp;</span><span style="color: #0000BB">index</span><span style="color: #007700">()<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">return&nbsp;</span><span style="color: #0000BB">view</span><span style="color: #007700">(</span><span style="color: #DD0000">'upload'</span><span style="color: #007700">);<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">}<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">public&nbsp;function&nbsp;</span><span style="color: #0000BB">store</span><span style="color: #007700">(</span><span style="color: #0000BB">Request&nbsp;&#36;request</span><span style="color: #007700">)<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">try&nbsp;{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;path&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #0000BB">&#36;request</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">file</span><span style="color: #007700">(</span><span style="color: #DD0000">'file'</span><span style="color: #007700">)-&gt;</span><span style="color: #0000BB">store</span><span style="color: #007700">(</span><span style="color: #DD0000">'storage'</span><span style="color: #007700">);<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;storage&nbsp;</span><span style="color: #007700">=&nbsp;new&nbsp;</span><span style="color: #0000BB">&#092;App&#092;Models&#092;Storage</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;storage</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">path&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #0000BB">&#36;path</span><span style="color: #007700">;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;storage</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">save</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">}&nbsp;catch&nbsp;(</span><span style="color: #0000BB">&#092;Throwable&nbsp;&#36;th</span><span style="color: #007700">)&nbsp;{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;dd</span><span style="color: #007700">(</span><span style="color: #0000BB">&#36;th</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">getMessage</span><span style="color: #007700">());<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">}<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">return&nbsp;</span><span style="color: #0000BB">back</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">}<br />}&nbsp;<br /></span></code></div></div></div><br />
Pada method index, kita sesederhana menampilkan view yang nanti berada di resources/views/upload.blade.php dan isinya berupa form upload saja dengan 2 elemen, yakni element input file dan tombol.<br />
<br />
Adapun pada method store, hanya berupa usaha untuk upload file ke Cloudflare R2 dan menyimpannya ke dalam model Storage. Jika gagal, maka akan menampilkan errornya dalam fungsi dd. Jika berhasil, maka kembali ke halaman upload lagi.<br />
<br />
Kita hanya menggunakan dua method itu saja dan silahkan hapus method lainnya karena tidak diperlukan.<br />
<br />
--<br />
<br />
Terakhir, buat file baru dengan nama upload.blade.php dalam folder resources/views dan isinya sesederhana berikut:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">&lt;!</span><span style="color: #0000BB">DOCTYPE&nbsp;html</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">html&nbsp;lang</span><span style="color: #007700">=</span><span style="color: #DD0000">"en"</span><span style="color: #007700">&gt;<br /><br />&lt;</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;charset</span><span style="color: #007700">=</span><span style="color: #DD0000">"UTF-8"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;name</span><span style="color: #007700">=</span><span style="color: #DD0000">"viewport"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"width=device-width,&nbsp;initial-scale=1.0"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;http</span><span style="color: #007700">-</span><span style="color: #0000BB">equiv</span><span style="color: #007700">=</span><span style="color: #DD0000">"X-UA-Compatible"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"ie=edge"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Upload&nbsp;to&nbsp;Cloudflare&nbsp;R2</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">link&nbsp;rel</span><span style="color: #007700">=</span><span style="color: #DD0000">"stylesheet"&nbsp;</span><span style="color: #0000BB">href</span><span style="color: #007700">=</span><span style="color: #DD0000">"https://cdn.jsdelivr.net/npm/@picocss/pico@2/css/pico.min.css"</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br /><br />&lt;</span><span style="color: #0000BB">body&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"container"</span><span style="color: #007700">&gt;<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">form&nbsp;action</span><span style="color: #007700">=</span><span style="color: #DD0000">"{{&nbsp;route('storage.store')&nbsp;}}"&nbsp;</span><span style="color: #0000BB">method</span><span style="color: #007700">=</span><span style="color: #DD0000">"post"&nbsp;</span><span style="color: #0000BB">enctype</span><span style="color: #007700">=</span><span style="color: #DD0000">"multipart/form-data"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">@</span><span style="color: #0000BB">csrf<br /><br /> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">input&nbsp;type</span><span style="color: #007700">=</span><span style="color: #DD0000">"file"&nbsp;</span><span style="color: #0000BB">name</span><span style="color: #007700">=</span><span style="color: #DD0000">"file"&nbsp;</span><span style="color: #0000BB">id</span><span style="color: #007700">=</span><span style="color: #DD0000">"file"&nbsp;</span><span style="color: #0000BB">required</span><span style="color: #007700">&gt;<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">input&nbsp;type</span><span style="color: #007700">=</span><span style="color: #DD0000">"submit"&nbsp;</span><span style="color: #0000BB">value</span><span style="color: #007700">=</span><span style="color: #DD0000">"Upload"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">form</span><span style="color: #007700">&gt;<br /><br />&lt;/</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br /><br />&lt;/</span><span style="color: #0000BB">html</span><span style="color: #007700">&gt;&nbsp;<br /></span></code></div></div></div><br />
--<br />
<br />
Ups, sebelum kita coba di browser, kita harus menambahkan route juga di routes/web.php seperti ini:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #FF8000">//&nbsp;...<br /><br /></span><span style="color: #0000BB">Route</span><span style="color: #007700">::</span><span style="color: #0000BB">resource</span><span style="color: #007700">(</span><span style="color: #DD0000">'storage'</span><span style="color: #007700">,&nbsp;</span><span style="color: #0000BB">&#092;App&#092;Http&#092;Controllers&#092;StorageController</span><span style="color: #007700">::class)<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">only</span><span style="color: #007700">([</span><span style="color: #DD0000">'index'</span><span style="color: #007700">,&nbsp;</span><span style="color: #DD0000">'store'</span><span style="color: #007700">]);&nbsp;<br /></span></code></div></div></div><br />
--<br />
<br />
Nah, saatnya pembuktian di browser!<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: x-large;" class="mycode_size">Langkah 5: Pembuktian!</span></span><br />
<br />
Silahkan jalankan web kita dengan perintah:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;serve&nbsp;<br /></span></code></div></div></div><br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>   INFO  Server running on [http://127.0.0.1:8000].  <br />
<br />
  Press Ctrl+C to stop the server</code></div></div><br />
Kemudian buka browser dan arahkan ke alamat <a href="http://localhost:8000/storage" target="_blank" rel="noopener" class="mycode_url">http://localhost:8000/storage</a>. Seharusnya muncul halaman seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-upload-form.jpg?resize=532%2C139&amp;ssl=1" loading="lazy"  width="532" height="139" alt="[Image: r2-upload-form.jpg?resize=532%2C139&amp;ssl=1]" class="mycode_img" /><br />
<br />
Silahkan coba upload satu gambar atau file.<br />
<br />
Pastikan di bucket kamu sudah bertambah 1 objek baru. Jika tidak, berarti masih ada yang keliru dari langkah-langkah sebelumnya. Silahkan diperiksa kembali.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-success-upload.jpg?resize=640%2C291&amp;ssl=1" loading="lazy"  width="640" height="291" alt="[Image: r2-success-upload.jpg?resize=640%2C291&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nampak ada satu file terupload di folder dengan nama storage dalam bucket nurfachmi-academy tersebut.<br />
<br />
Nah, demikian deh cara integrasi Cloudflare R2 ke dalam Laravel, sekaligus mengenalkan apa itu Cloudflare R2. Ada pertanyaan? Silahkan tanya di kolom komentar ya!<br />
<br />
Salam.<br />
<br />
<img src="https://nurfachmi.com/wp-content/uploads/2025/01/cloudflare-r2.png" loading="lazy"  width="1800" height="1013" alt="[Image: cloudflare-r2.png]" class="mycode_img" />]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, January 4, 2025</blockquote>
<br />
<span style="font-weight: bold;" class="mycode_b">Cloudflare R2 Storage</span> adalah layanan penyimpanan objek (object storage) yang dirancang sebagai alternatif dari solusi penyimpanan cloud tradisional seperti Amazon S3. R2 menawarkan cara untuk menyimpan data tidak terstruktur dalam jumlah besar, seperti file, gambar, video, atau dokumen, dengan fokus pada efisiensi biaya dan kinerja.<br />
<br />
<blockquote class="mycode_quote"><cite>Quote:</cite><img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/cloudflare.png?resize=381%2C376&amp;ssl=1" loading="lazy"  width="381" height="376" alt="[Image: cloudflare.png?resize=381%2C376&amp;ssl=1]" class="mycode_img" /></blockquote>
<br />
Keunggulan Utama Cloudflare R2<br />
<ul class="mycode_list"><li>Tanpa Biaya Egress<br />
</li>
</ul>
Salah satu fitur paling menarik dari R2 adalah penghapusan biaya egress (bandwidth keluar), yang biasanya menjadi komponen mahal dalam layanan penyimpanan cloud lainnya.<ul class="mycode_list"><li>Kompatibilitas dengan S3 API<br />
</li>
</ul>
R2 kompatibel dengan API Amazon S3, sehingga memudahkan pengembang untuk memigrasikan aplikasi atau integrasi yang sudah ada ke R2 tanpa banyak perubahan kode.<ul class="mycode_list"><li>Skalabilitas Tinggi<br />
</li>
</ul>
R2 dirancang untuk menyimpan data dalam jumlah besar dengan ketersediaan dan skalabilitas tinggi.<ul class="mycode_list"><li>Kinerja Optimal di Edge<br />
</li>
</ul>
Dengan jaringan edge Cloudflare yang luas, R2 memungkinkan pengiriman data yang cepat ke seluruh dunia, sehingga cocok untuk aplikasi yang memerlukan distribusi konten global.<ul class="mycode_list"><li>Harga Kompetitif<br />
</li>
</ul>
Biaya penyimpanan dan operasional R2 sangat kompetitif dibandingkan dengan layanan serupa, menjadikannya solusi ekonomis untuk berbagai kasus penggunaan.<br />
<br />
Bagaimana Cloudflare R2 Bekerja?<br />
<br />
R2 menyimpan data dalam bentuk objek, mirip dengan layanan object storage lainnya. Setiap objek diidentifikasi dengan kunci unik, dan metadata dapat ditambahkan untuk mempermudah pengelolaan data. Dengan integrasi yang mendalam ke dalam jaringan Cloudflare, data yang disimpan di R2 dapat diakses dengan cepat melalui jaringan edge Cloudflare.<br />
<br />
Jika kamu tertarik untuk mencoba Cloudflare R2, penulis akan menjelaskan langkah-langkah untuk mengintegrasikan R2 ke aplikasimu. ?<br />
<br />
---<br />
<br />
Berikut adalah langkah-langkah untuk mengintegrasikan Cloudflare R2 Storage ke aplikasi kamu, khususnya jika sudah familiar dengan Amazon S3 atau ingin memanfaatkan kompatibilitas S3 API:<br />
<br />
<span style="font-size: x-large;" class="mycode_size"><span style="font-weight: bold;" class="mycode_b">Langkah 1: Siapkan Bucket di Cloudflare R2</span></span><br />
<br />
Pertama, login ke akun Cloudflare kamu di Cloudflare Dashboard. Kalau belum punya akun, maka register dahulu.<br />
<br />
Kedua, akses menu R2 Object Storage dari sidebar. Jika ini adalah pertama kali, seharusnya muncul halaman register R2 seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/register-r2.png?resize=640%2C465&amp;ssl=1" loading="lazy"  width="640" height="465" alt="[Image: register-r2.png?resize=640%2C465&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jika seperti di atas, maka isi dulu formulir yang dibutuhkan. Tenang saja, kamu hanya akan ditagih jika melebihi batas pemakaian gratisannya kok.<br />
<br />
Lalu bagaimana soal tarif Cloudflare R2 ini? Apa maksudnya Storage, Class A operations dan Class B operations?<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/free-tier-r2.jpg?resize=640%2C401&amp;ssl=1" loading="lazy"  width="640" height="401" alt="[Image: free-tier-r2.jpg?resize=640%2C401&amp;ssl=1]" class="mycode_img" /><br />
<br />
Pada versi gratis, storage yang diberikan ialah sampai 10 GB per bulan. Jika lebih, maka akan kena biaya sebesar &#36;0.015 per GB dari kuota berlebihnya. Jika ukuran storage kamu 15 GB, maka akan kena biaya sekitar &#36;0.015 x 5 GB, yakni &#36;0.075 atau setara dengan IDR 1.125 jika kurs di angka IDR 15.000.<br />
<br />
Class A Operations, pada dasarnya adalah operasi yang cenderung mengubah status data, seperti menulis/upload atau memodifikasi objek, seperti PutObject (mengupload objek), CopyObject (menyalin objek), dan CompleteMultipartUpload (menyelesaikan upload multipart).<br />
<br />
Adapun Class B Operations adalah operasi yang biasanya membaca status data yang ada tanpa mengubahnya. Contohnya ialah GetObject (mengambil objek) dan HeadObject (memeriksa metadata objek).<br />
<br />
Baik, kembali lagi ke proses registrasi. Jika sudah berhasil memasukkan kredensial kartu kredit atau debit, maka akan muncul halaman seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-dashboard.png?resize=640%2C299&amp;ssl=1" loading="lazy"  width="640" height="299" alt="[Image: r2-dashboard.png?resize=640%2C299&amp;ssl=1]" class="mycode_img" /><br />
<br />
Selanjutnya adalah membuat Bucket. Apa itu Bucket? Bucket adalah keranjang yang isinya adalah objek-objek yang akan kita upload nanti.<br />
<br />
Silahkan isi nama bucket-mu.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/create-bucket.jpg?resize=640%2C574&amp;ssl=1" loading="lazy"  width="640" height="574" alt="[Image: create-bucket.jpg?resize=640%2C574&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jika berhasil, maka halamannya akan beralih seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/bucket-success.jpg?resize=640%2C345&amp;ssl=1" loading="lazy"  width="640" height="345" alt="[Image: bucket-success.jpg?resize=640%2C345&amp;ssl=1]" class="mycode_img" /><br />
<br />
Cobalah upload satu file dulu. Jika berhasil, maka tampilannya sebagai berikut:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-upload-success.jpg?resize=640%2C296&amp;ssl=1" loading="lazy"  width="640" height="296" alt="[Image: r2-upload-success.jpg?resize=640%2C296&amp;ssl=1]" class="mycode_img" /><br />
<br />
Saat ini, R2 kita hanya berlaku seperti flashdisk saja. Hanya bisa menyimpan data, tetapi belum bisa mengakses datanya secara online. Perhatikan pada bagian Public URL Access, di sana tertera Not allowed. Agar objek-objek yang kita upload bisa diakses, maka bagian tersebut harus berubah menjadi Allowed terlebih dahulu.<br />
<br />
Caranya adalah klik menu Settings, lalu cari bagian Public Access sebagai berikut, kemudian klik tombol Allow Access.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-go-public.jpg?resize=640%2C115&amp;ssl=1" loading="lazy"  width="640" height="115" alt="[Image: r2-go-public.jpg?resize=640%2C115&amp;ssl=1]" class="mycode_img" /><br />
<br />
Lalu ikuti arahannya sampai berubah menjadi seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-public-domain.jpg?resize=640%2C138&amp;ssl=1" loading="lazy"  width="640" height="138" alt="[Image: r2-public-domain.jpg?resize=640%2C138&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jika berhasil, maka saat masuk ke dalam objeknya, maka akan muncul URL publiknya sebagai berikut:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-public-url.jpg?resize=640%2C376&amp;ssl=1" loading="lazy"  width="640" height="376" alt="[Image: r2-public-url.jpg?resize=640%2C376&amp;ssl=1]" class="mycode_img" /><br />
<br />
Sampai sini, maka saatnya lanjut ke langkah berikutnya.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: x-large;" class="mycode_size">Langkah 2: Instalasi SDK atau Library</span></span><br />
<br />
Gunakan library yang mendukung Amazon S3 untuk mengintegrasikan aplikasi kita dengan R2. Contoh library populer:<br />
<br />
    PHP: AWS SDK for PHP<br />
    Node.js: AWS SDK for JavaScript<br />
    Python: Boto3<br />
    Go: Minio Go SDK<br />
<br />
Etapipaak, sebelum itu kita harus punya token API untuk dapat melakukan operasi menggunakan library di atas. Bagaimana caranya? Begini.<br />
<br />
Arahkan kembali ke halaman Overview R2 Object Storage, kemudian arahkan seperti gambar di bawah. Pilih Manage API tokens.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-menu-create-token.jpg?resize=640%2C244&amp;ssl=1" loading="lazy"  width="640" height="244" alt="[Image: r2-menu-create-token.jpg?resize=640%2C244&amp;ssl=1]" class="mycode_img" /><br />
<br />
Jika masih kosong, maka tampilannya sebagai berikut:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-token-empty-1024x228.jpg?resize=640%2C143&amp;ssl=1" loading="lazy"  width="640" height="143" alt="[Image: r2-token-empty-1024x228.jpg?resize=640%2C143&amp;ssl=1]" class="mycode_img" /><br />
<br />
Maka klik tombol <span style="font-weight: bold;" class="mycode_b">Create API token</span> untuk membuat satu. Berikut pengaturan penulis saat membuat token.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Token name</span>: <span style="text-decoration: underline;" class="mycode_u">token-r2-read-write</span><br />
<br />
<span style="font-weight: bold;" class="mycode_b">Permissions</span>: <span style="text-decoration: underline;" class="mycode_u">Object Read &amp; Write</span>: Allows the ability to read, write, and list objects in specific buckets.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Specify bucket(s)</span>: <span style="text-decoration: underline;" class="mycode_u">Apply to all buckets</span> in this account (including newly created buckets)<br />
<br />
<span style="font-weight: bold;" class="mycode_b">TTL</span>: <span style="text-decoration: underline;" class="mycode_u">Forever</span><br />
<br />
Jika telah berhasil, maka silahkan simpan kredensial yang diberikan, antara lain:<br />
<ul class="mycode_list"><li>    Token value<br />
</li>
<li>    Access Key ID<br />
</li>
<li>    Secret Access Key<br />
</li>
<li>    Default endpoint<br />
</li>
<li>    EU endpoint<br />
</li>
</ul>
<br />
Maka halamannya akan berubah menjadi seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-token-exists-1024x206.jpg?resize=640%2C129&amp;ssl=1" loading="lazy"  width="640" height="129" alt="[Image: r2-token-exists-1024x206.jpg?resize=640%2C129&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nah, selanjutnya kita akan mulai sedikit ngoding. Pada kali ini, saya contohkan pakai Laravel PHP ya.<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: x-large;" class="mycode_size">Langkah 3: Contoh Kode Implementasi</span></span><br />
<br />
Silahkan install Laravel fresh atau gunakan projek kamu yang ingin mengemplementasikan R2 ini.<br />
<br />
Selanjutnya install package S3<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">composer&nbsp;</span><span style="color: #007700">require&nbsp;</span><span style="color: #0000BB">league</span><span style="color: #007700">/</span><span style="color: #0000BB">flysystem</span><span style="color: #007700">-</span><span style="color: #0000BB">aws</span><span style="color: #007700">-</span><span style="color: #0000BB">s3</span><span style="color: #007700">-</span><span style="color: #0000BB">v3&nbsp;</span><span style="color: #DD0000">"^3.0"&nbsp;</span><span style="color: #007700">--</span><span style="color: #0000BB">with</span><span style="color: #007700">-</span><span style="color: #0000BB">all</span><span style="color: #007700">-</span><span style="color: #0000BB">dependencies&nbsp;<br /></span></code></div></div></div><br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>./composer.json has been updated<br />
Running composer update league/flysystem-aws-s3-v3 --with-all-dependencies<br />
Loading composer repositories with package information<br />
Updating dependencies<br />
Lock file operations: 4 installs, 3 updates, 0 removals<br />
  - Locking aws/aws-crt-php (v1.2.7)<br />
  - Locking aws/aws-sdk-php (3.336.7)<br />
  - Upgrading guzzlehttp/promises (2.0.3 =&gt; 2.0.4)<br />
  - Upgrading league/flysystem (3.29.0 =&gt; 3.29.1)<br />
  - Locking league/flysystem-aws-s3-v3 (3.29.0)<br />
  - Locking mtdowling/jmespath.php (2.8.0)<br />
  - Upgrading symfony/deprecation-contracts (v3.5.0 =&gt; v3.5.1)<br />
Writing lock file<br />
Installing dependencies from lock file (including require-dev)<br />
Package operations: 4 installs, 3 updates, 0 removals<br />
  - Downloading aws/aws-crt-php (v1.2.7)<br />
  - Downloading mtdowling/jmespath.php (2.8.0)<br />
  - Downloading aws/aws-sdk-php (3.336.7)<br />
  - Downloading league/flysystem-aws-s3-v3 (3.29.0)<br />
  - Installing aws/aws-crt-php (v1.2.7): Extracting archive<br />
  - Upgrading symfony/deprecation-contracts (v3.5.0 =&gt; v3.5.1): Extracting archive<br />
  - Upgrading guzzlehttp/promises (2.0.3 =&gt; 2.0.4): Extracting archive<br />
  - Upgrading league/flysystem (3.29.0 =&gt; 3.29.1): Extracting archive<br />
  - Installing mtdowling/jmespath.php (2.8.0): Extracting archive<br />
  - Installing aws/aws-sdk-php (3.336.7): Extracting archive<br />
  - Installing league/flysystem-aws-s3-v3 (3.29.0): Extracting archive<br />
3 package suggestions were added by new dependencies, use `composer suggest` to see details.<br />
Generating optimized autoload files<br />
&gt; Illuminate&#92;Foundation&#92;ComposerScripts::postAutoloadDump<br />
&gt; @php artisan package:discover --ansi<br />
<br />
   INFO  Discovering packages.  <br />
<br />
  laravel/sail .............................................................................. DONE<br />
  laravel/tinker ............................................................................ DONE<br />
  nesbot/carbon ............................................................................. DONE<br />
  nunomaduro/collision ...................................................................... DONE<br />
  nunomaduro/termwind ....................................................................... DONE<br />
<br />
78 packages you are using are looking for funding.<br />
Use the `composer fund` command to find out more!<br />
&gt; @php artisan vendor:publish --tag=laravel-assets --ansi --force<br />
<br />
   INFO  No publishable resources for tag [laravel-assets].  <br />
<br />
Found 4 security vulnerability advisories affecting 4 packages.<br />
Run "composer audit" for a full list of advisories.</code></div></div><br />
Oke, selanjutnya adalah tambahkan baris berikut ke file <span style="font-weight: bold;" class="mycode_b">.env</span> kita.<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>R2_ACCESS_KEY_ID=YOUR_ACCESS_KEY<br />
R2_SECRET_ACCESS_KEY=YOUR_SECRET_KEY<br />
R2_BUCKET=YOUR_BUCKET_NAME<br />
R2_ENDPOINT=XXXXXXX.r2.cloudflarestorage.com</code></div></div><br />
Lalu cari key <span style="font-weight: bold;" class="mycode_b">FILESYSTEM_DISK</span> dan ubah nilainya menjadi r2 seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>FILESYSTEM_DISK=r2</code></div></div><br />
Kira-kira lengkapnya menjadi seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>FILESYSTEM_DISK=r2<br />
<br />
// ...<br />
<br />
R2_ACCESS_KEY_ID=17c995******b72dec******87976<br />
R2_SECRET_ACCESS_KEY=fa55efa680d******5ecd898f06ae37761807f******b3bae36643f<br />
R2_BUCKET=nurfachmi-academy<br />
R2_ENDPOINT=https://9deccd0505******7560976cb3ff6.r2.cloudflarestorage.com</code></div></div><br />
Beberapa value di atas sudah disensor dengan karakter *.<br />
<br />
Selanjutnya tambahkan pengaturan disk di filesystem yang ada di <span style="font-weight: bold;" class="mycode_b">config/filesystem.php</span>.<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #007700">return&nbsp;[<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #FF8000">//&nbsp;...<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">'disks'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;[<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #FF8000">//&nbsp;...<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;  &nbsp;</span><span style="color: #DD0000">'r2'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;[<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'driver'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'s3'</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'key'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_ACCESS_KEY_ID'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'secret'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_SECRET_ACCESS_KEY'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'region'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'auto'</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'bucket'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_BUCKET'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'url'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_URL'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'endpoint'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_ENDPOINT'</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'use_path_style_endpoint'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">env</span><span style="color: #007700">(</span><span style="color: #DD0000">'R2_USE_PATH_STYLE_ENDPOINT'</span><span style="color: #007700">,&nbsp;</span><span style="color: #0000BB">false</span><span style="color: #007700">),<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #DD0000">'throw'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">false</span><span style="color: #007700">,<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">],<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">],<br />];&nbsp;<br /></span></code></div></div></div><br />
Sip, sekarang kita beralih ke MVC-nya. Model, View, dan Controller. Let’s go!<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: x-large;" class="mycode_size">Langkah 4: Model, View, dan Controller</span></span><br />
<br />
Kita buat ketiganya dalam satu perintah.<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;make</span><span style="color: #007700">:</span><span style="color: #0000BB">model&nbsp;Storage&nbsp;</span><span style="color: #007700">-</span><span style="color: #0000BB">mcr&nbsp;<br /></span></code></div></div></div><br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>INFO  Model [app/Models/Storage.php] created successfully.  <br />
<br />
   INFO  Migration [database/migrations/2025_01_04_005141_create_storages_table.php] created successfully.  <br />
<br />
   INFO  Controller [app/Http/Controllers/StorageController.php] created successfully.</code></div></div><br />
Dengan perintah di atas, kita membuat model Storage sekaligus migration dan resource controller.<br />
<br />
---<br />
<br />
Untuk migration, kita buat sederhana dulu saja seperti ini:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #FF8000">//&nbsp;...<br /><br /></span><span style="color: #007700">return&nbsp;new&nbsp;class&nbsp;extends&nbsp;</span><span style="color: #0000BB">Migration<br /></span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">public&nbsp;function&nbsp;</span><span style="color: #0000BB">up</span><span style="color: #007700">():&nbsp;</span><span style="color: #0000BB">void<br /> &nbsp; &nbsp;</span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;Schema</span><span style="color: #007700">::</span><span style="color: #0000BB">create</span><span style="color: #007700">(</span><span style="color: #DD0000">'storages'</span><span style="color: #007700">,&nbsp;function&nbsp;(</span><span style="color: #0000BB">Blueprint&nbsp;&#36;table</span><span style="color: #007700">)&nbsp;{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;table</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">id</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;table</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">string</span><span style="color: #007700">(</span><span style="color: #DD0000">'path'</span><span style="color: #007700">);<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;table</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">timestamps</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">});<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">}<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #FF8000">//&nbsp;...<br /></span><span style="color: #007700">}&nbsp;<br /></span></code></div></div></div><br />
Jalankan migratenya<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;migrate&nbsp;<br /></span></code></div></div></div><br />
File migration di atas setara dengan SQL command berikut:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">create&nbsp;table&nbsp;</span><span style="color: #DD0000">"storages"&nbsp;</span><span style="color: #007700">(<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">"id"&nbsp;</span><span style="color: #0000BB">integer&nbsp;primary&nbsp;key&nbsp;autoincrement&nbsp;not&nbsp;null</span><span style="color: #007700">,&nbsp;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">"path"&nbsp;</span><span style="color: #0000BB">varchar&nbsp;not&nbsp;null</span><span style="color: #007700">,&nbsp;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">"created_at"&nbsp;</span><span style="color: #0000BB">datetime</span><span style="color: #007700">,&nbsp;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #DD0000">"updated_at"&nbsp;</span><span style="color: #0000BB">datetime<br /></span><span style="color: #007700">);&nbsp;<br /></span></code></div></div></div><br />
---<br />
<br />
Selanjutnya kita modifikasi file controllernya seperti ini:<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #007700">namespace&nbsp;</span><span style="color: #0000BB">App&#092;Http&#092;Controllers</span><span style="color: #007700">;<br /><br />use&nbsp;</span><span style="color: #0000BB">Illuminate&#092;Http&#092;Request</span><span style="color: #007700">;<br /><br />class&nbsp;</span><span style="color: #0000BB">StorageController&nbsp;</span><span style="color: #007700">extends&nbsp;</span><span style="color: #0000BB">Controller<br /></span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">public&nbsp;function&nbsp;</span><span style="color: #0000BB">index</span><span style="color: #007700">()<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">return&nbsp;</span><span style="color: #0000BB">view</span><span style="color: #007700">(</span><span style="color: #DD0000">'upload'</span><span style="color: #007700">);<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">}<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">public&nbsp;function&nbsp;</span><span style="color: #0000BB">store</span><span style="color: #007700">(</span><span style="color: #0000BB">Request&nbsp;&#36;request</span><span style="color: #007700">)<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">try&nbsp;{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;path&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #0000BB">&#36;request</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">file</span><span style="color: #007700">(</span><span style="color: #DD0000">'file'</span><span style="color: #007700">)-&gt;</span><span style="color: #0000BB">store</span><span style="color: #007700">(</span><span style="color: #DD0000">'storage'</span><span style="color: #007700">);<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;storage&nbsp;</span><span style="color: #007700">=&nbsp;new&nbsp;</span><span style="color: #0000BB">&#092;App&#092;Models&#092;Storage</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;storage</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">path&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #0000BB">&#36;path</span><span style="color: #007700">;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&#36;storage</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">save</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">}&nbsp;catch&nbsp;(</span><span style="color: #0000BB">&#092;Throwable&nbsp;&#36;th</span><span style="color: #007700">)&nbsp;{<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;dd</span><span style="color: #007700">(</span><span style="color: #0000BB">&#36;th</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">getMessage</span><span style="color: #007700">());<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">}<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">return&nbsp;</span><span style="color: #0000BB">back</span><span style="color: #007700">();<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">}<br />}&nbsp;<br /></span></code></div></div></div><br />
Pada method index, kita sesederhana menampilkan view yang nanti berada di resources/views/upload.blade.php dan isinya berupa form upload saja dengan 2 elemen, yakni element input file dan tombol.<br />
<br />
Adapun pada method store, hanya berupa usaha untuk upload file ke Cloudflare R2 dan menyimpannya ke dalam model Storage. Jika gagal, maka akan menampilkan errornya dalam fungsi dd. Jika berhasil, maka kembali ke halaman upload lagi.<br />
<br />
Kita hanya menggunakan dua method itu saja dan silahkan hapus method lainnya karena tidak diperlukan.<br />
<br />
--<br />
<br />
Terakhir, buat file baru dengan nama upload.blade.php dalam folder resources/views dan isinya sesederhana berikut:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">&lt;!</span><span style="color: #0000BB">DOCTYPE&nbsp;html</span><span style="color: #007700">&gt;<br />&lt;</span><span style="color: #0000BB">html&nbsp;lang</span><span style="color: #007700">=</span><span style="color: #DD0000">"en"</span><span style="color: #007700">&gt;<br /><br />&lt;</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;charset</span><span style="color: #007700">=</span><span style="color: #DD0000">"UTF-8"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;name</span><span style="color: #007700">=</span><span style="color: #DD0000">"viewport"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"width=device-width,&nbsp;initial-scale=1.0"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">meta&nbsp;http</span><span style="color: #007700">-</span><span style="color: #0000BB">equiv</span><span style="color: #007700">=</span><span style="color: #DD0000">"X-UA-Compatible"&nbsp;</span><span style="color: #0000BB">content</span><span style="color: #007700">=</span><span style="color: #DD0000">"ie=edge"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;</span><span style="color: #0000BB">Upload&nbsp;to&nbsp;Cloudflare&nbsp;R2</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">title</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">link&nbsp;rel</span><span style="color: #007700">=</span><span style="color: #DD0000">"stylesheet"&nbsp;</span><span style="color: #0000BB">href</span><span style="color: #007700">=</span><span style="color: #DD0000">"https://cdn.jsdelivr.net/npm/@picocss/pico@2/css/pico.min.css"</span><span style="color: #007700">&gt;<br />&lt;/</span><span style="color: #0000BB">head</span><span style="color: #007700">&gt;<br /><br />&lt;</span><span style="color: #0000BB">body&nbsp;</span><span style="color: #007700">class=</span><span style="color: #DD0000">"container"</span><span style="color: #007700">&gt;<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">form&nbsp;action</span><span style="color: #007700">=</span><span style="color: #DD0000">"{{&nbsp;route('storage.store')&nbsp;}}"&nbsp;</span><span style="color: #0000BB">method</span><span style="color: #007700">=</span><span style="color: #DD0000">"post"&nbsp;</span><span style="color: #0000BB">enctype</span><span style="color: #007700">=</span><span style="color: #DD0000">"multipart/form-data"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">@</span><span style="color: #0000BB">csrf<br /><br /> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">input&nbsp;type</span><span style="color: #007700">=</span><span style="color: #DD0000">"file"&nbsp;</span><span style="color: #0000BB">name</span><span style="color: #007700">=</span><span style="color: #DD0000">"file"&nbsp;</span><span style="color: #0000BB">id</span><span style="color: #007700">=</span><span style="color: #DD0000">"file"&nbsp;</span><span style="color: #0000BB">required</span><span style="color: #007700">&gt;<br /><br /></span><span style="color: #0000BB"> &nbsp; &nbsp; &nbsp; &nbsp;</span><span style="color: #007700">&lt;</span><span style="color: #0000BB">input&nbsp;type</span><span style="color: #007700">=</span><span style="color: #DD0000">"submit"&nbsp;</span><span style="color: #0000BB">value</span><span style="color: #007700">=</span><span style="color: #DD0000">"Upload"</span><span style="color: #007700">&gt;<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">&lt;/</span><span style="color: #0000BB">form</span><span style="color: #007700">&gt;<br /><br />&lt;/</span><span style="color: #0000BB">body</span><span style="color: #007700">&gt;<br /><br />&lt;/</span><span style="color: #0000BB">html</span><span style="color: #007700">&gt;&nbsp;<br /></span></code></div></div></div><br />
--<br />
<br />
Ups, sebelum kita coba di browser, kita harus menambahkan route juga di routes/web.php seperti ini:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #FF8000">//&nbsp;...<br /><br /></span><span style="color: #0000BB">Route</span><span style="color: #007700">::</span><span style="color: #0000BB">resource</span><span style="color: #007700">(</span><span style="color: #DD0000">'storage'</span><span style="color: #007700">,&nbsp;</span><span style="color: #0000BB">&#092;App&#092;Http&#092;Controllers&#092;StorageController</span><span style="color: #007700">::class)<br /></span><span style="color: #0000BB"> &nbsp; &nbsp;</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">only</span><span style="color: #007700">([</span><span style="color: #DD0000">'index'</span><span style="color: #007700">,&nbsp;</span><span style="color: #DD0000">'store'</span><span style="color: #007700">]);&nbsp;<br /></span></code></div></div></div><br />
--<br />
<br />
Nah, saatnya pembuktian di browser!<br />
<br />
---<br />
<br />
<span style="font-weight: bold;" class="mycode_b"><span style="font-size: x-large;" class="mycode_size">Langkah 5: Pembuktian!</span></span><br />
<br />
Silahkan jalankan web kita dengan perintah:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">php&nbsp;artisan&nbsp;serve&nbsp;<br /></span></code></div></div></div><br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>   INFO  Server running on [http://127.0.0.1:8000].  <br />
<br />
  Press Ctrl+C to stop the server</code></div></div><br />
Kemudian buka browser dan arahkan ke alamat <a href="http://localhost:8000/storage" target="_blank" rel="noopener" class="mycode_url">http://localhost:8000/storage</a>. Seharusnya muncul halaman seperti ini:<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-upload-form.jpg?resize=532%2C139&amp;ssl=1" loading="lazy"  width="532" height="139" alt="[Image: r2-upload-form.jpg?resize=532%2C139&amp;ssl=1]" class="mycode_img" /><br />
<br />
Silahkan coba upload satu gambar atau file.<br />
<br />
Pastikan di bucket kamu sudah bertambah 1 objek baru. Jika tidak, berarti masih ada yang keliru dari langkah-langkah sebelumnya. Silahkan diperiksa kembali.<br />
<br />
<img src="https://i0.wp.com/nurfachmi.com/wp-content/uploads/2025/01/r2-success-upload.jpg?resize=640%2C291&amp;ssl=1" loading="lazy"  width="640" height="291" alt="[Image: r2-success-upload.jpg?resize=640%2C291&amp;ssl=1]" class="mycode_img" /><br />
<br />
Nampak ada satu file terupload di folder dengan nama storage dalam bucket nurfachmi-academy tersebut.<br />
<br />
Nah, demikian deh cara integrasi Cloudflare R2 ke dalam Laravel, sekaligus mengenalkan apa itu Cloudflare R2. Ada pertanyaan? Silahkan tanya di kolom komentar ya!<br />
<br />
Salam.<br />
<br />
<img src="https://nurfachmi.com/wp-content/uploads/2025/01/cloudflare-r2.png" loading="lazy"  width="1800" height="1013" alt="[Image: cloudflare-r2.png]" class="mycode_img" />]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Tech Bro vs Anak Seni]]></title>
			<link>https://bb.nurfachmi.com/thread-10.html</link>
			<pubDate>Sat, 02 May 2026 12:40:51 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-10.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, July 16, 2024</blockquote>
<br />
Bismillahirrahmanirrahim<br />
<br />
Sesekali ingin menuangkan pendapat yang ada di benak sejenak setelah baca tweet ini.<br />
<br />
<a href="https://x.com/fdmncfdmnc/status/1812657277784228049?ref_src=twsrc%5Etfw%7Ctwcamp%5Etweetembed%7Ctwterm%5E1812657277784228049%7Ctwgr%5E%7Ctwcon%5Es1_c10&amp;ref_url=https%3A%2F%2Fnurfachmi.com%2Ftech-bro-vs-anak-seni-artificial-intelligence%2F" target="_blank" rel="noopener" class="mycode_url">Twitter</a><br />
<br />
<img src="https://nurfachmi.com/wp-content/uploads/2024/12/IamProgrammerEnglish.png" loading="lazy"  width="1920" height="1080" alt="[Image: IamProgrammerEnglish.png]" class="mycode_img" /><br />
<br />
<span style="font-size: x-large;" class="mycode_size">Latar Belakang</span><br />
<br />
Mengapa tech bro seperti ndak tergeser keberadaannya dengan AI? Karena kami, ya saya juga termasuk tech bro karena berprofesi di bidang teknologi ~khususnya sebagai software engineer~, memanfaatkan AI untuk memudahkan pekerjaan. Lantas mengapa anak seni terlihat seperti melawan keberadaan AI?<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Rumusan Masalah</span><br />
<br />
IMHO karena anak seni belum memiliki wadah, semacam layanan AI, yang memudahkan pekerjaannya. Andaikan ada, maka lain cerita.<br />
<br />
Banyak AI Image Generator bertebaran di internet, dari yang gratis hingga yang nguras kantong abis. Namun, menurutku tetap kurang mengakomodir kebutuhan mereka.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Masalah Penulis</span><br />
<br />
Sejujurnya saya tidak memiliki pengetahuan apa-apa tentang seni dan menulis artikel ini pun tanpa bertanya-tanya dahulu ke anak seni satu pun. Jadi ini murni pendapat pribadi. Bahkan saya pun hanya penikmat layanan AI dan belum bisa membuat layanan menggunakan AI.<br />
<br />
Entah, jadi bingung nulis akar masalahnya yang dialami anak seni ini. Etapi saya kurang suka terlalu fokus dengan masalah. Lebih senang banyak menghabiskan waktu untuk mencari jalan keluar.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Pembahasan</span><br />
<br />
Saya hanya membayangkan jika ada servis AI yang flownya benar-benar dapat membantu para anak seni ini. Jadi ndak hanya sekedar menulis prompt yang benar, tetapi juga dataset yang digunakan sesuai dengan yang mereka kehendaki.<br />
<br />
Kira-kira begini flownya.<br />
<ol type="1" class="mycode_list"><li>User mendaftarkan dirinya ke website atau aplikasi gawai.<br />
</li>
<li>User memasukkan referensi gambar-gambar yang biasa ia hasilkan atau yang menjadi referensi sebagai keluaran hasilnya nanti.<br />
</li>
<li>User menunggu beberapa waktu untuk sistem dapat “belajar” dari materi-materi yang diberikan pada poin sebelumnya.<br />
</li>
<li>Setelah siap, user mendapatkan notifikasi dan mulai dapat menuliskan prompt yang ia inginkan dan hasilnya pun sesuai dengan referensi yang diinput.<br />
</li>
</ol>
<br />
Lalu apa bedanya dengan AI Image Generator pada umumnya? Berikut kira-kira perbedaannya, atau bisa dibilang sebagai “keuntungan”-nya.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Meminimalisir pencurian hak cipta.</span><br />
<br />
Dilansir bahwa AI Image Generator banyak melakukan pencurian hak cipta karena memakai sembarang gambar untuk dipelajari oleh AI mereka tanpa izin atau sepengetahuan pemilik gambar. Dengan flow di atas, maka si layanan AI ini hanya memakai sumber data yang diberikan oleh User. Jadi jika terjadi penuntutan atas pelanggaran hak cipta, maka bisa langsung ditujukan kepada User, bukan layanan AI-nya.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">WYGIWYG</span><br />
<br />
Kalau di skena Tech Bro ada WYSIWYG (baca: wisiwig) (What You See is What You Get), maka dengan flow di atas anak seni dapat WYGIWYG (baca: wigiwig) (What You Give is What You Get). Artinya hasil prompt yang diberikan akan selalu merujuk kepada materi-materi yang ia berikan sendiri kepada si AI.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Memudahkan Anak Seni</span><br />
<br />
Dengan dua keuntungan sebelumnya, maka saya rasa layanan AI tersebut akan menjadi salah satu alat yang sangat amat memudahkan pekerjaan si anak seni tersebut. Setelah memberikan prompt, layanan AI akan memberikan beberapa sugesti hasil yang kemudian bisa langsung dipakai atau hanya dijadikan referensi yang nanti akan dikerjakan secara manual oleh tangannya si anak seni tersebut.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Penutup</span><br />
<br />
Yah begitulah kira-kira yang ada dalam benak saya mengenai perseteruan pada tweet di atas. Maafkan jika ada kekurangan.]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, July 16, 2024</blockquote>
<br />
Bismillahirrahmanirrahim<br />
<br />
Sesekali ingin menuangkan pendapat yang ada di benak sejenak setelah baca tweet ini.<br />
<br />
<a href="https://x.com/fdmncfdmnc/status/1812657277784228049?ref_src=twsrc%5Etfw%7Ctwcamp%5Etweetembed%7Ctwterm%5E1812657277784228049%7Ctwgr%5E%7Ctwcon%5Es1_c10&amp;ref_url=https%3A%2F%2Fnurfachmi.com%2Ftech-bro-vs-anak-seni-artificial-intelligence%2F" target="_blank" rel="noopener" class="mycode_url">Twitter</a><br />
<br />
<img src="https://nurfachmi.com/wp-content/uploads/2024/12/IamProgrammerEnglish.png" loading="lazy"  width="1920" height="1080" alt="[Image: IamProgrammerEnglish.png]" class="mycode_img" /><br />
<br />
<span style="font-size: x-large;" class="mycode_size">Latar Belakang</span><br />
<br />
Mengapa tech bro seperti ndak tergeser keberadaannya dengan AI? Karena kami, ya saya juga termasuk tech bro karena berprofesi di bidang teknologi ~khususnya sebagai software engineer~, memanfaatkan AI untuk memudahkan pekerjaan. Lantas mengapa anak seni terlihat seperti melawan keberadaan AI?<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Rumusan Masalah</span><br />
<br />
IMHO karena anak seni belum memiliki wadah, semacam layanan AI, yang memudahkan pekerjaannya. Andaikan ada, maka lain cerita.<br />
<br />
Banyak AI Image Generator bertebaran di internet, dari yang gratis hingga yang nguras kantong abis. Namun, menurutku tetap kurang mengakomodir kebutuhan mereka.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Masalah Penulis</span><br />
<br />
Sejujurnya saya tidak memiliki pengetahuan apa-apa tentang seni dan menulis artikel ini pun tanpa bertanya-tanya dahulu ke anak seni satu pun. Jadi ini murni pendapat pribadi. Bahkan saya pun hanya penikmat layanan AI dan belum bisa membuat layanan menggunakan AI.<br />
<br />
Entah, jadi bingung nulis akar masalahnya yang dialami anak seni ini. Etapi saya kurang suka terlalu fokus dengan masalah. Lebih senang banyak menghabiskan waktu untuk mencari jalan keluar.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Pembahasan</span><br />
<br />
Saya hanya membayangkan jika ada servis AI yang flownya benar-benar dapat membantu para anak seni ini. Jadi ndak hanya sekedar menulis prompt yang benar, tetapi juga dataset yang digunakan sesuai dengan yang mereka kehendaki.<br />
<br />
Kira-kira begini flownya.<br />
<ol type="1" class="mycode_list"><li>User mendaftarkan dirinya ke website atau aplikasi gawai.<br />
</li>
<li>User memasukkan referensi gambar-gambar yang biasa ia hasilkan atau yang menjadi referensi sebagai keluaran hasilnya nanti.<br />
</li>
<li>User menunggu beberapa waktu untuk sistem dapat “belajar” dari materi-materi yang diberikan pada poin sebelumnya.<br />
</li>
<li>Setelah siap, user mendapatkan notifikasi dan mulai dapat menuliskan prompt yang ia inginkan dan hasilnya pun sesuai dengan referensi yang diinput.<br />
</li>
</ol>
<br />
Lalu apa bedanya dengan AI Image Generator pada umumnya? Berikut kira-kira perbedaannya, atau bisa dibilang sebagai “keuntungan”-nya.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Meminimalisir pencurian hak cipta.</span><br />
<br />
Dilansir bahwa AI Image Generator banyak melakukan pencurian hak cipta karena memakai sembarang gambar untuk dipelajari oleh AI mereka tanpa izin atau sepengetahuan pemilik gambar. Dengan flow di atas, maka si layanan AI ini hanya memakai sumber data yang diberikan oleh User. Jadi jika terjadi penuntutan atas pelanggaran hak cipta, maka bisa langsung ditujukan kepada User, bukan layanan AI-nya.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">WYGIWYG</span><br />
<br />
Kalau di skena Tech Bro ada WYSIWYG (baca: wisiwig) (What You See is What You Get), maka dengan flow di atas anak seni dapat WYGIWYG (baca: wigiwig) (What You Give is What You Get). Artinya hasil prompt yang diberikan akan selalu merujuk kepada materi-materi yang ia berikan sendiri kepada si AI.<br />
<br />
<span style="font-weight: bold;" class="mycode_b">Memudahkan Anak Seni</span><br />
<br />
Dengan dua keuntungan sebelumnya, maka saya rasa layanan AI tersebut akan menjadi salah satu alat yang sangat amat memudahkan pekerjaan si anak seni tersebut. Setelah memberikan prompt, layanan AI akan memberikan beberapa sugesti hasil yang kemudian bisa langsung dipakai atau hanya dijadikan referensi yang nanti akan dikerjakan secara manual oleh tangannya si anak seni tersebut.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Penutup</span><br />
<br />
Yah begitulah kira-kira yang ada dalam benak saya mengenai perseteruan pada tweet di atas. Maafkan jika ada kekurangan.]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Mengatur ID Increment Selanjutnya pada PostgreSQL dan MySQL]]></title>
			<link>https://bb.nurfachmi.com/thread-9.html</link>
			<pubDate>Sat, 02 May 2026 12:34:10 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-9.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, July 29, 2024</blockquote>
<br />
Bismillahirrahmanirrahim<br />
<br />
Bermula dari error yang saya temukan saat ingin menambahkan data lewat CMS dan keharusan saya untuk menuliskan nilai pada kolom “id” yang seharusnya terisi sendiri meski dikosongkan, maka saya mengambil keputusan bahwa ada yang keliru dengan nilai increment selanjutnya. Sebenarnya, kesulitan saya ini terjadi di PostgreSQL karena untuk menentukan nilai increment selanjutnya tidak semudah di MySQL dengan DBeaver sebagai Database GUI utama.<br />
<br />
<img src="https://nurfachmi.com/wp-content/uploads/2025/05/postgresql.jpeg" loading="lazy"  width="1520" height="852" alt="[Image: postgresql.jpeg]" class="mycode_img" /><br />
<br />
Pada MySQL, untuk menentukan nilai auto-increment selanjutnya bisa dilihat dan ditentukan tanpa menggunakan query. Cukup lihat pada properties tabel yang diinginkan, lalu ubah dan klik simpan.<br />
<br />
<img src="https://i0.wp.com/cdn.hashnode.com/res/hashnode/image/upload/v1722199356692/419e6b22-147e-4893-836f-296697984edf.png?w=640&amp;ssl=1" loading="lazy"  alt="[Image: 419e6b22-147e-4893-836f-296697984edf.png?w=640&amp;ssl=1]" class="mycode_img" /><br />
<br />
Pada PostgreSQL, tampilan properties tabelnya tidak seperti di atas, melainkan seperti ini:<br />
<br />
<img src="https://i0.wp.com/cdn.hashnode.com/res/hashnode/image/upload/v1722199435200/cc4ba708-628a-4acc-a351-bebcdd24b948.png?w=640&amp;ssl=1" loading="lazy"  alt="[Image: cc4ba708-628a-4acc-a351-bebcdd24b948.png?w=640&amp;ssl=1]" class="mycode_img" /><br />
<br />
Tidak terlihat pengaturan auto-increment-nya, kan?<br />
<br />
Yah begitu lah keterbatasan Database GUI Editor, tidak akan semudah dan sefleksibel command line pada terminal.<br />
<br />
Setelah googling sana-sini, beginilah cara mengetahui nilai increment selanjutnya dan cara mengatur nilai increment selanjutnya pada PostgreSQL maupun MySQL.<br />
<br />
<span style="font-size: xx-large;" class="mycode_size">PostgreSQL</span><br />
<br />
<span style="font-size: x-large;" class="mycode_size">Mengetahui nilai increment selanjutnya</span><br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT nextval('nama_sequence');</code></div></div><br />
Pertanyaannya, bagaimana mengetahui nama_sequence pada tabel tertentu itu?<br />
<br />
Pada DBeaver, hal itu bisa didapatkan dengan melihat tab <span style="font-weight: bold;" class="mycode_b">Columns</span> dan nilai kolom Defaultnya.<br />
<br />
<img src="https://i0.wp.com/cdn.hashnode.com/res/hashnode/image/upload/v1722199926610/58ad0d54-b6f1-4be0-ac7d-900318238679.png?w=640&amp;ssl=1" loading="lazy"  alt="[Image: 58ad0d54-b6f1-4be0-ac7d-900318238679.png?w=640&amp;ssl=1]" class="mycode_img" /><br />
<br />
Namun, untuk mendapatkan <span style="font-weight: bold;" class="mycode_b">nama_sequence</span> menggunakan query adalah sebagai berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT pg_get_serial_sequence('nama_tabel', 'nama_kolom');<br />
<br />
-- contoh:<br />
SELECT pg_get_serial_sequence('staff', 'id');<br />
<br />
-- contoh response:<br />
-- public.staff_id_seq</code></div></div><br />
Maka, selanjutnya tinggal dibungkus menjadi <span style="font-style: italic;" class="mycode_i">string</span> dan ditambahkan identifikasi kelas (class) dengan akhiran <span style="font-weight: bold;" class="mycode_b">::regclass</span> dan tanpa awalan public.-nya.<br />
<br />
Hasil akhirnya adalah berupa sequence_name : <span style="font-weight: bold;" class="mycode_b">‘staff_id_seq’::regclass</span><br />
<br />
Untuk mendapatkan nilai increment selanjutnya, bisa dengan query berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT nextval('staff_id_seq'::regclass);<br />
<br />
-- output<br />
-- kolom : nextval<br />
-- nilai : 853</code></div></div><br />
<span style="font-size: x-large;" class="mycode_size">Mengatur nilai increment selanjutnya</span><br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT setval('nama_sequence', nilai_baru);</code></div></div><br />
Jika mengikuti contoh kolom di atas, maka query lengkapnya akan seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT setval('staff_id_seq'::regclass, 860);</code></div></div><br />
<span style="font-size: xx-large;" class="mycode_size">MySQL</span><br />
<br />
<span style="font-size: x-large;" class="mycode_size">Mengetahui nilai increment selanjutnya</span><br />
<br />
Ada dua cara atau query untuk mendapatkan hal tersebut, yakni query panjang dan pendek. Mari kita mulai dengan query panjang dahulu, yaitu seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT AUTO_INCREMENT<br />
FROM information_schema.TABLES<br />
WHERE TABLE_SCHEMA = 'nama_database'<br />
AND TABLE_NAME = 'nama_tabel';</code></div></div><br />
Contohnya seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT AUTO_INCREMENT<br />
FROM information_schema.TABLES<br />
WHERE TABLE_SCHEMA = 'daycare'<br />
AND TABLE_NAME = 'staff';<br />
<br />
-- output<br />
-- kolom : AUTO_INCREMENT<br />
-- nilai : 853</code></div></div><br />
Adapun query pendeknya bisa seperti ini :<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SHOW TABLE STATUS LIKE 'nama_tabel';</code></div></div><br />
Contohnya seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SHOW TABLE STATUS LIKE 'staff';<br />
<br />
-- output<br />
-- kolom : Auto_increment<br />
-- nilai : 853</code></div></div><br />
Kemudian lihat hasil pada kolom ‘Auto_increment’. Angka yang tampil adalah yang menjadi nilai increment selanjutnya.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Mengatur nilai increment selanjutnya</span><br />
<br />
Untuk mengatur atau override nilai increment selanjutnya, bisa dicapai dengan query berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>ALTER TABLE nama_tabel AUTO_INCREMENT = nilai_baru;</code></div></div><br />
Contohnya seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>ALTER TABLE staff AUTO_INCREMENT = 860;</code></div></div><br />
---<br />
<br />
Ya, kira-kira demikian untuk mengetahui dan mengatur nilai increment selanjutnya pada PostgreSQL dan MySQL. Maafkan jika ada kekurangan dan mohon koreksi jika ada kekeliruan.]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, July 29, 2024</blockquote>
<br />
Bismillahirrahmanirrahim<br />
<br />
Bermula dari error yang saya temukan saat ingin menambahkan data lewat CMS dan keharusan saya untuk menuliskan nilai pada kolom “id” yang seharusnya terisi sendiri meski dikosongkan, maka saya mengambil keputusan bahwa ada yang keliru dengan nilai increment selanjutnya. Sebenarnya, kesulitan saya ini terjadi di PostgreSQL karena untuk menentukan nilai increment selanjutnya tidak semudah di MySQL dengan DBeaver sebagai Database GUI utama.<br />
<br />
<img src="https://nurfachmi.com/wp-content/uploads/2025/05/postgresql.jpeg" loading="lazy"  width="1520" height="852" alt="[Image: postgresql.jpeg]" class="mycode_img" /><br />
<br />
Pada MySQL, untuk menentukan nilai auto-increment selanjutnya bisa dilihat dan ditentukan tanpa menggunakan query. Cukup lihat pada properties tabel yang diinginkan, lalu ubah dan klik simpan.<br />
<br />
<img src="https://i0.wp.com/cdn.hashnode.com/res/hashnode/image/upload/v1722199356692/419e6b22-147e-4893-836f-296697984edf.png?w=640&amp;ssl=1" loading="lazy"  alt="[Image: 419e6b22-147e-4893-836f-296697984edf.png?w=640&amp;ssl=1]" class="mycode_img" /><br />
<br />
Pada PostgreSQL, tampilan properties tabelnya tidak seperti di atas, melainkan seperti ini:<br />
<br />
<img src="https://i0.wp.com/cdn.hashnode.com/res/hashnode/image/upload/v1722199435200/cc4ba708-628a-4acc-a351-bebcdd24b948.png?w=640&amp;ssl=1" loading="lazy"  alt="[Image: cc4ba708-628a-4acc-a351-bebcdd24b948.png?w=640&amp;ssl=1]" class="mycode_img" /><br />
<br />
Tidak terlihat pengaturan auto-increment-nya, kan?<br />
<br />
Yah begitu lah keterbatasan Database GUI Editor, tidak akan semudah dan sefleksibel command line pada terminal.<br />
<br />
Setelah googling sana-sini, beginilah cara mengetahui nilai increment selanjutnya dan cara mengatur nilai increment selanjutnya pada PostgreSQL maupun MySQL.<br />
<br />
<span style="font-size: xx-large;" class="mycode_size">PostgreSQL</span><br />
<br />
<span style="font-size: x-large;" class="mycode_size">Mengetahui nilai increment selanjutnya</span><br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT nextval('nama_sequence');</code></div></div><br />
Pertanyaannya, bagaimana mengetahui nama_sequence pada tabel tertentu itu?<br />
<br />
Pada DBeaver, hal itu bisa didapatkan dengan melihat tab <span style="font-weight: bold;" class="mycode_b">Columns</span> dan nilai kolom Defaultnya.<br />
<br />
<img src="https://i0.wp.com/cdn.hashnode.com/res/hashnode/image/upload/v1722199926610/58ad0d54-b6f1-4be0-ac7d-900318238679.png?w=640&amp;ssl=1" loading="lazy"  alt="[Image: 58ad0d54-b6f1-4be0-ac7d-900318238679.png?w=640&amp;ssl=1]" class="mycode_img" /><br />
<br />
Namun, untuk mendapatkan <span style="font-weight: bold;" class="mycode_b">nama_sequence</span> menggunakan query adalah sebagai berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT pg_get_serial_sequence('nama_tabel', 'nama_kolom');<br />
<br />
-- contoh:<br />
SELECT pg_get_serial_sequence('staff', 'id');<br />
<br />
-- contoh response:<br />
-- public.staff_id_seq</code></div></div><br />
Maka, selanjutnya tinggal dibungkus menjadi <span style="font-style: italic;" class="mycode_i">string</span> dan ditambahkan identifikasi kelas (class) dengan akhiran <span style="font-weight: bold;" class="mycode_b">::regclass</span> dan tanpa awalan public.-nya.<br />
<br />
Hasil akhirnya adalah berupa sequence_name : <span style="font-weight: bold;" class="mycode_b">‘staff_id_seq’::regclass</span><br />
<br />
Untuk mendapatkan nilai increment selanjutnya, bisa dengan query berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT nextval('staff_id_seq'::regclass);<br />
<br />
-- output<br />
-- kolom : nextval<br />
-- nilai : 853</code></div></div><br />
<span style="font-size: x-large;" class="mycode_size">Mengatur nilai increment selanjutnya</span><br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT setval('nama_sequence', nilai_baru);</code></div></div><br />
Jika mengikuti contoh kolom di atas, maka query lengkapnya akan seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT setval('staff_id_seq'::regclass, 860);</code></div></div><br />
<span style="font-size: xx-large;" class="mycode_size">MySQL</span><br />
<br />
<span style="font-size: x-large;" class="mycode_size">Mengetahui nilai increment selanjutnya</span><br />
<br />
Ada dua cara atau query untuk mendapatkan hal tersebut, yakni query panjang dan pendek. Mari kita mulai dengan query panjang dahulu, yaitu seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT AUTO_INCREMENT<br />
FROM information_schema.TABLES<br />
WHERE TABLE_SCHEMA = 'nama_database'<br />
AND TABLE_NAME = 'nama_tabel';</code></div></div><br />
Contohnya seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SELECT AUTO_INCREMENT<br />
FROM information_schema.TABLES<br />
WHERE TABLE_SCHEMA = 'daycare'<br />
AND TABLE_NAME = 'staff';<br />
<br />
-- output<br />
-- kolom : AUTO_INCREMENT<br />
-- nilai : 853</code></div></div><br />
Adapun query pendeknya bisa seperti ini :<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SHOW TABLE STATUS LIKE 'nama_tabel';</code></div></div><br />
Contohnya seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>SHOW TABLE STATUS LIKE 'staff';<br />
<br />
-- output<br />
-- kolom : Auto_increment<br />
-- nilai : 853</code></div></div><br />
Kemudian lihat hasil pada kolom ‘Auto_increment’. Angka yang tampil adalah yang menjadi nilai increment selanjutnya.<br />
<br />
<span style="font-size: x-large;" class="mycode_size">Mengatur nilai increment selanjutnya</span><br />
<br />
Untuk mengatur atau override nilai increment selanjutnya, bisa dicapai dengan query berikut:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>ALTER TABLE nama_tabel AUTO_INCREMENT = nilai_baru;</code></div></div><br />
Contohnya seperti ini:<br />
<br />
<div class="codeblock"><div class="title">Code:</div><div class="body" dir="ltr"><code>ALTER TABLE staff AUTO_INCREMENT = 860;</code></div></div><br />
---<br />
<br />
Ya, kira-kira demikian untuk mengetahui dan mengatur nilai increment selanjutnya pada PostgreSQL dan MySQL. Maafkan jika ada kekurangan dan mohon koreksi jika ada kekeliruan.]]></content:encoded>
		</item>
		<item>
			<title><![CDATA[Class Ajaib di Laravel]]></title>
			<link>https://bb.nurfachmi.com/thread-8.html</link>
			<pubDate>Sat, 02 May 2026 12:27:22 +0000</pubDate>
			<dc:creator><![CDATA[<a href="https://bb.nurfachmi.com/member.php?action=profile&uid=1">admin</a>]]></dc:creator>
			<guid isPermaLink="false">https://bb.nurfachmi.com/thread-8.html</guid>
			<description><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, March 28, 2023</blockquote>
<br />
Tau nggak sih kenapa barisan kode sederhana seperti ini bisa mengeluarkan output dengan berbagai cara?<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;user&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #0000BB">&#092;App&#092;Models&#092;User</span><span style="color: #007700">::</span><span style="color: #0000BB">inRandomOrder</span><span style="color: #007700">()-&gt;</span><span style="color: #0000BB">first</span><span style="color: #007700">();&nbsp;<br /></span></code></div></div></div><br />
Dengan keluaran sebagai array, bisa…<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;user</span><span style="color: #007700">[</span><span style="color: #DD0000">'name'</span><span style="color: #007700">];&nbsp;</span><span style="color: #FF8000">//&nbsp;output:&nbsp;John&nbsp;<br /></span></code></div></div></div><br />
Dengan keluaran sebagai object, bisa juga…<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;user</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">name</span><span style="color: #007700">;&nbsp;</span><span style="color: #FF8000">//&nbsp;output:&nbsp;John&nbsp;<br /></span></code></div></div></div><br />
Jawabannya adalah karena ada suatu class yang namanya Fluent. Class ini secara ajaib melakukan mutasi kepada data agar bisa diakses dalam berbagai metode. Salah duanya adalah seperti yang sudah penulis jabarkan di atas.<br />
<br />
Sebelum penulis berikan berbagai contoh penggunaannya, mari kita kenalan dengan class Fluent ini.<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">use&nbsp;</span><span style="color: #0000BB">Illuminate&#092;Support&#092;Fluent</span><span style="color: #007700">;<br /><br /></span><span style="color: #0000BB">&#36;attributes&nbsp;</span><span style="color: #007700">=&nbsp;[</span><span style="color: #DD0000">'name'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'Reza'</span><span style="color: #007700">];<br /></span><span style="color: #0000BB">&#36;data&nbsp;</span><span style="color: #007700">=&nbsp;new&nbsp;</span><span style="color: #0000BB">Fluent</span><span style="color: #007700">(</span><span style="color: #0000BB">&#36;attributes</span><span style="color: #007700">);&nbsp;<br /></span></code></div></div></div><br />
Selanjutnya adalah ada berbagai metode yang bisa dilakukan oleh class Fluent ini. Penulis langsung jabarkan melalui contoh satu per satu ya.<br />
<br />
---<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">get</span><span style="color: #007700">(</span><span style="color: #DD0000">'name'</span><span style="color: #007700">,&nbsp;</span><span style="color: #DD0000">'Nurfachmi'</span><span style="color: #007700">);&nbsp;<br /></span></code></div></div></div><br />
Kode di atas akan mengembalikan nilai dari name atau Nurfachmi jika name belum di-set nilainya.<br />
<br />
---<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">getAttributes</span><span style="color: #007700">();&nbsp;<br /></span></code></div></div></div><br />
Kode di atas akan mengembalikan seluruh atribut yang sudah di-set, termasuk yang baru dibuat, misalnya:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">last_name&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #DD0000">"Nurfachmi"</span><span style="color: #007700">;<br /><br /></span><span style="color: #0000BB">print_r</span><span style="color: #007700">(</span><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">getAttributes</span><span style="color: #007700">());<br /></span><span style="color: #FF8000">/***<br />Output:<br />Array&nbsp;(&nbsp;[name]&nbsp;=&gt;&nbsp;Reza&nbsp;[last_name]&nbsp;=&gt;&nbsp;Nurfachmi&nbsp;)<br />***/&nbsp;<br /></span></code></div></div></div><br />
---<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">toArray</span><span style="color: #007700">();&nbsp;<br /></span></code></div></div></div><br />
Kode di atas akan mengembalikan data sebagai array.<br />
<br />
---<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">toJson</span><span style="color: #007700">();&nbsp;<br /></span></code></div></div></div><br />
Kode di atas akan mengembalikan data sebagai json.<br />
<br />
---<br />
<br />
Fluent adalah sebuah utiliti class yang disediakan oleh Laravel sendiri agar kita dapat secara luwes mengolah data.]]></description>
			<content:encoded><![CDATA[<blockquote class="mycode_quote"><cite>Quote:</cite>Reza Nurfachmi, March 28, 2023</blockquote>
<br />
Tau nggak sih kenapa barisan kode sederhana seperti ini bisa mengeluarkan output dengan berbagai cara?<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;user&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #0000BB">&#092;App&#092;Models&#092;User</span><span style="color: #007700">::</span><span style="color: #0000BB">inRandomOrder</span><span style="color: #007700">()-&gt;</span><span style="color: #0000BB">first</span><span style="color: #007700">();&nbsp;<br /></span></code></div></div></div><br />
Dengan keluaran sebagai array, bisa…<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;user</span><span style="color: #007700">[</span><span style="color: #DD0000">'name'</span><span style="color: #007700">];&nbsp;</span><span style="color: #FF8000">//&nbsp;output:&nbsp;John&nbsp;<br /></span></code></div></div></div><br />
Dengan keluaran sebagai object, bisa juga…<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;user</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">name</span><span style="color: #007700">;&nbsp;</span><span style="color: #FF8000">//&nbsp;output:&nbsp;John&nbsp;<br /></span></code></div></div></div><br />
Jawabannya adalah karena ada suatu class yang namanya Fluent. Class ini secara ajaib melakukan mutasi kepada data agar bisa diakses dalam berbagai metode. Salah duanya adalah seperti yang sudah penulis jabarkan di atas.<br />
<br />
Sebelum penulis berikan berbagai contoh penggunaannya, mari kita kenalan dengan class Fluent ini.<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #007700">use&nbsp;</span><span style="color: #0000BB">Illuminate&#092;Support&#092;Fluent</span><span style="color: #007700">;<br /><br /></span><span style="color: #0000BB">&#36;attributes&nbsp;</span><span style="color: #007700">=&nbsp;[</span><span style="color: #DD0000">'name'&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">'Reza'</span><span style="color: #007700">];<br /></span><span style="color: #0000BB">&#36;data&nbsp;</span><span style="color: #007700">=&nbsp;new&nbsp;</span><span style="color: #0000BB">Fluent</span><span style="color: #007700">(</span><span style="color: #0000BB">&#36;attributes</span><span style="color: #007700">);&nbsp;<br /></span></code></div></div></div><br />
Selanjutnya adalah ada berbagai metode yang bisa dilakukan oleh class Fluent ini. Penulis langsung jabarkan melalui contoh satu per satu ya.<br />
<br />
---<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">get</span><span style="color: #007700">(</span><span style="color: #DD0000">'name'</span><span style="color: #007700">,&nbsp;</span><span style="color: #DD0000">'Nurfachmi'</span><span style="color: #007700">);&nbsp;<br /></span></code></div></div></div><br />
Kode di atas akan mengembalikan nilai dari name atau Nurfachmi jika name belum di-set nilainya.<br />
<br />
---<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">getAttributes</span><span style="color: #007700">();&nbsp;<br /></span></code></div></div></div><br />
Kode di atas akan mengembalikan seluruh atribut yang sudah di-set, termasuk yang baru dibuat, misalnya:<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">last_name&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #DD0000">"Nurfachmi"</span><span style="color: #007700">;<br /><br /></span><span style="color: #0000BB">print_r</span><span style="color: #007700">(</span><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">getAttributes</span><span style="color: #007700">());<br /></span><span style="color: #FF8000">/***<br />Output:<br />Array&nbsp;(&nbsp;[name]&nbsp;=&gt;&nbsp;Reza&nbsp;[last_name]&nbsp;=&gt;&nbsp;Nurfachmi&nbsp;)<br />***/&nbsp;<br /></span></code></div></div></div><br />
---<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">toArray</span><span style="color: #007700">();&nbsp;<br /></span></code></div></div></div><br />
Kode di atas akan mengembalikan data sebagai array.<br />
<br />
---<br />
<br />
<div class="codeblock phpcodeblock"><div class="title">PHP Code:</div><div class="body"><div dir="ltr"><code><span style="color: #0000BB">&#36;data</span><span style="color: #007700">-&gt;</span><span style="color: #0000BB">toJson</span><span style="color: #007700">();&nbsp;<br /></span></code></div></div></div><br />
Kode di atas akan mengembalikan data sebagai json.<br />
<br />
---<br />
<br />
Fluent adalah sebuah utiliti class yang disediakan oleh Laravel sendiri agar kita dapat secara luwes mengolah data.]]></content:encoded>
		</item>
	</channel>
</rss>