SQL Server Agent 启动失败排查实录:从权限拒绝到双实例解析

摘要 :本文记录了一次典型的 SQL Server Agent 无法启动问题的完整排查过程。通过分析日志、验证服务账户权限、修复登录主体,最终成功解决问题,并深入解释了为何一台机器上会出现两个 SQL Server 实例(MSSQLSERVERSQLEXPRESS),帮助开发者理解 SQL Server 实例管理机制。


一、问题现象

在 Windows 服务器上,尝试启动 SQL Server 代理 (SQLEXPRESS) 服务时,服务看似"启动成功",但几秒后自动停止。Windows 事件查看器中仅显示两条日志:

  • 事件 ID 101SQLServerAgent service successfully started.
  • 事件 ID 102:无详细描述(通常表示服务已停止)

表面上看没有报错,但实际 Agent 无法持续运行,导致作业(Jobs)、警报(Alerts)等功能完全不可用。


二、初步排查:服务配置与连接测试

1. 服务登录账户设置

检查服务属性发现,SQL Server Agent 使用的是 Local Service 账户。这是一个低权限内置账户,不具备访问 SQL Server 数据库所需的权限

修正操作

将登录账户改为 Local System(高权限内置账户),重启服务。

⚠️ 注意:Local ServiceLocal System!前者权限不足,后者可代表本地系统管理员。

2. 验证 SQL Server 引擎是否可用

使用 SSMS 尝试连接:

  • . → 连接默认实例(失败)
  • .\SQLEXPRESS连接成功

说明:

  • SQLEXPRESS 是命名实例
  • . 只能连接默认实例(MSSQLSERVER),不能自动跳转到命名实例

✅ 正确连接命名实例的方式:.\SQLEXPRESSlocalhost\SQLEXPRESS


三、关键突破:分析 SQLAGENT.OUT 日志

在路径
C:\Program Files\Microsoft SQL Server\MSSQL15.SQLEXPRESS\MSSQL\Log\SQLAGENT.OUT

中发现核心错误:

text 复制代码
[298] SQLServer 错误: 229, 拒绝了对对象 'sp_sqlagent_update_agent_xps' 
(数据库 'msdb', 架构 'dbo') 的 EXECUTE 权限。

这表明:Agent 服务账户没有执行系统存储过程的权限


四、根本原因:服务账户未注册为 SQL Server 登录主体

SQL Server Agent 在启动时,会以虚拟 Windows 服务账户身份连接数据库:

NT SERVICE\SQLAgent$<实例名>

对于 SQLEXPRESS,该账户为:
NT SERVICE\SQLAgent$SQLEXPRESS

但查询 sys.server_principals 发现该登录名不存在

sql 复制代码
SELECT name FROM sys.server_principals 
WHERE name = 'NT SERVICE\SQLAgent$SQLEXPRESS';
-- 返回空

即使服务使用 Local System 运行,SQL Server 内部仍通过此虚拟账户认证,必须显式创建并授权


五、解决方案:创建登录并授予 sysadmin 角色

步骤 1:创建服务账户登录

sql 复制代码
CREATE LOGIN [NT SERVICE\SQLAgent$SQLEXPRESS] FROM WINDOWS;

步骤 2:授予 sysadmin 角色(必需)

sql 复制代码
ALTER SERVER ROLE sysadmin ADD MEMBER [NT SERVICE\SQLAgent$SQLEXPRESS];

💡 Microsoft 官方要求:SQL Server Agent 服务账户必须是 sysadmin 成员,否则无法正常工作。

步骤 3:重启服务

复制代码
net stop "SQLAgent$SQLEXPRESS"
net start "SQLAgent$SQLEXPRESS"

✅ 服务状态变为 "正在运行",且保持稳定!


六、延伸问题:为什么我的机器上有两个 SQL Server 实例?

在服务列表中同时看到:

  • SQL Server (MSSQLSERVER) → 默认实例
  • SQL Server (SQLEXPRESS) → 命名实例

原因分析:

实例 来源 特点
MSSQLSERVER 安装 SQL Server Developer / Standard / Enterprise 版本 默认实例,连接方式:.
SQLEXPRESS 安装 SQL Server Express Edition 命名实例,连接方式:.\SQLEXPRESS

常见场景:

  • 安装 Visual Studio 时自动附带 SQL Server Express
  • 后续又手动安装了 SQL Server Developer Edition
  • 某些应用(如旧版 SharePoint)依赖 Express 实例

✅ 一台机器可安装多个 SQL Server 实例,彼此独立,互不影响。

是否需要保留两个?

  • 开发环境:保留无妨,资源占用小
  • 生产环境:建议只保留一个,降低复杂度
  • 清理方法:通过"控制面板 → 程序和功能"卸载不用的版本

七、经验总结

  1. 不要混淆 Local ServiceLocal System ------ 前者权限不足,无法运行 Agent。
  2. 命名实例必须用 .\实例名 连接. 只适用于默认实例。
  3. SQL Server Agent 必须拥有 sysadmin 权限,这是硬性要求。
  4. 日志文件 SQLAGENT.OUT 是诊断 Agent 问题的第一手资料
  5. 多实例共存是正常现象,源于多次安装不同版本的 SQL Server。

八、附录:常用排查命令

sql 复制代码
-- 检查服务账户是否存在
SELECT name, type_desc, is_disabled 
FROM sys.server_principals 
WHERE name = 'NT SERVICE\SQLAgent$SQLEXPRESS';

-- 检查是否拥有 sysadmin 角色
SELECT r.name AS role_name
FROM sys.server_role_members rm
JOIN sys.server_principals r ON rm.role_principal_id = r.principal_id
JOIN sys.server_principals m ON rm.member_principal_id = m.principal_id
WHERE m.name = 'NT SERVICE\SQLAgent$SQLEXPRESS';

-- 禁用所有作业(用于排除作业干扰)
USE msdb;
UPDATE dbo.sysjobs SET enabled = 0;

结语

SQL Server 是一个强大但复杂的数据库平台,服务启动失败往往隐藏着权限、配置或实例管理的细节问题。通过系统化日志分析 + 权限验证,我们不仅能解决当前问题,还能加深对 SQL Server 架构的理解。

希望本文能帮助遇到类似问题的开发者快速定位并修复故障!

相关推荐
woshilys6 小时前
sql server 索引选择
数据库·sqlserver
松涛和鸣8 小时前
DAY67 IMX6 Development Board Configuration from Scratch
数据库·postgresql·sqlserver
wangqiaowq14 小时前
SQL server 的3种数据库连接协议
sqlserver
山岚的运维笔记2 天前
SQL Server笔记 -- 第13章:IF...ELSE
数据库·笔记·sql·microsoft·sqlserver
woshilys5 天前
sql server 表被另外一张表锁
sqlserver
zhangzeyuaaa6 天前
SQL Server删除重复数据
运维·sqlserver
雪碧聊技术7 天前
DBeaver连接sql server数据库时,提示驱动版本不合适
数据库·sqlserver·dbeaver·更换驱动·修改java.security
雷工笔记8 天前
数据库|SQLServer2025安装教程
数据库·sqlserver
梁正雄10 天前
linux服务-麒麟10安装sqlserver
linux·运维·sqlserver