Nota
O acesso a esta página requer autorização. Pode tentar iniciar sessão ou alterar os diretórios.
O acesso a esta página requer autorização. Pode tentar alterar os diretórios.
Este artigo fornece orientações para migrar aplicações Django do PostgreSQL, MySQL ou SQLite para o SQL Server usando o mssql-django backend.
Overview
O ORM do Django abstrai a maioria das diferenças nas bases de dados, mas alguns comportamentos e dialetos SQL variam entre backends. Este guia cobre as principais diferenças que encontra ao migrar para o SQL Server.
Passo 1: Instalar mssql-django
Instale o mssql-django pacote e as suas dependências:
pip install mssql-django
Certifique-se de que o driver Microsoft ODBC para SQL Server está instalado. Consulte Instalar mssql-django para instruções específicas da plataforma.
Passo 2: Atualizar DATABASE a configuração
Substitua a configuração existente da sua base de dados em 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",
},
},
}
Passo 3: Criar novas migrações
Comece com um histórico de migração limpo para o SQL Server:
# Remove existing migration files (keep __init__.py)
# Then regenerate
python manage.py makemigrations
python manage.py migrate
Importante
Transfira os seus dados usando uma migração de dados ou um processo ETL separado. Não tentes executar ficheiros de migração PostgreSQL ou MySQL contra o SQL Server.
Principais diferenças em relação ao PostgreSQL
| Característica | PostgreSQL | SQL Server (mssql-django) |
|---|---|---|
| Incremento automático | SERIAL / BIGSERIAL |
IDENTITY(1,1) |
| Tipo booleano | Nativo boolean |
bit (0 ou 1) |
| Campos de texto |
text (ilimitado) |
nvarchar(max) |
| Suporte a JSON | Nativo jsonb |
nvarchar(max) com funções JSON (SQL Server 2016+) |
| Campos de arrays | ArrayField |
Não suportado. Use uma tabela relacionada ou JSON. |
| Campos de HStore | HStoreField |
Não suportado. Utilize JSONField em substituição. |
| Campos de intervalo |
IntegerRangeField, BigIntegerRangeField, DateRangeField, DateTimeRangeField |
Não suportado. Usa dois campos separados. |
| Pesquisa em texto completo |
SearchVector, SearchRank |
Utilize SQL em bruto com a pesquisa de texto completo do SQL Server. |
DISTINCT ON |
Supported | Não suportado. Uso GROUP BY ou subconsultas. |
DateTimeField com fuso horário |
timestamp with time zone |
datetimeoffset (quando USE_TZ=True) ou datetime2 |
Funcionalidades específicas do PostgreSQL para substituir
Se o seu código utiliza funcionalidades específicas do PostgreSQL de django.contrib.postgres, substitua-as:
# 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)
Principais diferenças em relação ao MySQL
| Característica | MySQL | SQL Server (mssql-django) |
|---|---|---|
| Incremento automático | AUTO_INCREMENT |
IDENTITY(1,1) |
| Tipo booleano | tinyint(1) |
bit |
| Campos de texto | longtext |
nvarchar(max) |
| Suporte a JSON | Nativo JSON (5.7 e posteriores) |
nvarchar(max) com funções JSON |
| Collation | Configurável por coluna | Nível de instância ou de base de dados (pode ser substituído com a opção COLLATE) |
DateTimeField |
datahora(6) | datetimeoffset ou datetime2 |
Principais diferenças em relação ao SQLite
| Característica | SQLite | SQL Server (mssql-django) |
|---|---|---|
| Imposição de tipos | Tipagem flexível | Imposição estrita de tipos |
| Gravações simultâneas | Limitado | Suporte total de concorrência |
| Número máximo de ligações | Basicamente 1 escritor | Agrupamento de ligações com muitas ligações concorrentes |
DateTimeField |
Armazenado como texto | datetimeoffset ou datetime2 |
Diferenças de agrupamento
A Collation controla como o SQL Server compara e ordena o texto. Esta é uma das fontes mais comuns de comportamento inesperado ao migrar do PostgreSQL ou do MySQL.
Sensível às maiúsculas e minúsculas
A colação predefinida do SQL Server (SQL_Latin1_General_CP1_CI_AS) é insensível a maiúsculas e minúsculas. O PostgreSQL é sensível a maiúsculas minúsculas por defeito.
Este comportamento significa que, após a migração, as consultas que anteriormente distinguiam entre "Smith" e "smith" passam a tratá-los como iguais:
# On PostgreSQL: returns only exact case matches
# On SQL Server (default collation): returns both "Smith" and "smith"
User.objects.filter(last_name="Smith")
Se a sua aplicação depender de comparações que diferenciam maiúsculas de minúsculas, tem duas opções:
Altere o agrupamento da base de dados ou da coluna para uma variante sensível a maiúsculas e minúsculas:
-- 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;Use a operação de pesquisa do Django com uma sobrescrita de ordenação em SQL nativo para consultas específicas.
Sensibilidade ao sotaque
A colação padrão do SQL Server é sensível ao acento (AS), o que corresponde ao comportamento do PostgreSQL. Caracteres como é e e são tratados como diferentes. Se precisares de comparações insensíveis ao acento, usa uma colação que termina em _AI.
Configurar a colação no mssql-django
Substitui a ordenação predefinida das pesquisas em campos de texto na configuração da base de dados:
DATABASES = {
"default": {
"ENGINE": "mssql",
"NAME": "<your-database>",
"OPTIONS": {
"driver": "ODBC Driver 18 for SQL Server",
"collation": "Latin1_General_CS_AS", # Case-sensitive
},
},
}
Note
A opção collation em mssql-django controla a ordenação usada em LIKE e nas operações de comparação geradas pelas pesquisas do ORM do Django. Não altera a ordenação das colunas existentes na base de dados. Para alterar a ordenação armazenada da coluna, use instruções ALTER TABLE / ALTER COLUMN. Para mais informações, consulte a documentação de compilação do SQL Server.
Passo 4: Atualizar SQL personalizado
Se o seu código contém SQL bruto, atualize-o para a sintaxe do 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")
Diferenças comuns na sintaxe SQL:
| Operação | PostgreSQL/MySQL | SQL Server |
|---|---|---|
| Limitar resultados | LIMIT 10 |
TOP 10 ou OFFSET ... FETCH NEXT ... |
| Concatenação de cordas |
\|\| (PG) / CONCAT() |
+ ou CONCAT() |
| Literais booleanos | TRUE / FALSE |
1 / 0 |
| Carimbo de data/hora atual | NOW() |
GETDATE(), SYSDATETIME(), ou SYSDATETIMEOFFSET() para valores com reconhecimento de fuso horário |
| SE NÃO EXISTE | CREATE TABLE IF NOT EXISTS |
Verificar sys.objects ou usar IF NOT EXISTS |
Diferenças de isolamento de transações
O PostgreSQL utiliza MVCC (Multi-Version Concurrency Control) para o seu READ COMMITTED nível de isolamento. Os leitores nunca bloqueiam escritores e escritores nunca bloqueiam leitores.
A predefinição READ COMMITTED do SQL Server utiliza bloqueios, o que significa que as consultas de leitura podem ficar bloqueadas enquanto esperam que as transações de escrita sejam concluídas. Se a sua aplicação sofrer um aumento do bloqueio após a migração, considere ativar READ COMMITTED SNAPSHOT a base de dados:
ALTER DATABASE [<your-database>]
SET READ_COMMITTED_SNAPSHOT ON;
Isto faz com que o READ COMMITTED do SQL Server passe a utilizar o controlo de versões de linhas (semelhante ao MVCC do PostgreSQL) em vez de bloqueios. Os leitores veem a última versão comprometida de uma linha sem esperar por escritores ativos.
Note
READ COMMITTED SNAPSHOT requer espaço adicional tempdb para versões de linhas. Teste sob uma carga realista antes de ativar em ambiente de produção. Para mais informações, consulte Gestão de transações em mssql-django.
Passo 5: Migrar dados
A estratégia de migração de dados depende do tamanho do conjunto de dados:
Conjuntos de dados pequenos (<500 MB)
Utilize os dumpdata/loaddata do Django:
# 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
Grandes conjuntos de dados (>500 MB)
Para migrações grandes, utilize ferramentas especializadas para evitar esgotamento de memória e problemas de timeout. O ORM da Django não é a ferramenta certa para cargas em massa a esta escala. Ignora isso para a transferência de dados e deixa o Django gerir o esquema e a lógica da aplicação depois.
| Tool | Melhor para |
|---|---|
| Assistente de Importação e Exportação do SQL Server | Migrações on-premises para on-premises com interface gráfica |
| Fábrica de Dados do Azure | Qualquer fonte para SQL do Azure, incluindo cenários híbridos |
| Serviço de Migração de Banco de Dados do Azure | Migrações em grande escala com validação e rollback incorporados |
| mssql-python: cópia em massa com Apache Arrow | Pipelines Python personalizados que precisam de máximo rendimento entre SQL Server, Base de Dados SQL do Azure e SQL Database em Fabric |
Validação pós-migração
Após a migração, valide a consistência da semente de identidade para colunas de incremento automático:
-- 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;
Se CurrentIdentity for superior a IdentitySeed + record_count, reinicialize a propagação:
DBCC CHECKIDENT ('your_table', RESEED, new_seed);