PyODBC 17通过ActiveDirectoryPassword认证无法连接本地MSSQL 2019
根因说明
你碰到的空用户名18456登录错误,核心是两个问题:
- 认证模式用错了:
Authentication=ActiveDirectoryPassword是ODBC驱动专门给Azure云的Entra ID(原Azure AD)做的认证选项,根本不支持本地AD域环境下部署的MSSQL实例。在这个模式下驱动不会解析你传的DOMAIN\USER格式账号,也不会把UID正确传给SQL Server,服务端收到的用户名是空的,自然报登录失败。 - 连接字符串参数有冗余冲突:你加的
Trusted_Connection=no和本地域认证的逻辑不匹配,反而会干扰驱动的认证流程判断。
修复方案
适配本地部署MSSQL+本地AD域的场景
你本地搭的MSSQL2019集群用本地AD账号认证的话,直接删掉连接字符串里的Authentication=ActiveDirectoryPassword和Trusted_Connection=no两行即可,改完的连接字符串如下:
UID=<DOMAIN>\<USER>; PWD=<password>; Server=<server.url>; Driver={ODBC Driver 17 for SQL Server}; Database=<dbname>; TrustServerCertificate=yes;
驱动识别到DOMAIN\USER格式的UID和对应密码,会自动走NTLM认证,域账号信息会正确传递给SQL Server。如果反斜杠格式的账号还是报错,把UID换成UPN格式(即<USER>@<DOMAIN>.local)再试,早期Linux版ODBC驱动对反斜杠转义的处理有兼容问题。
注意用Python传参的时候,字符串里的反斜杠要做转义,要么写DOMAIN\\USER,要么直接用raw字符串r'DOMAIN\USER',避免反斜杠被Python解析成转义字符,导致实际传给驱动的账号格式不对。
改完可以先在容器里用sqlcmd直接测连通性,排除pyodbc层面的问题:
sqlcmd -S <server.url> -d <dbname> -U <DOMAIN>\<USER> -P '<password>' -C
sqlcmd能连通的话再调整pyodbc的代码即可。
额外检查项
- 确认容器内安装的ODBC Driver 17版本不低于17.2,早期17版本的Linux端域认证存在已知bug
- 确认容器DNS配置正确,能正常解析MSSQL实例域名、域控域名,且能连通域控的NTLM/Kerberos认证端口
- 确认MSSQL实例端开启了混合认证模式,没有禁用NTLM认证入口
如果你确实需要用ActiveDirectoryPassword模式
只有当你的MSSQL实例配置了Azure Entra ID认证(比如Azure SQL、Azure Arc托管的MSSQL实例)时才需要用这个参数,这时候要注意:
- UID不能用
DOMAIN\USER格式,必须传Entra ID账号的UPN格式(比如user@your-tenant.onmicrosoft.com) - 容器必须能正常访问公网的Entra ID认证端点,纯本地离线环境用不了这个模式
- 删掉
Trusted_Connection=no参数,这个参数和Azure AD认证流程存在冲突
内容的提问来源于stack exchange,提问作者Nobody moving away from SE
相关产品推荐
相关产品推荐

