Kommentar
Åtkomst till den här sidan kräver auktorisering. Du kan prova att logga in eller ändra kataloger.
Åtkomst till den här sidan kräver auktorisering. Du kan prova att ändra kataloger.
Diagnostisera och lösa vanliga problem när du använder mssql-python-drivrutinen för att ansluta till SQL Server, Azure SQL Database, Azure SQL Managed Instance och SQL database i Microsoft Fabric.
Installationsproblem
Pip-installationen misslyckas eller byggs från källkoden
Symtom:
error: Microsoft Visual C++ 14.0 or greater is required
ERROR: Failed building wheel for mssql-python
Möjliga orsaker och lösningar:
Ingen förbyggd wheel för din plattform
- Kontrollera att du kör en stödd Python-version (3.10 och senare versioner) och plattform. Se Supportlivscykel för kompatibilitetsmatrisen . Uppgradera pip innan du installerar med
pip install --upgrade pip. För repeterbara teammiljöer, använd det låsta arbetsflödet i Repeatable deployments eller container-mönstren i Container- och lokal utveckling för att minska lokal maskindrift.
- Kontrollera att du kör en stödd Python-version (3.10 och senare versioner) och plattform. Se Supportlivscykel för kompatibilitetsmatrisen . Uppgradera pip innan du installerar med
Virtuell miljö aktiverad ej
- Aktivera din virtuella miljö först. Att installera Python i systemet kan orsaka behörighetsfel eller konflikter.
python -m venv .venv .venv\Scripts\activate pip install mssql-python
-
Saknade Linux-systembibliotek
- Drivrutinen kräver en liten uppsättning systembibliotek på Linux. Se Plattformsspecifika beroenden för vilka paket som ska installeras.
Motstridiga installationer av drivrutiner
Symtom:
Importfel eller oväntat beteende efter installation av mssql-python tillsammans med pyodbc i samma miljö.
Lösningen
mssql-python och pyodbc kan samexistera. Om du ser konflikter, skapa en ren virtuell miljö:
python -m venv .venv --clear
.venv\Scripts\activate
pip install mssql-python
Anslutningsproblem
Kan inte ansluta till servern
Symtom:
OperationalError: [08001] (0) Client unable to establish connection
Möjliga orsaker och lösningar:
Server är inte tillgänglig
- Verifiera att servernamnet och porten är korrekta.
- Kontrollera nätverksanslutningen:
ping servernameellertelnet servername 1433. - Se till att brandväggen tillåter utgående anslutningar på port 1433.
SQL Server körs inte
- Verifiera att SQL Server-tjänsten har startats.
- För namngivna instanser, kontrollera att SQL Server Browser-tjänsten körs.
Azure SQL firewall rules
- Lägg till din klient-IP i Azure SQL-brandväggsreglerna i Azure-portalen.
- För Azure SQL Managed Instance, se till att du ansluter från ett tillåtet nätverk.
# Test basic connectivity
import socket
try:
sock = socket.create_connection(("<server>.database.windows.net", 1433), timeout=5)
print("TCP connection successful")
sock.close()
except Exception as e:
print(f"Cannot reach server: {e}")
Inloggningen misslyckades
Symtom:
OperationalError: [28000] (18456) Login failed for user 'username'.
Möjliga orsaker och lösningar:
Missanpassning i autentiseringsläge
- För Azure SQL Database, Azure SQL Managed Instance och SQL database in Fabric, föredra ett Microsoft Entra-läge såsom
Authentication=ActiveDirectoryDefault. - Om du medvetet använder SQL-autentisering, kontrollera att servern tillåter det och att du använder rätt inloggningsformat för den endpointen.
- För Azure SQL Database, Azure SQL Managed Instance och SQL database in Fabric, föredra ett Microsoft Entra-läge såsom
Felaktiga SQL-autentiseringsuppgifter
- Verifiera användarnamn och lösenord.
- För Azure SQL, inkludera det fullständiga användarnamnet:
username@servername.
Användaren existerar inte i databasen
- Verifiera att användaren har tillgång till den angivna databasen.
- Kontrollera om inloggningen är mappad till en databasanvändare.
Autentisering ej konfigurerad
- Använd Microsoft Entra-autentisering (rekommenderas):
Authentication=ActiveDirectoryDefault. - Om du felsöker en lokal SQL Server som borde acceptera SQL-autentisering, kontrollera att SQL Server använder mixed mode-autentisering.
- Använd Microsoft Entra-autentisering (rekommenderas):
Tidsgräns för anslutning
Symtom:
OperationalError: [HYT00] (0) Timeout expired
OperationalError: [HYT01] (0) Connection timeout expired
Möjliga orsaker och lösningar:
Servern är långsam att svara
- Öka tidsgränsen för anslutningen:
conn = mssql_python.connect(connection_string, timeout=60)Nätverksfördröjning
- Kolla nätverksvägen till servern.
- Överväg att använda en kortare nätverksväg eller VPN.
Server under hög belastning
- Försök att ansluta under lågtrafiktid.
- Kontakta din databasadministratör.
SSL-certifikatfel
Symtom:
OperationalError: [08001] SSL Provider: The certificate chain was issued by an authority that is not trusted
Lösningar:
För det första, föredra ett betrodd certifikat eller lokala utvecklingsmönster i Container och lokal utveckling. Använd TrustServerCertificate=yes endast för lokal utveckling mot en server som du kontrollerar.
För utveckling och testning med ett självsignerat certifikat:
conn = mssql_python.connect(
"Server=<server>.database.windows.net;"
"Database=<database>;"
"Authentication=ActiveDirectoryDefault;"
"Encrypt=yes;"
"TrustServerCertificate=yes;" # Don't use in production
)
Caution
TrustServerCertificate=yes är en endast lokal reservlösning. Ta inte med det in i delade devcontainers, CI-pipelines eller produktionsdistributioner. För bredare vägledning, se Kryptering och certifikat.
För produktion, se till att rätt certifikat installeras och använd:
conn = mssql_python.connect(
"Server=<server>.database.windows.net;"
"Database=<database>;"
"Authentication=ActiveDirectoryDefault;"
"Encrypt=yes;"
"HostnameInCertificate=<server>.domain.com;"
)
Problem med frågeexekvering
Tabell eller objekt hittades ej
Symtom:
ProgrammingError: [42S02] (208) Invalid object name 'TableName'.
Möjliga orsaker och lösningar:
Fel databaskontext
# Ensure you're connected to the correct database cursor.execute("SELECT DB_NAME()") print(cursor.fetchone()[0])Schema ej specificerat
# Use fully qualified name cursor.execute("SELECT * FROM dbo.TableName")Tabellen finns inte
# Check if table exists cursor.execute(""" SELECT TABLE_NAME FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_NAME = 'TableName' """)
Syntaxfel
Symtom:
ProgrammingError: [42000] (102) Incorrect syntax near '...'.
Lösningar:
Testa SQL i SSMS först för att verifiera syntaxen
Kontrollera escaping av strängar – använd parametriserade frågor:
# Wrong - vulnerable to syntax issues and SQL injection cursor.execute(f"SELECT * FROM Production.Product WHERE Name = '{name}'") # Correct - use parameters cursor.execute("SELECT * FROM Production.Product WHERE Name = %(name)s", {"name": name})
Parameterfel
Symtom:
ProgrammingError: [07001] Wrong number of parameters
Lösningar:
Räkna platshållare och parametrar – de måste matcha
Välj rätt parameterstil:
# Qmark style - positional cursor.execute("SELECT * FROM Production.Product WHERE ProductID = ? AND Name LIKE ?", (1, "Adjustable%")) print(cursor.fetchone()) # Pyformat style - named cursor.execute("SELECT * FROM Production.Product WHERE ProductID = %(id)s AND Name LIKE %(name)s", {"id": 1, "name": "Adjustable%"}) print(cursor.fetchone())
Datatypproblem
Fel vid konvertering av datum och tid
Symtom:
DataError: [22007] Invalid datetime format
Lösningar:
Använd Python datetime-objekt istället för strängar:
from datetime import datetime
cursor.execute("CREATE TABLE #Events (EventDate DATETIME)")
# Wrong - this raises an error for invalid dates
try:
cursor.execute("INSERT INTO #Events (EventDate) VALUES (%(event_date)s)", {"event_date": "2024-13-45"})
except Exception as e:
print(f"Expected error: {e}")
# Correct - use Python datetime objects
cursor.execute("INSERT INTO #Events (EventDate) VALUES (%(event_date)s)", {"event_date": datetime(2024, 3, 15)})
cursor.execute("SELECT EventDate FROM #Events")
print(cursor.fetchone())
Decimalprecisionsproblem
Symtom:
Siffror visas avkortade eller avrundade felaktigt.
Lösningar:
Användning decimal.Decimal för exakta numeriska värden:
from decimal import Decimal
cursor.execute("CREATE TABLE #PriceDemo (ListPrice DECIMAL(10,2))")
# Preserve full precision
cursor.execute(
"INSERT INTO #PriceDemo (ListPrice) VALUES (%(list_price)s)",
{"list_price": Decimal("19.99")}
)
Unicode-kodningsproblem
Symtom:
Specialtecken verkar osammanhängande eller orsakar fel.
Lösningar:
Använd NVARCHAR-kolumner för Unicode-data i din databas
Skicka strängar direkt – drivrutinen hanterar teckenkodningen:
cursor.execute("CREATE TABLE #UnicodeDemo (Name NVARCHAR(50))") cursor.execute("INSERT INTO #UnicodeDemo (Name) VALUES (%(name)s)", {"name": "日本語"}) cursor.execute("SELECT Name FROM #UnicodeDemo") print(cursor.fetchone())
Prestandaproblem
Långsam frågeexekvering
Möjliga orsaker och lösningar:
Saknade index: Kontrollera frågeexekveringsplanen i SSMS.
Stora resultatmängder: Använd
fetchmany()istället förfetchall():cursor.arraysize = 1000 while True: rows = cursor.fetchmany() if not rows: break process_rows(rows)Anslutningspoolning inaktiverad: Aktivera anslutningspoolning:
import mssql_python mssql_python.pooling(max_size=20, idle_timeout=300)
Minnesproblem med stora resultat
Symtom:
Python-processen får slut på minne.
Lösningar:
Strömresultat istället för att ladda in allt i minnet:
cursor.execute("SELECT * FROM LargeTable") for row in cursor: # Iterates one row at a time process_row(row)Använd serverside-paginering:
page_size = 1000 offset = 0 while True: cursor.execute( "SELECT * FROM LargeTable ORDER BY ID " "OFFSET ? ROWS FETCH NEXT ? ROWS ONLY", (offset, page_size) ) rows = cursor.fetchall() if not rows: break process_rows(rows) offset += page_size
Transaktionsproblem
Temporär tabellscoping med autocommit
Tillfälliga tabeller (#tablename) som skapas i en transaktion försvinner när transaktionen rullas tillbaka. Detta är en vanlig källa till förvirring när autocommit är avstängt (standardinställningen):
conn = mssql_python.connect(connection_string) # autocommit=False by default
cursor = conn.cursor()
cursor.execute("CREATE TABLE #TempData (ID INT, Name NVARCHAR(50))")
cursor.execute("INSERT INTO #TempData VALUES (1, 'test')")
# If the connection rolls back (explicit or on error), #TempData disappears
conn.rollback()
# This fails: Invalid object name '#TempData'
cursor.execute("SELECT * FROM #TempData")
Fix: Verkställ direkt efter att du skapat en temporär tabell, eller använd autocommit-läge:
cursor.execute("CREATE TABLE #TempData (ID INT, Name NVARCHAR(50))")
conn.commit() # Lock in the table definition
cursor.execute("INSERT INTO #TempData VALUES (1, 'test')")
conn.commit()
DDL-satser som kräver autocommit mode, såsom CREATE DATABASE, misslyckas inom en öppen transaktion. Ställ in autocommit innan du kör dem:
conn.autocommit = True
cursor.execute("CREATE DATABASE TestDB")
conn.autocommit = False
Transaktion som inte är genomförd
Symtom:
Dataändringar kvarstår inte efter att anslutningen stängts.
Solution:
Med autocommit=False (standard) måste du anropa commit():
cursor.execute("CREATE TABLE #Products (Name NVARCHAR(100))")
cursor.execute("INSERT INTO #Products (Name) VALUES (%(name)s)", {"name": "Widget"})
conn.commit() # Don't forget this!
Eller använd autocommit-läget:
conn = mssql_python.connect(connection_string, autocommit=True)
Dödlägesfel
Symtom:
OperationalError: [40001] (1205) Transaction ... was deadlocked on lock resources with another process
Solution:
Omprovlogik (se Ompröva logik) hanterar det omedelbara felet, men återkommande deadlocks indikerar ett designproblem. För att åtgärda grundorsaken, fånga deadlock-grafen och analysera vilka satser och låstyper som är involverade. Vanliga lösningar inkluderar omordningsoperationer så att konkurrerande transaktioner får lås i samma sekvens, minska transaktionsomfattningen och lägga till lämpliga index för att minska låsets varaktighet.
För en fullständig genomgång av deadlock-analys, se Deadlocks-guiden. Om du använder Azure SQL Database, se Analysera och förhindra deadlocks.
Bulklastproblem
Begränsningsbrott under bulkkopiering
Symtom:
RuntimeError: CHECK constraint ... Conflict occurred in database ...
RuntimeError: Cannot insert duplicate key ... violation of PRIMARY KEY constraint
Orsak:
Data i din batch bryter mot tabellbegränsningar (primärnyckel, unik, CHECK eller främmande nyckel).
Lösningen
Validera data innan du laddar. För stora datamängder, läs först in dem i en mellantabell och sammanfoga dem sedan med måltabellen:
# Load into staging, then validate
cursor.execute("CREATE TABLE ##Staging (ID INT, Name NVARCHAR(100))")
cursor.bulkcopy("##Staging", rows)
# Check for duplicates before merging
cursor.execute("""
SELECT s.ID FROM ##Staging s
INNER JOIN dbo.Target t ON s.ID = t.ID
""")
dupes = cursor.fetchall()
if dupes:
print(f"Skipping {len(dupes)} duplicate rows")
# Insert only non-duplicate rows
cursor.execute("""
INSERT INTO dbo.Target (ID, Name)
SELECT s.ID, s.Name FROM ##Staging s
WHERE NOT EXISTS (SELECT 1 FROM dbo.Target t WHERE t.ID = s.ID)
""")
conn.commit()
För upsert-mönster med stagingtabeller, se Data loading and movement patterns.
Fel vid kolumnmappning
Symtom:
RuntimeError: Bulk copy failure - column count mismatch
Orsak:
Antalet kolumner i din data stämmer inte överens med måltabellens kolumnantal, eller så är kolumnerna i fel ordning.
Lösningen
Se till att dina data matchar tabellschemat exakt i ordning och antal:
# Check the target table schema
cursor.execute("""
SELECT COLUMN_NAME, DATA_TYPE
FROM INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_NAME = 'MyTable'
ORDER BY ORDINAL_POSITION
""")
for col in cursor.fetchall():
print(col)
# Match your data to the column order
rows = [
(1, "Widget", Decimal("19.99")), # Must match table column order
(2, "Gadget", Decimal("29.99")),
]
cursor.bulkcopy("dbo.MyTable", rows)
Typkonflikter vid bulkkopiering
Symtom:
Data läses in men värdena är avkortade, avrundade eller felaktiga.
Orsak:
Python-värden mappas inte rent till målkolumntyperna. Vanliga fall: float värden laddade i decimal kolumner (precisionsförlust), eller överdimensionerade strängar laddade i kolumner med fast längd.
Lösningen
Använd rätt Python-typer som matchar ditt schema:
from decimal import Decimal
# Use Decimal for decimal/numeric columns, not float
rows = [
(1, "Widget", Decimal("19.99")), # Correct
# (1, "Widget", 19.99), # Avoid: float loses precision
]
cursor.bulkcopy("dbo.Products", rows)
Fel vid typbindning i NumPy
Symtom:
Parametrar fallerar tyst eller utlöser datatypfel när NumPy-heltals- eller flyttalstyper används.
Orsak:
NumPy-typer som numpy.int64 och numpy.int32 klarar inte isinstance(x, int) i NumPy 2.x. Förarens typinferens känner inte igen dem, vilket orsakar oväntat beteende.
Lösningen
Konvertera numpy-värden till inbyggda Python-typer innan bindning:
import numpy as np
# Convert individual values
cursor.execute("SELECT * FROM Production.Product WHERE ProductID = %(product_id)s", {"product_id": int(np.int64(42))})
# Convert DataFrame values
for _, row in df.iterrows():
cursor.execute(
"INSERT INTO #Orders (ProductID, Qty) VALUES (%(product_id)s, %(qty)s)",
{"product_id": int(row["ProductID"]), "qty": int(row["Qty"])}
)
För större datamängder bör du i stället använda integrationsalternativen Arrow eller pandas, som hanterar typkonvertering internt.
Bulkkopiering med tillfälliga tabeller
Symtom:
cursor.bulkcopy("#TempTable", data) höjer RuntimeError: Invalid object name '#TempTable'.
Orsak:
bulkcopy() Kan inte lösa sessionstemptabeller (#tablename) på grund av begränsningar i metadatauppslag. Globala tillfälliga tabeller (##tablename) och permanenta tabeller fungerar.
Lösningen
Använd en global temptabell eller en vanlig staging-tabell:
# Global temp table (visible to all sessions, dropped when last session disconnects)
cursor.execute("CREATE TABLE ##Staging (ID INT, Name NVARCHAR(50))")
cursor.bulkcopy("##Staging", rows)
# Or use a permanent staging table
cursor.execute("CREATE TABLE dbo.Staging (ID INT, Name NVARCHAR(50))")
cursor.bulkcopy("dbo.Staging", rows)
För små dataset där en sessionstemptabell föredras, använd executemany() istället:
cursor.execute("CREATE TABLE #Staging (ID INT, Name NVARCHAR(50))")
cursor.executemany("INSERT INTO #Staging (ID, Name) VALUES (?, ?)", rows)
Container- och CI-problem
Saknade systembibliotek på Linux
Symtom:
ImportError: libltdl.so.7: cannot open shared object file: No such file or directory
ImportError: libkrb5.so.3: cannot open shared object file
Lösningen
Installera de nödvändiga systempaketen. Paketen skiljer sig åt beroende på fördelning:
| Distribution | Installationskommando |
|---|---|
| Ubuntu/Debian | sudo apt-get install libltdl7 libkrb5-3 libgssapi-krb5-2 |
| Red Hat / Fedora | sudo dnf install libtool-ltdl krb5-libs |
| Alpine | apk add libltdl krb5-libs |
För exempel på Dockerfile, se Container och lokal utveckling.
macOS SSL-fel efter installation
Symtom:
SSL-relaterade fel när man ansluter från macOS, särskilt på Apple Silicon.
Lösningen
Installera OpenSSL via Homebrew och sätt länkarflaggorna:
brew install openssl
export LDFLAGS="-L/opt/homebrew/opt/openssl/lib"
export CPPFLAGS="-I/opt/homebrew/opt/openssl/include"
Diagnosverktyg
Aktivera drivrutinsloggning
Använd mssql_python.setup_logging() för att aktivera omfattande DEBUG-loggning för felsökning. Alla drivrutinsoperationer loggas, inklusive SQL-satser, parametrar, interna ODBC-operationer och ändringar i anslutningstillstånd.
import mssql_python
# Enable logging to file (default)
mssql_python.setup_logging()
# Output to stdout (useful for CI/CD and containers)
mssql_python.setup_logging(output='stdout')
# Output to both file and stdout
mssql_python.setup_logging(output='both')
# Custom log file path (must use .txt, .log, or .csv extension)
mssql_python.setup_logging(log_file_path="/var/log/myapp/mssql.log")
Loggfiler skrivs i CSV-format och roterar automatiskt vid 512 MB med fem säkerhetskopior. Känslig data som lösenord och åtkomsttokens saneras automatiskt i loggutdata.
För att lägga till egna loggposter tillsammans med drivrutinsloggar, använd driver_logger:
from mssql_python.logging import driver_logger
mssql_python.setup_logging()
driver_logger.debug("[App] Starting data processing")
driver_logger.error("[App] Failed to process record")
# Your entries appear in the same file with the same format
Caution
Loggning medför prestandapåverkan. Aktivera det endast vid felsökning, inte i produktion som standard.
Få information om föraren
Hämta drivrutinsversionen och serverdetaljer från en aktiv anslutning:
import mssql_python
conn = mssql_python.connect(connection_string)
# Driver version
print(f"Version: {mssql_python.__version__}")
# Server information
print(f"Server name: {conn.getinfo(mssql_python.SQL_SERVER_NAME)}")
print(f"Database name: {conn.getinfo(mssql_python.SQL_DATABASE_NAME)}")
Kontrollera anslutningstillstånd
Testa om en anslutning fortfarande är öppen innan du försöker operationer:
try:
cursor = conn.cursor()
cursor.execute("SELECT 1")
print("Connection is open")
except mssql_python.Error:
print("Connection is closed or broken")
Snabb referens: Vanliga fel
| Error | SQLSTATE | Vanlig orsak | Snabbåtgärd |
|---|---|---|---|
| Klient kan inte upprätta anslutning | 08001 | Servern kan inte nås | Kontrollera servernamn/port |
| Inloggningen misslyckades | 28000 | Felaktiga inloggningsuppgifter | Verifiera användarnamn/lösenord |
| Tidsgränsen har upphört att gälla | HYT00/HYT01 | Långsamt nätverk | Öka tidsgräns |
| Ogiltigt objektnamn | 42S02 | Felaktig tabell/felaktigt schema | Använd fullt kvalificerade namn |
| Syntaxfel | 42000 | SQL-fel | Använda parametriserade frågor |
| Begränsningsfel | 23000 | FK/PK-överträdelse | Kontrollera dataintegriteten |
| Dödläge | 40001 | Låskonflikt | Försök igen, analysera sedan deadlock-grafen |