Microsoft SQL Server Agent Job: Get Schedule that triggered the Job - sql-server

I have SQL Server Agent Job on my System that copies data into at table for later evaluation purposes. The Job runs on two types of schedules every Friday every week and last day of the month. The target data records should also contain a column indicating the schedule that originally triggered the job. But I found no way so far to receive this data as parameter or so. I'm using a Microsoft SQL Server 2017.
I did a web search but maybe searched for the wrong keywords. I also thought about comparing current time to expected runtime per schedule but that seemed to be not a fault tolerant option to me.
I like to fill a column "schedule" with values like "End of week", "End of month"

sys tables are your friend here. Documentation
sysjobs has your job information.
sysjobschedules links your job to its schedule.
sysschedules has your schedule info.
SELECT j.*
, s.*
FROM sysjobs j
JOIN sysjobschedules js ON j.id = js.job_id
JOIN sysschedules s ON js.schedule_id = s.schedule_id
WHERE j.name = 'your job name here'

After long search and analyzing I finally found a solution that at least fit my needs:
The undocumented and unsupport stored procedures provides the schedule that triggered a job ind Column Request Source ID:
EXEC master.dbo.xp_sqlagent_enum_jobs 1, garbage
see also: https://am2.co/2016/02/xp_sqlagent_enum_jobs_alt/

Related

SQL Server : how to automatically update data in table after a certain time interval

I have an OrderProduct table with these columns and some data:
-order_number : ORDER01
-customer_name : Jackie
-order_status : Wait For Payment
-datetime_order_status : 25-01-2020 15:30:00
-datetime_transfer_notify : NULL
A customer needs to transfer notify in my order product system in 24 hours if not the Microsoft SQL will automatic update data in column 'order_status' from 'Wait for payment' to 'Cancel'.
How can I do that?
I believe the easiest way to do this is with a SQL Agent job (MS Docs). This is very dependent on the architecture and size of your databases and tables, but it would definitely get the job done. Depending on how sensitive the business is to being up to date, you could set the job to run every 1 minute, every 5 minutes, or any other time interval you would like. If I was going to do this, I would use a query along the lines of the following:
UPDATE OrderProduct SET order_state = 'Cancel' WHERE datetime_order_status < DATEADD(DAY, -1, GETDATE()) AND order_status = 'Wait for Payment'
Along with this, I would use something like SQL Server Management Studio to create a SQL Agent job on that server that ran at the interval you'd like, similar to this (Stack Overflow). Here (Stack Exchange DBA) is a very similar question to yours for MySQL as added reference.

How can I find out if someone modified a row in SQL server in a specific date?

I am just wondering, can I find out if somebody wrote a query and updated a row against specific table in some date?
I tried this :
SELECT id, name
FROM sys.sysobjects
WHERE NAME = ''
SELECT TOP 1 *
FROM ::fn_dblog(NULL,NULL)
WHERE [Lock Information] LIKE '%TheOutoput%'
It does not show me ?
Any suggestions.
No, row level history/change stamps is not built into SQL Server. You need to add that in the table design. If you want an automatic update date column it would typically be set by a trigger on the table.
There is however a way if you really need to find out what happened in a forensics scenario. But that is only available if you have the right backup plans. What you can do then is to use the DB transaction log to find when the modification was done. Note that this is not anything an application can or should do runtime.

Aggregate data from msdb.dbo.sysjobhistory

each time i run agent job it puts some data to the log. I can access those data via T-SQL like this: SELECT * FROM msdb.dbo.sysjobhistory WHERE step_id = 0. It will show me summary information about job.
Problem is that if there was a step with failed but "on failure action" was "go to next step" run_status will show success.
I've try to aggregate data from step_id <> 0 but i don't know how to distinguish each run of a job.
Can You help me with that problem? Best result would be additional column with distinct list of statuses that appeared in a job showed by first query.
What i want to achieve is a daily raport of a jobs that ran (some of them multiple time during the day) last day.
Try joining your query to:
SELECT * FROM [dbo].[sysjobsteps]
This includes the field last_run_outcome.
MSDN link of complete table:
https://msdn.microsoft.com/en-us/library/ms187387.aspx

