<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: M K Wiro</title>
    <description>The latest articles on DEV Community by M K Wiro (@mkwcorp).</description>
    <link>https://dev.to/mkwcorp</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F4079260%2Fbb6590b7-4aa8-45e6-a568-4a73b60df46c.png</url>
      <title>DEV Community: M K Wiro</title>
      <link>https://dev.to/mkwcorp</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/mkwcorp"/>
    <language>en</language>
    <item>
      <title>Bikin Halaman Unduh OS-Aware &amp; Global dengan Tencent EdgeOne Pages (Studi Kasus BerQuran)</title>
      <dc:creator>M K Wiro</dc:creator>
      <pubDate>Sat, 15 Aug 2026 17:00:57 +0000</pubDate>
      <link>https://dev.to/mkwcorp/bikin-halaman-unduh-os-aware-global-dengan-tencent-edgeone-pages-studi-kasus-berquran-4jjj</link>
      <guid>https://dev.to/mkwcorp/bikin-halaman-unduh-os-aware-global-dengan-tencent-edgeone-pages-studi-kasus-berquran-4jjj</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;Pengalaman saya memakai &lt;strong&gt;Tencent EdgeOne Makers (Pages) + Edge Functions&lt;/strong&gt; untuk menyajikan halaman unduh aplikasi desktop yang otomatis mendeteksi OS dan lokasi pengunjung — berjalan di &lt;em&gt;edge&lt;/em&gt; global, gratis, dan hidup dalam hitungan menit.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;#TencentEdgeOne #EdgeOneMakers #CODEPOLITAN #EdgeOne&lt;/code&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  Latar belakang
&lt;/h2&gt;

&lt;p&gt;Saya mengembangkan &lt;strong&gt;&lt;a href="https://berquran.com" rel="noopener noreferrer"&gt;BerQuran&lt;/a&gt;&lt;/strong&gt; — aplikasi baca Al-Qur'an yang memverifikasi bacaan dari suara pengguna. Selain Android &amp;amp; iOS, BerQuran baru saja hadir untuk &lt;strong&gt;desktop&lt;/strong&gt;: macOS (&lt;code&gt;.dmg&lt;/code&gt;), Windows (&lt;code&gt;.zip&lt;/code&gt;), dan Linux (&lt;code&gt;AppImage&lt;/code&gt;), lengkap dengan &lt;strong&gt;auto-update&lt;/strong&gt; dan mesin pengenal yang berjalan &lt;strong&gt;on-device&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Masalah klasik halaman unduh multi-OS: pengunjung harus menebak sendiri file mana yang cocok, dan aset disajikan dari &lt;strong&gt;satu origin&lt;/strong&gt; (server saya di Indonesia) sehingga terasa jauh untuk pengguna global. Saya ingin halaman yang:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Otomatis menyodorkan installer yang tepat&lt;/strong&gt; sesuai OS pengunjung.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Cepat di mana pun&lt;/strong&gt; — disajikan dari &lt;em&gt;edge&lt;/em&gt; terdekat.&lt;/li&gt;
&lt;li&gt;Punya &lt;strong&gt;logika di server&lt;/strong&gt; (bukan cuma statis) tanpa saya mengelola server.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Jawabannya: &lt;strong&gt;Tencent EdgeOne Pages + Edge Functions&lt;/strong&gt;. Ini catatan pengalaman saya.&lt;/p&gt;

&lt;h2&gt;
  
  
  Apa itu EdgeOne Pages / Makers?
&lt;/h2&gt;

&lt;p&gt;EdgeOne Makers (Pages) adalah platform Tencent EdgeOne untuk men-&lt;em&gt;deploy&lt;/em&gt; web app langsung ke &lt;strong&gt;jaringan edge global&lt;/strong&gt; — mirip Cloudflare Pages/Workers. Yang saya pakai:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Static hosting&lt;/strong&gt; di edge (CDN global otomatis).&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Edge Functions&lt;/strong&gt;: kode serverless yang jalan di node edge &lt;strong&gt;dekat pengunjung&lt;/strong&gt; — bisa baca header lokasi &amp;amp; User-Agent, lalu merespons dinamis. Latensi rendah tanpa server sendiri.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Git-connected deploy&lt;/strong&gt;: connect repo GitHub → tiap &lt;code&gt;git push&lt;/code&gt; auto-deploy.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Yang saya bangun
&lt;/h2&gt;

&lt;p&gt;Sebuah proyek kecil tapi nyata:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;berquran-edge/
├─ index.html              # landing unduh (auto-detect OS via /api/latest)
└─ functions/
   └─ api/
      └─ latest.js         # Edge Function: deteksi OS + geo → installer yang tepat
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Edge Function-nya
&lt;/h3&gt;

