最近,我们构建了一个小型应用程序,该应用程序允许最终用户远程启动SQL Server上的作业。为了确定作业是否已经在运行,我们使用以下查询:
SELECT
sj.job_id
, name
FROM
msdb.dbo.sysjobactivity AS sja
INNER JOIN msdb.dbo.sysjobs AS sj
ON sja.job_id = sj.job_id
WHERE
sja.start_execution_date IS NOT NULL
AND sja.stop_execution_date IS NULL
这就像一个符咒,但在理想情况下,如果已经开始工作,我们还希望显示开始该工作的用户的ID /名称。
我检查了不同的sysjobs *表,但是无法找到任何可以让我们获取该信息的列。
我希望我只是忽略了一些东西,希望有人能够帮助我找出完成此任务的捷径。我的替代方法是在作业开始时添加一个自己的额外表,其中包含作业ID和用户名,然后以这种方式输入名称。
我们最终建立了自己的表来存储要开始的作业的详细信息:
CREATE TABLE [dbo].[dwh_jobs](
[job_id] [uniqueidentifier] NOT NULL,
[started_by_user_name] [nvarchar](255) NOT NULL,
[start_time] [datetime] NOT NULL,
[end_time] [datetime] NULL,
[run_time] [nvarchar](250) NULL,
[rows_affected] [bigint] NULL DEFAULT ((0))
)
然后,我们创建了两个存储过程来记录正在启动的作业的开始和结束时间:
CREATE PROCEDURE [dbo].[usp_job_start]
@job_id uniqueidentifier
, @started_by_user_name nvarchar(255)
, @start_time datetime
AS
BEGIN
INSERT INTO msdb.dbo.dwh_jobs
(job_id, started_by_user_name, start_time, end_time, run_time, rows_affected)
VALUES
(@job_id, @started_by_user_name, @start_time, NULL, NULL, 0)
END
这是结束过程:
CREATE PROCEDURE [dbo].[usp_job_end]
@job_id uniqueidentifier
, @started_by_user_name nvarchar(255)
, @start_time datetime
, @end_time datetime
, @run_time nvarchar(255)
, @rows_affected bigint
AS
BEGIN
UPDATE msdb.dbo.dwh_jobs
SET
end_time = @end_time
, run_time = @run_time
, rows_affected = @rows_affected
WHERE
job_id = @job_id
AND started_by_user_name = @started_by_user_name
AND start_time = @start_time
AND end_time IS NULL
AND run_time IS NULL
AND rows_affected = 0
END;
最后,我们添加了一个proc来查找哪个用户开始了特定工作:
CREATE PROCEDURE [dbo].[usp_job_lookup_user]
@job_id uniqueidentifier
, @started_by_user_name nvarchar(255) OUTPUT
AS
BEGIN
SELECT
@started_by_user_name = started_by_user_name
FROM
msdb.dbo.dwh_jobs
WHERE
start_time = (SELECT MAX(start_time) FROM msdb.dbo.dwh_jobs
WHERE job_id = @job_id AND end_time IS NULL)
END;
这还不是很完美,因为还没有维护来清理未关闭的工作,但是它至少可以让我们找出哪个用户开始了特定工作。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句