Kursus Python / Menghubungkan MariaDB dengan PyMySQL dan transaksi
Python terhubung ke MariaDB melalui driver database dan mengirim nilai SQL terpisah dari teks pernyataannya. Latihan ini memakai PyMySQL untuk menyimpan satu record dengan transaksi dan membaca hasilnya kembali. Berbeda dari SQLite tertanam, MariaDB memerlukan server aktif, database, dan akun aplikasi tersendiri.
Menyiapkan server lokal dan akun khusus
Siapkan MariaDB lokal yang terpisah dari data pekerjaan. Melalui koneksi administrator, jalankan SQL berikut setelah memastikan nama database serta akun belum dipakai. Jika sudah ada, pahami kegunaannya dan pilih nama latihan lain; jangan menimpa atau menghapus objek yang tidak dikenal. Ganti password contoh dengan rahasia lokal yang benar.
CREATE DATABASE python_lab CHARACTER SET utf8mb4;
CREATE USER 'python_app'@'127.0.0.1' IDENTIFIED BY 'replace-with-a-local-secret';
CREATE TABLE python_lab.expenses (
id BIGINT PRIMARY KEY AUTO_INCREMENT,
external_id VARCHAR(64) NOT NULL UNIQUE,
name VARCHAR(100) NOT NULL,
amount BIGINT NOT NULL CHECK(amount >= 0)
) ENGINE=InnoDB;
GRANT SELECT, INSERT, UPDATE ON python_lab.expenses TO 'python_app'@'127.0.0.1';
Akun python_app dibatasi untuk SELECT, INSERT, dan UPDATE pada satu tabel. Administrator hanya dipakai menyiapkan skema, sedangkan program Python memakai akun aplikasi. Tabel menggunakan InnoDB untuk transaksi; constraint menolak jumlah negatif. Nilai pada latihan adalah jumlah integer dalam satuan KRW.
Host akun adalah 127.0.0.1 karena program memakai TCP ke alamat itu. Akun dengan host localhost belum tentu sama dengan akun tersebut. Periksa layanan server, port, host akun, password, lalu hak tabel secara berurutan ketika koneksi atau operasi ditolak. Jangan mengatasi hak tabel yang kurang dengan memberi akses seluruh server.
Memasang driver dan memasukkan rahasia
Aktifkan lingkungan virtual proyek dan pasang driver:
python -m pip install PyMySQL
Program membaca MARIADB_USER dan MARIADB_PASSWORD dari lingkungan proses. Jangan menyimpan nilai rahasia dalam kode, commit, atau log. Mengetik password sebagai bagian perintah shell dapat menyimpannya di riwayat. Siapkan mariadb_demo.py pada bagian berikut sebelum menjalankan contoh sesi terminal ini.
Pada Windows PowerShell, masukkan password tersembunyi lalu bersihkan variabel setelah selesai:
$env:MARIADB_USER = "python_app"
$secret = Read-Host "MariaDB password" -AsSecureString
$credential = New-Object System.Net.NetworkCredential("", $secret)
$env:MARIADB_PASSWORD = $credential.Password
python mariadb_demo.py
Remove-Item Env:MARIADB_PASSWORD
Remove-Item Env:MARIADB_USER
Remove-Variable secret, credential
Pada Bash di macOS atau Ubuntu, gunakan variabel sesi shell:
export MARIADB_USER=python_app
read -r -s -p "MariaDB password: " MARIADB_PASSWORD
printf "\n"
export MARIADB_PASSWORD
python mariadb_demo.py
unset MARIADB_PASSWORD MARIADB_USER
Jika server latihan memakai port selain 3306, tetapkan MARIADB_PORT pada sesi yang sama dengan nilainya yang benar dan bersihkan setelah selesai. Variabel lingkungan diteruskan ke proses anak; cara ini tidak memberi perlindungan yang sama dengan penyimpanan rahasia khusus. Pastikan sesi dan lokasi file latihan sesuai sebelum menjalankan program.
Contoh ditujukan ke localhost. Untuk server jarak jauh, rancang TLS yang memverifikasi CA dan identitas host menggunakan konfigurasi server serta opsi driver yang sesuai. Mengubah alamat saja tidak mempertahankan asumsi koneksi lokal. Lihat opsi koneksi PyMySQL untuk pengaturan dan timeout.
Menjalankan koneksi dan penyimpanan lengkap
Simpan kode lengkap berikut sebagai mariadb_demo.py dengan UTF-8 pada folder latihan baru. Gunakan Python 3.12 atau lebih baru dan lingkungan yang berisi PyMySQL.
import os
import pymysql
con = pymysql.connect(
host="127.0.0.1", port=int(os.environ.get("MARIADB_PORT", "3306")),
user=os.environ["MARIADB_USER"], password=os.environ["MARIADB_PASSWORD"],
database="python_lab", charset="utf8mb4", autocommit=False,
connect_timeout=5, read_timeout=5, write_timeout=5,
)
try:
try:
with con.cursor() as cur:
cur.execute("INSERT INTO expenses(external_id,name,amount) VALUES(%s,%s,%s) ON DUPLICATE KEY UPDATE name=VALUES(name), amount=VALUES(amount)", ("demo-1", "lunch", 8000))
con.commit()
except Exception:
con.rollback()
raise
with con.cursor() as cur:
cur.execute("SELECT name,amount FROM expenses WHERE external_id=%s", ("demo-1",))
print(cur.fetchone())
finally:
con.close()
Setelah server, tabel, akun, dan variabel sesi siap, jalankan:
python mariadb_demo.py
Hasil normal adalah ('lunch', 8000). Kolom external_id yang unik menyebabkan eksekusi ulang memperbarui record demo-1, bukan menambah transaksi kedua. id adalah kunci internal otomatis; identitas eksternal menentukan transaksi contoh yang diperbarui. Jika ID sumber berbeda, jangan menggabungkan transaksi hanya karena nama dan jumlah sama.
Program membuka koneksi dengan autocommit dimatikan. Setelah INSERT atau UPDATE selesai, commit() menyimpan perubahan. Jika exception terjadi pada bagian penulisan, rollback() dipanggil dan exception diteruskan. Pembacaan berikutnya memeriksa hasil yang tersimpan, sementara finally menutup koneksi pada jalur setelah koneksi berhasil dibuat.
Jika connect() sendiri gagal, variabel koneksi belum terbentuk dan program tidak memasuki blok pembersihan setelahnya. Kegagalan membaca hasil sesudah commit juga tidak membatalkan commit yang sudah selesai. Bedakan kegagalan penyimpanan, kegagalan pembacaan, dan keadaan yang hasil akhirnya belum pasti sebelum memutuskan mencoba ulang.
Memeriksa parameter, rollback, dan hak akses
PyMySQL memakai placeholder %s untuk nilai string maupun angka. Berikan tuple nilai sebagai argumen execute, bukan memakai interpolasi Python % atau f-string. Nama tabel dan kolom merupakan struktur SQL; jika perlu dinamis, pilih dari daftar yang dikendalikan. Panduan contoh PyMySQL memperlihatkan pemisahan parameter dan commit.
- Jalankan contoh dua kali dan periksa bahwa external_id demo-1 tetap satu record dengan jumlah 8000.
- Ubah hanya jumlah pada tuple masukan menjadi 9000, jalankan, dan pastikan record yang sama diperbarui. Setelah itu, coba -1: constraint harus menolak dan jumlah 9000 sebelumnya tetap tersimpan.
- Pakai password yang salah pada sesi uji, periksa kegagalan autentikasi, lalu pulihkan pengaturan yang benar. Jangan menampilkan nilai password ketika mencatat hasil.
- Periksa operasi yang diizinkan dengan akun aplikasi. Akun contoh tidak memiliki DELETE; kegagalan operasi di luar haknya harus tetap ditolak. Gunakan hanya data latihan untuk percobaan hak akses.
- Kembalikan tuple ke lunch dan 8000, jalankan kembali, lalu bersihkan variabel sesi sesuai shell yang digunakan.
Nilai yang mengandung tanda kutip harus tetap diperlakukan sebagai data oleh pengikatan parameter. Ini tidak menggantikan aturan bisnis seperti panjang nama, rentang jumlah yang lebih sempit, atau format external_id. Kebijakan pembaruan mengikuti INSERT ON DUPLICATE KEY UPDATE MariaDB.
Rollback database tidak membatalkan permintaan jaringan atau perubahan file yang sudah dilakukan di luar transaksi. Hubungan antara exception dan pembersihan dibahas dalam penanganan exception, sedangkan transaksi SQLite memperlihatkan prinsip serupa pada database tertanam. Pertahankan laporan kegagalan yang jelas agar proses lanjutan tidak menganggap transaksi berhasil hanya karena program pernah tersambung.




