Catatan
Akses ke halaman ini memerlukan otorisasi. Anda dapat mencoba masuk atau mengubah direktori.
Akses ke halaman ini memerlukan otorisasi. Anda dapat mencoba mengubah direktori.
Artikel ini menyediakan panduan untuk memigrasikan aplikasi Django dari PostgreSQL, MySQL, atau SQLite ke SQL Server menggunakan mssql-django backend.
Overview
ORM Django mengabstraksi sebagian besar perbedaan database, tetapi beberapa perilaku dan dialek SQL bervariasi di antara backend. Panduan ini mencakup perbedaan utama yang Anda temui saat bermigrasi ke SQL Server.
Langkah 1: Instal mssql-django
mssql-django Instal paket dan dependensinya:
pip install mssql-django
Pastikan Driver Microsoft ODBC untuk SQL Server diinstal. Lihat Menginstal mssql-django untuk instruksi khusus platform.
Langkah 2: Memperbarui DATABASE konfigurasi
Ganti konfigurasi database Anda yang sudah ada di settings.py:
# Example: From PostgreSQL
# DATABASES = {
# "default": {
# "ENGINE": "django.db.backends.postgresql",
# "NAME": "mydb",
# },
# }
# To SQL Server
DATABASES = {
"default": {
"ENGINE": "mssql",
"NAME": "<your-database>",
"USER": "<your-username>",
"PASSWORD": "<your-password>",
"HOST": "<your-server>",
"PORT": "1433",
"OPTIONS": {
"driver": "ODBC Driver 18 for SQL Server",
},
},
}
Langkah 3: Membuat migrasi baru
Mulailah dengan riwayat migrasi yang bersih untuk SQL Server:
# Remove existing migration files (keep __init__.py)
# Then regenerate
python manage.py makemigrations
python manage.py migrate
Important
Transfer data Anda menggunakan migrasi data atau proses ETL terpisah. Jangan mencoba menjalankan file migrasi PostgreSQL atau MySQL terhadap SQL Server.
Perbedaan utama dari PostgreSQL
| Fitur | PostgreSQL | SQL Server (mssql-django) |
|---|---|---|
| Pertambahan otomatis | SERIAL / BIGSERIAL |
IDENTITY(1,1) |
| Jenis Boolean | Bawaan boolean |
bit (0 atau 1) |
| Bidang teks |
text (tidak terbatas) |
nvarchar(max) |
| Dukungan JSON | Native jsonb |
nvarchar(max) dengan fungsi JSON (SQL Server 2016+) |
| Bidang array | ArrayField |
Tidak didukung. Gunakan tabel terkait atau JSON. |
| Bidang HStore | HStoreField |
Tidak didukung. Gunakan JSONField sebagai gantinya. |
| Bidang rentang |
IntegerRangeField,BigIntegerRangeField,DateRangeField,DateTimeRangeField |
Tidak didukung. Gunakan dua bidang terpisah. |
| Pencarian teks lengkap |
SearchVector, SearchRank |
Gunakan SQL mentah dengan SQL Server pencarian teks lengkap. |
DISTINCT ON |
Didukung | Tidak didukung. Gunakan GROUP BY atau subkueri. |
DateTimeField dengan zona waktu |
timestamp with time zone |
datetimeoffset (ketika USE_TZ=True) atau datetime2 |
Fitur khusus PostgreSQL yang perlu diganti
Jika kode Anda menggunakan fitur khusus PostgreSQL dari django.contrib.postgres, ganti:
# PostgreSQL ArrayField - replace with JSONField or related table
# Before
from django.contrib.postgres.fields import ArrayField
tags = ArrayField(models.CharField(max_length=50))
# After (using JSONField)
tags = models.JSONField(default=list)
# PostgreSQL HStoreField - replace with JSONField
# Before
from django.contrib.postgres.fields import HStoreField
metadata = HStoreField()
# After
metadata = models.JSONField(default=dict)
Perbedaan utama dari MySQL
| Fitur | MySQL | SQL Server (mssql-django) |
|---|---|---|
| Inkrementasi otomatis | AUTO_INCREMENT |
IDENTITY(1,1) |
| Jenis Boolean | tinyint(1) |
bit |
| Bidang teks | longtext |
nvarchar(max) |
| Dukungan JSON |
JSON Asli (5.7 dan yang lebih baru) |
nvarchar(max) dengan fungsi JSON |
| Collation | Dapat dikonfigurasi per kolom | Tingkat instans atau database (ditimpa dengan opsi COLLATE) |
DateTimeField |
datetime(6) | datetimeoffset atau datetime2 |
Perbedaan utama dari SQLite
| Fitur | SQLite | SQL Server (mssql-django) |
|---|---|---|
| Penerapan tipe | Pengetikan fleksibel | Penegakan jenis yang ketat |
| Penulisan serentak | Limited | Dukungan konkurensi penuh |
| Koneksi maksimum | Praktis 1 penulis | Pengumpulan koneksi dengan banyak koneksi bersamaan |
DateTimeField |
Disimpan sebagai teks | datetimeoffset atau datetime2 |
Perbedaan kolasi
Kolasi menentukan cara SQL Server membandingkan dan mengurutkan teks. Ini adalah salah satu sumber perilaku tak terduga yang paling umum saat bermigrasi dari PostgreSQL atau MySQL.
Peka huruf besar/kecil
Kolasi bawaan SQL Server (SQL_Latin1_General_CP1_CI_AS) tidak peka terhadap huruf besar/kecil. PostgreSQL peka terhadap huruf besar/kecil secara bawaan.
Perilaku ini berarti bahwa setelah migrasi, kueri yang sebelumnya dibedakan antara "Smith" dan "smith" memperlakukannya sebagai sama:
# On PostgreSQL: returns only exact case matches
# On SQL Server (default collation): returns both "Smith" and "smith"
User.objects.filter(last_name="Smith")
Jika aplikasi Anda bergantung pada perbandingan peka huruf besar/kecil, Anda memiliki dua opsi:
Ubah basis data atau kolasi kolom menjadi varian yang peka terhadap huruf besar/kecil:
-- Database-level (affects all new columns) ALTER DATABASE [<your-database>] COLLATE Latin1_General_CS_AS; -- Column-level (for specific columns) ALTER TABLE [<your-table>] ALTER COLUMN [<column-name>] NVARCHAR (150) COLLATE Latin1_General_CS_AS;Gunakan lookup Django
__exactdengan penggantian kolasi dalam SQL mentah untuk kueri yang ditargetkan secara spesifik.
Sensitivitas aksen
Kolasi bawaan SQL Server peka aksen (AS), yang sesuai dengan perilaku PostgreSQL. Karakter seperti é dan e diperlakukan berbeda. Jika Anda memerlukan perbandingan yang tidak peka terhadap aksen, gunakan kolasi yang berakhiran _AI.
Mengonfigurasi kolase dalam mssql-django
Ubah kolasi bawaan untuk pencarian field teks dalam konfigurasi basis data Anda:
DATABASES = {
"default": {
"ENGINE": "mssql",
"NAME": "<your-database>",
"OPTIONS": {
"driver": "ODBC Driver 18 for SQL Server",
"collation": "Latin1_General_CS_AS", # Case-sensitive
},
},
}
Note
Opsi collation dalam mssql-django mengatur kolasi yang digunakan dalam LIKE dan operasi perbandingan yang dihasilkan oleh lookups ORM Django. Ini tidak mengubah kolatasi kolom yang ada dalam database. Untuk mengubah kolasi kolom tersimpan, gunakan pernyataan ALTER TABLE / ALTER COLUMN. Untuk informasi selengkapnya, lihat dokumentasi kolasi SQL Server.
Langkah 4: Memperbarui SQL kustom
Jika kode Anda berisi SQL mentah, perbarui untuk sintaks SQL Server:
# PostgreSQL syntax
# cursor.execute("SELECT * FROM products LIMIT 10 OFFSET 20")
# SQL Server syntax
cursor.execute("SELECT * FROM products ORDER BY id OFFSET 20 ROWS FETCH NEXT 10 ROWS ONLY")
Perbedaan sintaks SQL umum:
| Pengoperasian | PostgreSQL/MySQL | SQL Server |
|---|---|---|
| Membatasi hasil | LIMIT 10 |
TOP 10 atau OFFSET ... FETCH NEXT ... |
| Penggabungan string |
\|\| (PG) / CONCAT() |
+ atau CONCAT() |
| Literal Boolean | TRUE / FALSE |
1 / 0 |
| Tanda waktu saat ini | NOW() |
GETDATE(), SYSDATETIME(), atau SYSDATETIMEOFFSET() untuk nilai sadar zona waktu |
| JIKA TIDAK ADA | CREATE TABLE IF NOT EXISTS |
Periksa sys.objects atau gunakan IF NOT EXISTS |
Perbedaan isolasi transaksi
PostgreSQL menggunakan MVCC (Kontrol Konkurensi Multi-Versi) untuk tingkat isolasinya READ COMMITTED . Pembaca tidak pernah memblokir penulis dan penulis tidak pernah memblokir pembaca.
default SQL Server READ COMMITTED menggunakan penguncian, yang berarti kueri baca dapat terblokir saat menunggu transaksi tulis selesai. Jika aplikasi Anda mengalami peningkatan pemblokiran setelah migrasi, pertimbangkan untuk mengaktifkan READ COMMITTED SNAPSHOT pada basis data:
ALTER DATABASE [<your-database>]
SET READ_COMMITTED_SNAPSHOT ON;
Ini mengubah SQL Server READ COMMITTED agar menggunakan pembuatan versi baris (mirip dengan MVCC PostgreSQL) alih-alih mekanisme penguncian. Pembaca melihat versi terakhir dari sebuah baris yang telah dikomit tanpa menunggu proses tulis yang aktif.
Note
READ COMMITTED SNAPSHOT memerlukan ruang tambahan tempdb untuk versi baris. Uji dengan beban yang realistis sebelum menerapkannya di lingkungan produksi. Untuk informasi selengkapnya, lihat Manajemen transaksi di mssql-django.
Langkah 5: Memigrasikan data
Strategi migrasi data bergantung pada ukuran himpunan data:
Himpunan data kecil (<500 MB)
Gunakan Django:dumpdata/loaddata
# On the source database
python manage.py dumpdata --natural-foreign --natural-primary -o data.json
# Switch settings.py to SQL Server, then:
python manage.py migrate
python manage.py loaddata data.json
Himpunan data besar (>500 MB)
Untuk migrasi besar, gunakan alat khusus untuk menghindari kehabisan memori dan masalah batas waktu. ORM Django bukanlah alat yang tepat untuk beban massal pada skala ini. Lewati untuk pemindahan data dan biarkan Django mengelola skema dan logika aplikasi setelahnya.
| Tool | Paling cocok untuk |
|---|---|
| Wizard Impor dan Ekspor SQL Server | Migrasi on-premises ke on-premises dengan GUI |
| Azure Data Factory | Sumber apa pun untuk Azure SQL, termasuk skenario hibrid |
| Layanan Migrasi Basis Data Azure | Migrasi skala besar dengan validasi dan rollback bawaan |
| mssql-python salinan massal dengan Apache Arrow | Alur Python kustom yang membutuhkan throughput maksimum antara database SQL Server, Azure SQL Database, dan SQL di Fabric |
Validasi pascamigrasi
Setelah migrasi, validasi konsistensi benih identitas untuk kolom peningkatan otomatis:
-- Check identity seed and current value for all tables
SELECT
TABLE_NAME,
IDENT_SEED(TABLE_SCHEMA + '.' + TABLE_NAME) AS IdentitySeed,
IDENT_INCR(TABLE_SCHEMA + '.' + TABLE_NAME) AS IdentityIncrement,
IDENT_CURRENT(TABLE_SCHEMA + '.' + TABLE_NAME) AS CurrentIdentity
FROM INFORMATION_SCHEMA.TABLES
WHERE TABLE_TYPE = 'BASE TABLE'
AND OBJECTPROPERTY(OBJECT_ID(TABLE_SCHEMA + '.' + TABLE_NAME), 'TableHasIdentity') = 1
ORDER BY TABLE_NAME;
Jika CurrentIdentity melebihi IdentitySeed + record_count, lakukan penyemaian ulang:
DBCC CHECKIDENT ('your_table', RESEED, new_seed);