&lt;p&gt;Di EdgeOne Pages, setiap file di &lt;code&gt;functions/&lt;/code&gt; otomatis jadi endpoint. &lt;code&gt;functions/api/latest.js&lt;/code&gt; menjadi &lt;code&gt;GET /api/latest&lt;/code&gt;. Isinya inti dari "kepintaran" halaman ini:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// functions/api/latest.js  (dipangkas)&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;VERSION&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1.7.1&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;BASE&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;https://cdn.berquran.com/berquran/download&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ASSETS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;macos&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;label&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;macOS&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;   &lt;span class="na"&gt;url&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;BASE&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;/BerQuran-macOS-&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;.dmg`&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="na"&gt;windows&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;label&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Windows&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;url&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;BASE&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;/BerQuran-windows-x64-&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;.zip`&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="na"&gt;linux&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;label&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Linux&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;   &lt;span class="na"&gt;url&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;BASE&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;/BerQuran-x86_64.AppImage`&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;

&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;detectOS&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;ua&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;''&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;ua&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ua&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;toLowerCase&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;ua&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;includes&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;windows&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;windows&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;ua&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;includes&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mac&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;macos&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;ua&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;includes&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;linux&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;ua&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;includes&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;x11&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;linux&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;macos&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;onRequest&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;context&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;request&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;context&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;os&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;detectOS&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;headers&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;user-agent&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;

  &lt;span class="c1"&gt;// ?go=1 → langsung redirect ke installer yang pas OS&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;URL&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;url&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;searchParams&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;go&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;Response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;redirect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;ASSETS&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;os&lt;/span&gt;&lt;span class="p"&gt;].&lt;/span&gt;&lt;span class="nx"&gt;url&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;302&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="c1"&gt;// request.eo → info edge (lokasi geografis pengunjung)&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;geo&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;eo&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;eo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;geo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="p"&gt;{};&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;Response&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;JSON&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;stringify&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="na"&gt;version&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;VERSION&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;detectedOS&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;os&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;recommended&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;ASSETS&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;os&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="na"&gt;all&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;ASSETS&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;edge&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;country&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;geo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;countryCodeAlpha2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;region&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;geo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;regionName&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;city&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;geo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;cityName&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;headers&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;content-type&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;application/json; charset=utf-8&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="p"&gt;});&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Dua hal penting yang saya suka:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;request.headers.get('user-agent')&lt;/code&gt;&lt;/strong&gt; untuk memilih installer — tak perlu library.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;request.eo.geo&lt;/code&gt;&lt;/strong&gt; memberi lokasi pengunjung &lt;strong&gt;di edge&lt;/strong&gt;, tanpa panggil API geo eksternal.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Langkah deploy (dari nol sampai live &amp;lt; 10 menit)
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;1. Siapkan repo.&lt;/strong&gt; Push &lt;code&gt;index.html&lt;/code&gt; + folder &lt;code&gt;functions/&lt;/code&gt; ke GitHub.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. Buat project di EdgeOne Makers.&lt;/strong&gt; Console EdgeOne → tab &lt;strong&gt;Makers&lt;/strong&gt; → &lt;strong&gt;Import Git repository&lt;/strong&gt; → pilih &lt;strong&gt;GitHub&lt;/strong&gt; → &lt;em&gt;Authorize&lt;/em&gt; aplikasi EdgeOne Pages → pilih repo.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;3. Konfigurasi.&lt;/strong&gt; Nama project, &lt;strong&gt;Acceleration region: Global (MLC excluded)&lt;/strong&gt; (edge internasional, tanpa perlu ICP filing China), branch &lt;code&gt;main&lt;/code&gt;. Situs statis → tak perlu build command. Klik &lt;strong&gt;Start deployment&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;4. Selesai.&lt;/strong&gt; Beberapa saat kemudian: &lt;code&gt;Initialize → Clone → Install → Build → Deploy&lt;/code&gt; semua hijau, dan dapat domain gratis: &lt;strong&gt;&lt;code&gt;https://berquran-edge.edgeone.dev&lt;/code&gt;&lt;/strong&gt;. Tiap &lt;code&gt;git push&lt;/code&gt; berikutnya auto-deploy.&lt;/p&gt;

&lt;h2&gt;
  
  
  Hasilnya — dan bukti ini benar-benar di &lt;em&gt;edge&lt;/em&gt;
&lt;/h2&gt;

&lt;p&gt;Halaman live: &lt;strong&gt;&lt;a href="https://berquran-edge.edgeone.dev" rel="noopener noreferrer"&gt;berquran-edge.edgeone.dev&lt;/a&gt;&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Yang bikin saya senyum: panggil &lt;code&gt;/api/latest&lt;/code&gt; dari perangkat berbeda, hasilnya beda sesuai OS — dan &lt;strong&gt;field &lt;code&gt;edge&lt;/code&gt; menunjukkan lokasi node edge yang melayani saya&lt;/strong&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;dari&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;laptop&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;saya&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;(Indonesia)&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"detectedOS"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"macos"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"recommended"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"label"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"macOS"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"url"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;".../BerQuran-macOS-1.7.1.dmg"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"edge"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"country"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ID"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"region"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Yogyakarta"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"city"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Kabupaten Sleman"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Ganti User-Agent jadi Windows → otomatis &lt;code&gt;recommended&lt;/code&gt; jadi installer &lt;code&gt;.zip&lt;/code&gt;. Inilah kekuatan Edge Function: &lt;strong&gt;logika personalisasi berjalan di node terdekat pengunjung&lt;/strong&gt;, bukan bolak-balik ke origin yang jauh. Halaman utamanya sendiri tinggal &lt;code&gt;fetch('/api/latest')&lt;/code&gt; lalu menonjolkan tombol unduh sesuai OS.&lt;/p&gt;

