Katakanlah bahwa situs yang digunakan pengguna Anda ditulis dalam Joomla, tetapi untuk membuat produk baru untuk audiens Anda, Anda memilih bundel Python / Django.
Akibatnya, Anda perlu menggunakan akun pengguna dari database Joomla di Django.
Masalahnya, bagaimanapun, adalah bahwa Joomla dan Django menggunakan algoritma hashing kata sandi yang berbeda, jadi hanya menyalin akun gagal.
Setelah membaca dokumentasi Django, stack overflow dan menghabiskan waktu, saya mendapatkan solusi yang dijelaskan di bawah ini, yang menggunakan praktik pengembangan yang disarankan untuk Django secara maksimal.
Peringatan
Solusi arsitektur ini mungkin tidak cocok untuk Anda, lihat diskusi di komentar .
Untuk memahami apa yang terjadi dalam contoh di bawah ini, Anda harus memiliki pemahaman tentang arsitektur Django.
Saya juga berasumsi bahwa Anda tahu cara menggunakan proyek Django, jadi saya tidak menjelaskan proses ini.
Kode disalin dari proyek yang berfungsi, tetapi akan mudah untuk menyesuaikan dengan proyek Anda dengan minimum perubahan.
Mungkin, dalam versi utama Django berikutnya, kode ini dapat rusak, namun, prinsip solusinya akan tetap sama.
Dalam panduan ini, saya tidak menjelaskan ujung depan sistem otorisasi, karena:
- apa front-end yang Anda miliki akan tergantung pada kebutuhan proyek Anda (bahkan mungkin titik akhir Json API, misalnya)
- informasi ini sudah dijelaskan dalam tutorial resmi Django dan berbagai artikel pemula
Algoritma
- sambungkan database Joomla (DB) ke proyek Django
- buat model JoomlaUser yang mewakili pengguna dari database Joomla
- tulis fungsi
check_joomla_password()
yang memverifikasi bahwa kata sandi yang dimasukkan cocok dengan kata sandi asli pengguna. - tambahkan backend otorisasi baru "Joomla Auth Backend" ke proyek, yang, ketika mengotorisasi klien di Django, akan mendapatkan akun pengguna dari database Joomla
1. Koneksi ke database Joomla:
Jika perlu, dalam file yang sama dengan pengaturan proyek, Anda dapat mengaktifkan pencatatan permintaan basis data:
2. buat model JoomlaUser
- Baca bagaimana model Django dapat menggunakan database yang ada
- Pikirkan tentang di mana menempatkan JoomlaUser baru.
Dalam proyek saya, saya membuat aplikasi yang disebut "pengguna" ( manage.py startapp users
). Ini akan berisi backend otorisasi dan model pengguna Joomla. - buat model secara otomatis menggunakan inspectdb:
python manage.py inspectdb live_users --database="joomla_db"
joomla_db - nama database yang Anda tentukan di settings.py/DATABASES
;
live_users - nama tabel dengan akun.
tambahkan model Anda ke users/models.py
:
class JoomlaUser(models.Model): """ Represents our customer from the legacy Joomla database. """ username = models.CharField(max_length=150, primary_key=True) email = models.CharField(max_length=100) password = models.CharField(max_length=100)
Selanjutnya, kita perlu memastikan bahwa model akan mengakses database yang benar. Untuk melakukan ini, tambahkan proyek router untuk permintaan ke database yang berbeda , yang akan mengarahkan permintaan dari model JoomlaUser ke database asli.
Buat file "db_routers.py" di folder utama proyek (di tempat yang sama dengan "settings.py" Anda):
daftarkan router baru di settings.py
:
Sekarang Anda bisa mendapatkan akun dari basis data lama.
Luncurkan terminal Django dan coba tarik pengguna yang sudah ada: python manage.py shell
>>> from users.models import JoomlaUser >>> print(JoomlaUser.objects.get(username='someuser')) JoomlaUser object (someusername) >>>
Jika semuanya berfungsi (Anda melihat pengguna), maka lanjutkan ke langkah berikutnya. Jika tidak, lihat output kesalahan dan koreksi pengaturan.
3. Verifikasi Kata Sandi Akun Joomla
Joomla tidak menyimpan kata sandi pengguna, tetapi hash mereka, misalnya
$2y$10$aoZ4/bA7pe.QvjTU0R5.IeFGYrGag/THGvgKpoTk6bTz6XNkY0F2e
Dimulai dengan Joomla v3.2, kata sandi pengguna dienkripsi menggunakan algoritma BLOWFISH .
Jadi saya mengunduh kode python dengan algoritma ini:
pip install bcrypt echo bcrypt >> requirements.txt
Dan membuat fungsi untuk memeriksa kata sandi di file users/backend.py
:
def check_joomla_password(password, hashed): """ Check if password matches the hashed password, using same hashing method (Blowfish) as Joomla >= 3.2 If you get wrong results with this function, check that the Hash starts from prefix "$2y", otherwise it is probably not a blowfish hash :return: True/False """ import bcrypt if password is None: return False
Perhatian! Versi Joomla lebih rendah dari 3,2 menggunakan metode hashing yang berbeda (md5 + garam), jadi fungsi ini tidak akan berfungsi. Dalam hal ini, baca
diskusi tentang Stackoverflow dan buat fungsi pemeriksaan hash yang terlihat seperti ini:
Sayangnya, saya tidak memiliki basis pengguna dari versi lama Joomla, jadi saya tidak dapat menguji fitur ini untuk Anda.
4. Backend otorisasi pengguna Joomla
Sekarang Anda siap membuat backend Django untuk mengesahkan pengguna dari proyek Joomla.
baca cara memodifikasi sistem otorisasi Django
Daftarkan backend baru (belum ada) di project/settings.py
:
AUTHENTICATION_BACKENDS = [
Buat backend otorisasi pengguna Joomla di users/backend.py
from django.contrib.auth.models import User from .models import JoomlaUser def check_joomla_password(password, hashed):
Ringkasan
Selamat - sekarang pengguna situs Joomla Anda yang ada dapat menggunakan kredensial mereka di situs / aplikasi baru.
Sebagai otorisasi pengguna aktif melalui antarmuka baru, mereka akan disalin satu per satu ke dalam basis data baru.
Atau, Anda mungkin tidak ingin menyalin entitas pengguna dari sistem lama ke yang baru.
Dalam hal ini, inilah tautan ke artikel yang menjelaskan cara mengganti model pengguna default dengan Anda sendiri di Django (model JoomlaUser dijelaskan di atas).
Keputusan akhir, apakah atau tidak untuk mentransfer pengguna, dibuat berdasarkan hubungan di mana proyek-proyek baru dan lama akan. Misalnya, di mana pendaftaran pengguna baru berlangsung, situs / aplikasi mana yang akan menjadi yang utama, dll.
Pengujian dan dokumentasi
Sekarang tolong tambahkan tes dan dokumentasi yang sesuai yang mencakup kode baru. Logika solusi ini terkait erat dengan arsitektur Django dan tidak terlalu jelas, jadi jika Anda tidak melakukan tes / dokumentasi sekarang, dukungan untuk proyek akan menjadi lebih rumit di masa depan.