Selama ini program Python yang kita tulis berjalan di komputer sendiri: input datang dari keyboard, output muncul di terminal. Web application membalik skema tersebut — kode Python berjalan terus-menerus di sebuah server, menunggu permintaan dari browser pengguna di mana pun berada. Pada chapter ini kita akan membedah apa yang sebenarnya terjadi antara klik pengguna dan halaman yang tampil, dan di titik mana web framework seperti Flask, Django, dan FastAPI membantu.
Siklus Request dan Response #
Seluruh komunikasi web berjalan lewat protokol HTTP dengan pola yang selalu sama: browser mengirim request, server membalas dengan response. Detail protokol ini sudah kita bahas tuntas pada chapter HTTP Request dan Response di Section Networking dan HTTP; di sini kita fokus pada posisi kode Python di dalam siklus tersebut.
Setiap klik tautan atau submit formulir memicu satu putaran penuh diagram di atas. Response selalu terdiri dari tiga bagian: status (misalnya 200 untuk sukses atau 404 untuk tidak ditemukan), header (metadata seperti Content-Type), dan body (isi HTML, JSON, atau file).
Apa yang Dikerjakan Web Framework #
Membuat server HTTP bisa dilakukan dengan standard library Python, tanpa framework apa pun. Kode berikut benar-benar berfungsi — dan sekaligus memperlihatkan mengapa framework tetap diperlukan:
import threading
import urllib.request
from http.server import BaseHTTPRequestHandler, ThreadingHTTPServer
class HaloHandler(BaseHTTPRequestHandler):
def do_GET(self):
body = "Halo dari server Python murni!".encode("utf-8")
self.send_response(200)
self.send_header("Content-Type", "text/plain; charset=utf-8")
self.send_header("Content-Length", str(len(body)))
self.end_headers()
self.wfile.write(body)
def log_message(self, format, *args):
pass # matikan log akses agar contoh tetap bersih
server = ThreadingHTTPServer(("127.0.0.1", 8000), HaloHandler)
thread = threading.Thread(target=server.serve_forever, daemon=True)
thread.start()
response = urllib.request.urlopen("http://127.0.0.1:8000/")
print("Status:", response.status)
print("Content-Type:", response.headers["Content-Type"])
print("Isi:", response.read().decode("utf-8"))
server.shutdown()
print("Server berhenti.")Output yang Dihasilkan:
Status: 200
Content-Type: text/plain; charset=utf-8
Isi: Halo dari server Python murni!
Server berhenti.Mari kita telaah peran setiap bagian kode di atas:
- Baris 6 (
class HaloHandler(...)): classHaloHandlermewarisiBaseHTTPRequestHandlerdan menangani request dengan metodeGET. - Baris 8 (
body = ...): teks respons dikonversi menjadibyteskarena protokol HTTP mengirim data mentah, bukan string. - Baris 9-12 (
self.send_response(200)sampaiself.end_headers()): handler menyusun status200dan dua header secara manual, satu per satu. - Baris 13 (
self.wfile.write(body)): body akhirnya ditulis ke koneksi. - Baris 20-21 (
ThreadingHTTPServer…thread.start()): server dijalankan di thread terpisah agar kode setelahnya tetap dieksekusi. - Baris 23-26 (
urllib.request.urlopen…):urllibberperan sebagai klien yang mengirim request dan mencetak hasilnya.
Satu halaman statis saja sudah menuntut belasan baris. Bayangkan menambahkan rute lain, parsing formulir, session, hingga koneksi database — semuanya manual. Web framework mengambil alih pekerjaan rutin tersebut:
- Routing: memetakan URL seperti
/produk/7ke fungsi Python yang tepat. - Parsing request: mengekstrak query string, form data, dan body JSON menjadi struktur data Python.
- Membangun response: menyusun status, header, dan body dari nilai kembalian fungsi.
Frontend dan Backend #
| Lapisan | Teknologi | Dijalankan di | Tugas utama |
|---|---|---|---|
| Frontend | HTML, CSS, JavaScript | Browser pengguna | tampilan dan interaksi |
| Backend | Python + framework | Server | logika, data, keamanan |
Browser tidak pernah mengeksekusi kode Python; browser hanya menerima HTML, CSS, dan JavaScript dari server. Kode Python kita berada sepenuhnya di sisi backend — menerima request, mengolah data, lalu mengirim response kembali.
Statelessness, Cookie, dan Session #
HTTP bersifat stateless: setiap request berdiri sendiri, dan server tidak mengingat request sebelumnya. Lalu bagaimana website “ingat” bahwa kita sudah login? Jawabannya ada di header Set-Cookie. Ketika pengguna berhasil login, server menyisipkan pengenal acak pada response:
HTTP/1.1 200 OK
Set-Cookie: sesi=abc123Browser menyimpan cookie tersebut lalu mencantumkannya otomatis pada setiap request berikutnya:
GET /keranjang HTTP/1.1
Host: example.com
Cookie: sesi=abc123Di sisi server, framework menyimpan data login pada struktur bernama session yang pengenalnya cocok dengan cookie. Mekanisme inilah yang membuat fitur “sudah login” dan “isi keranjang” mungkin terwujud tanpa melanggar sifat stateless HTTP.
Sekilas Menuju Deployment #
Selama pengembangan, framework menjalankan development server yang ringan tetapi lambat dan tidak aman. Saat aplikasi diterbitkan, kode framework justru tidak berhadapan langsung dengan internet — ada satu lapisan lagi bernama server aplikasi (misalnya gunicorn untuk WSGI, uvicorn untuk ASGI) yang bertugas menerima koneksi dan meneruskannya ke kode Python kita. Arsitektur lengkap ini akan kita praktikkan pada Section Packaging dan Deployment, khususnya chapter Deployment Aplikasi Web. Untuk sekarang, cukup pahami bahwa menjalankan aplikasi web di produksi melibatkan lebih dari satu komponen.