&lt;h2&gt;
  
  
  Benchmark: edge vs origin (angka nyata)
&lt;/h2&gt;

&lt;p&gt;Klaim "lebih cepat" harus dibuktikan. Saya ukur &lt;strong&gt;TTFB (Time To First Byte)&lt;/strong&gt; ke halaman edge (&lt;code&gt;berquran-edge.edgeone.dev&lt;/code&gt;) vs origin tunggal saya (&lt;code&gt;berquran.com&lt;/code&gt;, 1 server di Indonesia, tanpa CDN) dari &lt;strong&gt;5 kota di 4 benua&lt;/strong&gt;, memakai &lt;a href="https://globalping.io" rel="noopener noreferrer"&gt;Globalping&lt;/a&gt;.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Lokasi&lt;/th&gt;
&lt;th&gt;Origin (1 server, Indonesia)&lt;/th&gt;
&lt;th&gt;EdgeOne Edge (warm)&lt;/th&gt;
&lt;th&gt;Selisih&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;London 🇬🇧&lt;/td&gt;
&lt;td&gt;188 ms&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;26 ms&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;~7× lebih cepat&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;São Paulo 🇧🇷&lt;/td&gt;
&lt;td&gt;324 ms&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;49 ms&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;~6,6×&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Falkenstein 🇩🇪&lt;/td&gt;
&lt;td&gt;219 ms&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;44 ms&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;~5×&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Los Angeles 🇺🇸&lt;/td&gt;
&lt;td&gt;197 ms&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;55 ms&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;~3,6×&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Singapore 🇸🇬&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;22 ms&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;215 ms&lt;/td&gt;
&lt;td&gt;origin menang&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Rata-rata&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;190 ms&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;77 ms&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;~2,5×&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Dua pelajaran jujur dari benchmark ini:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Edge menang telak untuk pengunjung JAUH.&lt;/strong&gt; Dari Eropa &amp;amp; Amerika, edge 3,6–7× lebih cepat karena disajikan dari PoP terdekat, bukan menyeberang setengah bumi ke Indonesia. Untuk Singapura (tetangga Indonesia), origin justru menang — wajar, edge paling berguna untuk audiens global.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Ada "cold start".&lt;/strong&gt; Pengukuran PERTAMA saya ke edge yang belum pernah diakses sangat lambat (avg &lt;strong&gt;~1500 ms&lt;/strong&gt;, LA sempat 2,8 detik) karena node edge itu harus mengambil dari origin dulu. Setelah cache hangat (permintaan berikutnya), turun ke &lt;strong&gt;77 ms&lt;/strong&gt; rata-rata. Artinya: pengunjung pertama di suatu wilayah "membayar" pemanasan cache; sisanya menikmati kecepatan edge. Untuk aset penting, ini bisa diatasi dengan &lt;em&gt;prefetch&lt;/em&gt;/&lt;em&gt;cache warming&lt;/em&gt;.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Ini justru yang saya suka dari Edge Functions + edge cache: performanya bisa diukur, dan perilakunya (termasuk cold start) transparan.&lt;/p&gt;

&lt;h2&gt;
  
  
  Kesan &amp;amp; kenapa ini berguna nyata
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Cepat &amp;amp; global tanpa ribet.&lt;/strong&gt; Saya tak menyewa server atau atur CDN manual — cukup &lt;code&gt;git push&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Edge Functions = server-logic tanpa server.&lt;/strong&gt; Deteksi OS + geo yang biasanya butuh backend, kini jalan di edge dalam belasan baris.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Cocok untuk distribusi app.&lt;/strong&gt; Halaman unduh, feed auto-update, smart-redirect installer — semua diuntungkan latensi rendah edge.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Gratis untuk mulai&lt;/strong&gt; dan langsung dapat domain + HTTPS.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Untuk BerQuran, ini melengkapi sistem desktop yang baru saya bangun (3 OS + auto-update): sekarang pengguna dapat halaman unduh yang &lt;em&gt;pintar&lt;/em&gt; dan cepat di mana pun mereka berada.&lt;/p&gt;

&lt;p&gt;Repo: &lt;code&gt;github.com/mkwcorp88/berquran-edge&lt;/code&gt; · Live: &lt;code&gt;berquran-edge.edgeone.dev&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;code&gt;#TencentEdgeOne #EdgeOneMakers #CODEPOLITAN #EdgeOne&lt;/code&gt;&lt;/p&gt;

</description>
      <category>tencentedgeone</category>
      <category>edgeone</category>
      <category>webdev</category>
      <category>tutorial</category>
    </item>
  </channel>
</rss>