Executing SSRS Reports From SSIS

I need to execute a SSRS reports from SSIS on periodic schedule.
Saw a solution here :
https://www.mssqltips.com/sqlservertip/3475/execute-a-sql-server-reporting-services-report-from-integration-services-package/
But is there any other option in SSIS without using Script Task ? I don't quite understand the script and concern there could be some support issue for me.
Database : SQL Server 2008R2 Standard Edition
Any ideas ? Thanks very much ...
SSIS controlling the running of an SSRS in SQL Agent.
This assumes that the SSIS job will have updated a control record or written some other identifiable record to a database.
1. Create a subscription for the report.
2. Run this SQL to get the GUID of the report
SELECT c.Name AS ReportName
, rs.ScheduleID AS JOB_NAME
, s.[Description]
, s.LastStatus
, s.LastRunTime
FROM
ReportServer..[Catalog] c
JOIN ReportServer..Subscriptions s ON c.ItemID = s.Report_OID
JOIN ReportServer..ReportSchedule rs ON c.ItemID = rs.ReportID
AND rs.SubscriptionID = s.SubscriptionID<br>
3. Create a SQL Agent job.
a. Step 1. A SQL statement to look for data in a table containing a flagged record where the Advanced setting is "on failure end job reporting success"
IF NOT exists ( select top 1 * from mytable where mykey = 'x'
and mycondition = 'y') RAISERROR ('No Records Found',16,1)
b. Step 2
USE msdb
EXEC sp_start_job #job_name = ‘1X2C91X5-8B86-4CDA-9G1B-112C4F6E450A'<br>
Replacing the GUID with the one returned from your GUID query.
One thing to note though ... once the report subscription has been executed then as far as SQL Agent is concerned then that step is complete, even though the report has not necessarily finished running. I once had a clean up job after the Exec step which effectively deleted some of my data before the report reached it!
You can create a subscription for the report that is never scheduled to run.
If you have the Subscription ID, you can fire the report subscription using a simple SQL Task in SSIS.
You can get the Subscription ID from the Report Server database. It is in the Subscriptions table.
Use this query to help locate the subscription:
SELECT Catalog.Path
,Catalog.Name
,SubscriptionID
,Subscriptions.Description
FROM Catalog
INNER JOIN Subscriptions
ON Catalog.ItemID = Subscriptions.Report_OID
In SSIS, you can use this statement, inside of a SQL Task, to fire the subscription:
EXEC reportserver.dbo.AddEvent #EventType='TimedSubscription',#EventData= [Your Subscription ID]
Hope this helps.

How to monitor an SQL Server Agent Job that runs after being triggered

I'm running SQL Server 2008 and I have 3 agent jobs set up to run one after the other because the success of the second depends on the first, etc.
Every other job I have is independent and I monitor using a script that incorporates MSDB..sysjobhistory run_status field, among others.
I want to know if there is a way to specifically find all jobs that never started for a specific day. I know that I can think of the problem the other way and say job 2 couldn't possibly run if job 1 failed; however, I'm looking for a more general purpose solution so in case I need to create other jobs that are linked similarly I won't have to hard code more logic into my nightly report.
Any suggestions are welcome!
The MSDB..sysjobservers table holds a single record for every agent job in your server, and includes the field last_run_date which makes it easy to tell which jobs haven't run in the last 24 hours. My query looks something like this
SELECT A.name AS [Name]
,##servername AS [Server]
,'Yes' AS [Critical]
FROM MSDB.dbo.sysjobs A
INNER JOIN MSDB.dbo.sysjobservers B ON A.job_id = B.job_id
WHERE A.name LIKE '2%SPRING%'
AND DATEDIFF(DAY, CONVERT(DATETIME, CONVERT(CHAR(8),B.last_run_date)), GETDATE( )) > 1)

Resources