Conectando-se ao servidor Microsoft SQL usando Python


97

Estou tentando me conectar ao SQL por meio de python para executar algumas consultas em alguns bancos de dados SQL no servidor Microsoft SQL. De minha pesquisa online e neste fórum, a biblioteca mais promissora parece ser a pyodbc. Então eu fiz o seguinte código

import pyodbc
conn = pyodbc.connect(init_string="driver={SQLOLEDB}; server=+ServerName+; 
database=+MSQLDatabase+; trusted_connection=true")
cursor = conn.cursor()

e obter o seguinte erro

Traceback (most recent call last):
  File "C:\Users...\scrap.py", line 3, in <module>
    conn = pyodbc.connect(init_string="driver={SQLOLEDB}; server=+ServerName+; database=+MSQLDatabase+; trusted_connection=true")
pyodbc.Error: ('IM002', '[IM002] [Microsoft][ODBC Driver Manager] Data source name not found and no default driver specified (0) (SQLDriverConnect)')

Eu olhei os posts a seguir e tentei mudar meu driver para {sql server} e me conectei usando links ODBC antes no SAS, que é parcialmente o que meu código acima é baseado, então não acho que eu preciso instalar mais nada.

pyodbc.Error: ('IM002', '[IM002] [unixODBC] [Gerenciador de Driver] Nome da fonte de dados não encontrado e nenhum driver padrão especificado (0) (SQLDriverConnect)')

Pyodbc - "Nome da fonte de dados não encontrado e nenhum driver padrão especificado"

obrigado

Respostas:


144

É assim que eu faço ...

import pyodbc 
cnxn = pyodbc.connect("Driver={SQL Server Native Client 11.0};"
                      "Server=server_name;"
                      "Database=db_name;"
                      "Trusted_Connection=yes;")


cursor = cnxn.cursor()
cursor.execute('SELECT * FROM Table')

for row in cursor:
    print('row = %r' % (row,))

Recursos relevantes:


60

Pequeno acréscimo ao que foi dito antes. Você provavelmente deseja retornar um dataframe. Isso seria feito como

import pypyodbc 
import pandas as pd

cnxn = pypyodbc.connect("Driver={SQL Server Native Client 11.0};"
                        "Server=server_name;"
                        "Database=db_name;"
                        "uid=User;pwd=password")
df = pd.read_sql_query('select * from table', cnxn)

38

Nas conexões de fonte de dados entre um cliente e um servidor, existem dois tipos gerais: ODBC que usa um DRIVER e OLEDB que usa um PROVIDER. E, no mundo da programação, é um debate regular sobre qual caminho seguir para se conectar às fontes de dados.

Você está usando um provedor SQLOLEDB, mas especificando-o como um driver. Pelo que eu sei, nem os módulos pyodbc nem pypyodbc oferecem suporte a conexões OLEDB do Windows. No entanto, o adodbapi faz o que usa o Microsoft ADO como um componente subjacente.

Abaixo estão as duas abordagens para seus parâmetros de conexão. Além disso, eu formato string suas variáveis, pois sua concatenação não quebrou as aspas dentro da string. Você notará que dobro as chaves, pois é necessário na string de conexão e string.format()também o usa.

# PROVIDER
import adodbapi
conn = adodbapi.connect("PROVIDER=SQLOLEDB;Data Source={0};Database={1}; \
       trusted_connection=yes;UID={2};PWD={3};".format(ServerName,MSQLDatabase,username,password))
cursor = conn.cursor()

# DRIVER
import pyodbc
conn = pyodbc.connect("DRIVER={{SQL Server}};SERVER={0}; database={1}; \
       trusted_connection=yes;UID={2};PWD={3}".format(ServerName,MSQLDatabase,username,password))
cursor = conn.cursor()

Obrigado pela explicação e código que fiz o driver funcionar. Porém tive que me livrar do .format (...) e colocar as variáveis ​​nos devidos lugares. O que o formato deveria fazer?
Christopher Ell

1
Você precisa instalar adodbapipara usar a conexão OLEDB. E o formato de string é a maneira recomendada de passar variáveis ​​para uma string em vez de usar o +operador. As chaves com números são marcadores de posição que são format()preenchidos de acordo. Você pode até mesmo passar listas e tuplas usando format(). Seu código original não quebrou string e variáveis ​​entre aspas, então +foi considerado parte da string.
Parfait

4
Embora essa resposta seja ótima e tenha me ajudado a resolver o problema. quem quer que esteja tentando fazer isso, lembre-se de que você pode obter uma exceção se definir conexão confiável = sim e inserir o UID / pwd na mesma string de conexão. Esta é uma combinação ou / ou e quando você usa uma conexão confiável, sua credencial do NT / sistema é usada para autenticação, mesmo se você estiver mencionando explicitamente o UID / PWD.
S4nd33p



4

Tente usar o pytds, ele funciona em ambientes mais complexos pyodbce mais fáceis de configurar.

Eu fiz funcionar no Ubuntu 18.04

Ref: https://github.com/denisenkom/pytds

Exemplo de código na documentação:

import pytds
with pytds.connect('server', 'database', 'user', 'password') as conn:
    with conn.cursor() as cur:
        cur.execute("select 1")
        cur.fetchall()

1
Obrigado. Funciona perfeitamente sem qualquer configuração complexa.
Shubham Patel

3

Seguir o código Python funcionou para mim. Para verificar a conexão ODBC, primeiro criei um aplicativo de console C # de 4 linhas conforme listado abaixo.

Código Python

import pandas as pd
import pyodbc 
cnxn = pyodbc.connect("Driver={SQL Server};Server=serverName;UID=UserName;PWD=Password;Database=RCO_DW;")
df = pd.read_sql_query('select TOP 10 * from dbo.Table WHERE Patient_Key > 1000', cnxn)
df.head()

Chamando um procedimento armazenado

 dfProcResult = pd.read_sql_query('exec dbo.usp_GetPatientProfile ?', cnxn, params=['MyParam'] )

Programa C # para verificar a conexão ODBC

    static void Main(string[] args)
    {
        string connectionString = "Driver={SQL Server};Server=serverName;UID=UserName;PWD=Password;Database=RCO_DW;";
        OdbcConnection cn = new OdbcConnection(connectionString);
        cn.Open();
        cn.Close();
    }

0

Uma abordagem alternativa seria instalar o driver ODBC 13 da Microsoft e substituí-lo SQLOLEDBporODBC Driver 13 for SQL Server

Saudações.


0

aqui está o que funciona para mim:

from sqlalchemy import create_engine
import urllib

conn_str = (
r'Driver=ODBC Driver 13 for SQL Server;'
r'Server=DefinitelyNotProd;'
r'Database=PlayPen;'
r'Trusted_Connection=Yes;')

quoted_conn_str = urllib.parse.quote_plus(conn_str)
engine = create_engine('mssql+pyodbc:///?odbc_connect={}'.format(quoted_conn_str))

0

Encontrei recursos atualizados aqui: Microsoft | SQL Docs | Driver Python SQL

Existem essas duas opções explicadas, incluindo todos os pré-requisitos necessários e exemplos de código: Driver Python SQL - pyodbc (testado e funcionando) Driver Python SQL - pymssql


Olá - Bem-vindo ao Stack Overflow - você deve tentar abordar a questão com algumas idéias (novas idéias neste caso) - Parte do seu próprio código ou uma nova abordagem. Em seguida, use alguns links para fornecer mais ajuda ou fazer backup de sua solução. Você não deve apenas postar alguns links.
Alex Leo

0

Minha versão. Espero que ajude.


import pandas.io.sql
import pyodbc
import sys

server = 'example'
db = 'NORTHWND'
db2 = 'example'

#Crear la conexión
conn = pyodbc.connect('DRIVER={SQL Server};SERVER=' + server +
                      ';DATABASE=' + db +
                      ';DATABASE=' + db2 +
                      ';Trusted_Connection=yes')
#Query db
sql = """SELECT [EmployeeID]
      ,[LastName]
      ,[FirstName]
      ,[Title]
      ,[TitleOfCourtesy]
      ,[BirthDate]
      ,[HireDate]
      ,[Address]
      ,[City]
      ,[Region]
      ,[PostalCode]
      ,[Country]
      ,[HomePhone]
      ,[Extension]
      ,[Photo]
      ,[Notes]
      ,[ReportsTo]
      ,[PhotoPath]
  FROM [NORTHWND].[dbo].[Employees] """
data_frame = pd.read_sql(sql, conn)
data_frame

0

Tentei conectar o sql server das seguintes maneiras e funcionou para mim.

Para conectar usando a autenticação do Windows

import pyodbc

conn = pyodbc.connect('Driver={SQL Server};Server='+servername+';Trusted_Connection=yes;Database='+databasename+';')
cursor = conn.cursor()
cursor.execute("Select 1 as Data")

Para usar a autenticação de servidor sql, usei o seguinte código.

import pyodbc

conn = pyodbc.connect('Driver={SQL Server};Server='+servername+  ';UID='+userid+';PWD='+password+';Database='+databasename) 
cursor1 = conn.cursor()
cursor1.execute("SELECT 1 AS DATA")

0

Experimente com pymssql:pip install pymssql

import pymssql

try:
    conn = pymssql.connect(server="host_or_ip", user="your_username", password="your_password", database="your_db")
    cursor = conn.cursor()
    cursor.execute ("SELECT @@VERSION")
    row = cursor.fetchone()
    print(f"\n\nSERVER VERSION:\n\n{row[0]}")
    cursor.close()
    conn.close()
except Exception:
    print("\nERROR: Unable to connect to the server.")
    exit(-1)

Resultado:

SERVER VERSION:

Microsoft SQL Server 2016 (SP2-CU14) (KB4564903) - 13.0.5830.85 (X64)
        Jul 31 2020 18:47:07
        Copyright (c) Microsoft Corporation
        Standard Edition (64-bit) on Windows Server 2012 R2 Standard 6.3 <X64> (Build 9600: ) (Hypervisor)

A conexão também pode ser verificada no terminal, com uma única linha de código com sqlcmd. Veja a sintaxe .

╔═════════╦═════════════════════════════════════════╗
 Command                Description               
╠═════════╬═════════════════════════════════════════╣
   -S     [protocol:]server[instance_name][,port] 
   -U     login_id                                
   -p     password                                
   -Q     "cmdline query" (and exit)              
╚═════════╩═════════════════════════════════════════╝
sqlcmd -S "host_or_ip"  -U "your_username" -p -Q "SELECT @@VERSION"

resultado:

Password:    your_password



--------------------------------------------------------------------------------------------------------------------------------------------------------
Microsoft SQL Server 2016 (SP2-CU14) (KB4564903) - 13.0.5830.85 (X64) 
        Jul 31 2020 18:47:07 
        Copyright (c) Microsoft Corporation
        Standard Edition (64-bit) on Windows Server 2012 R2 Standard 6.3 <X64> (Build 9600: ) (Hypervisor)


(1 rows affected)

Network packet size (bytes): 4096
1 xact[s]:
Clock Time (ms.): total         1  avg   1.00 (1000.00 xacts per sec.)
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.