msdb.dbo.sp_start_job 卡在存储过程中

msdb.dbo.sp_start_job got stuck in stored procedure

我有一个存储过程USP_A,其逻辑如下:

......
exec dbo.usp_Log 'Start to run job job1'
Exec @intErrorCode = msdb.dbo.sp_start_job 'job1'   
  IF @intErrorCode <> 0 Goto errorHandling
exec dbo.usp_Log 'End to run job job1'
......

但是当我 运行 这个存储过程时,它卡住了,当我检查日志时我只能看到消息 'Start to run job job1'。同样在 SQL 服务器代理作业监视器中,我看不到该作业被触发。

但是如果我手动 运行

Exec @intErrorCode = msdb.dbo.sp_start_job 'job1' 

它工作正常。

SQL服务器是微软SQLServer 2005企业版(版本9.00.5000.00)

您的作业可能无法启动,并且 运行 正在转到代码的 errorHandling 部分。如果您首先将 @@ERROR_MESSAGE 添加到日志中,那么您将在日志中看到问题。类似于:

exec dbo.usp_Log 'Start to run job job1'
begin try
    Exec @intErrorCode = msdb.dbo.sp_start_job 'job1'
end try
begin catch
    exec dbo.usp_Log 'Error: ' + ERROR_MESSAGE()
    Goto errorHandling
end catch
exec dbo.usp_Log 'End to run job job1'

更新

我运行 在我的服务器上进行测试。我尝试启动一个已经 运行ning 的作业并返回错误,但没有触发 catch 块。显然这是 sp_start_job 的问题。这可能是您有些困惑的根源。这里发布了一个解决方法:TRY/CATCH does not work on SQL Server Agent error?

不过,我最好的猜测是当代码在不同的用户上下文中 运行 时存在权限问题。您可以将 运行 作业的代码包装到一个在不同安全上下文下执行的过程中......像这样:

create procedure dbo.sp_RunJob1
with execute as owner
as
exec sp_start_job @job_name = 'job1'

然后在您的代码中调用 sp_RunJob1 而不是 sp_start_job 语句。

原来是某种 SQL 服务器错误(也许 SQL Server 2005 很旧)。存储过程意外结束,没有 return 任何代码。

因此,通过将此 msdb.dbo.sp_start_job 过程之前的所有逻辑移动到单独的存储过程中来解决问题。

希望对遇到同样问题的人有所帮助。