narrow default width wide
colour style colour style colour style colour style

SCCM Patch Reporting-Patch 0-Enterprise Summary

This is a fairly complex SCCM report for patching. It uses multiple table variables and a loop to process multiple Collections.



CCM Patch Reporting-Patch0-Enterprise Summary


--SSM - Patch - 0 - Enterprise Summary (ver4)
 
SET NOCOUNT ON 
 
DECLARE @AuthListName varchar(128)  
SELECT @AuthListName = 'Windows-Critical and Security Updates'  
 
DECLARE @AuthListID varchar(128); SELECT @AuthListID = CI_UniqueID FROM v_AuthListInfo WHERE Title = @AuthListName  
DECLARE @AuthList_CI_ID int; SELECT @AuthList_CI_ID=CI_ID FROM v_AuthListInfo WHERE Title = @AuthListName  
 
 
--Get the CI_IDs from the AuthList and put in a table variable
DECLARE @CI TABLE(CI_ID int PRIMARY KEY)  
INSERT @CI  
SELECT CIR.ToCIID  
FROM v_CIRelation CIR  
WHERE CIR.FromCIID = @AuthList_CI_ID  
 
--Declare main table to store all results in
DECLARE @SSM TABLE
  (
  [CollectionID] varchar(64)  
  , [Collection Name] varchar(64)  
  , [UPDATE List] varchar(64)  
  , [Percentage Patched] decimal(5,2)
  , [Compliant] int  
  , [Non-Compliant] int 
  , [Total Reporting ON] int  
  , [Collection Total] int  
  , [Clients] int  
  , [Non-Clients] int  
  , [Patches Required] int 
  , [Unknown PatchState] int  
  , [PACS] int
  , [DenyPatch] int
  , [DenySCCMClient] int
  , [Servers] int
  ) 
 
--Build table of the collections we will process
DECLARE @CollTable TABLE
  (RowID int IDENTITY(1, 1),  
  CollID varchar(64)) 
 
INSERT INTO @CollTable  
  SELECT CollectionID 
  FROM v_Collection 
  WHERE Name LIKE '%: Systems' 
    OR Name LIKE '000: Deny Auto Patch' 
  ORDER BY Name 
 
--These 2 are used for looping
DECLARE @NumberRecords int; SELECT @NumberRecords = Count(*) FROM @CollTable 
DECLARE @RowCount int; SET @RowCount = 1 
 
 
WHILE @RowCount <= @NumberRecords 
BEGIN 
 
  DECLARE @CollID varchar(64); SELECT @CollID=CollID FROM @CollTable WHERE RowID = @RowCount 
 
  --@RESOURCEIDS is the list of systems that we are reporting on
  DECLARE @RESOURCEIDS TABLE(ResourceID varchar(10) PRIMARY KEY) 
  INSERT @RESOURCEIDS 
    SELECT COLLMEM.ResourceID 
    FROM v_ClientCollectionMembers COLLMEM 
    LEFT JOIN v_R_System SYS ON COLLMEM.ResourceID = SYS.ResourceID 
    WHERE COLLMEM.CollectionID = @CollID 
      AND (SYS.Operating_System_name_and0 LIKE '%workstation%' 
        OR SYS.g_erating_System_name_and0 IS NULL)
      AND COLLMEM.ResourceID NOT IN 
        (SELECT CCM.ResourceID 
        FROM v_ClientCollectionMembers CCM 
        JOIN v_Collection COLL ON CCM.CollectionID = COLL.CollectionID 
        WHERE COLL.Name = '000: RA1000 and CA1000' 
          OR COLL.Name = '000: DenyPatch' 
          OR COLL.Name = '000: DenySCCMClient' 
        ) 
 
  --Misc info about this collections
  DECLARE @CollectionTotal int; SELECT @CollectionTotal=COUNT(*) FROM v_ClientCollectionMembers WHERE CollectionID = @CollID 
  DECLARE @ReportingTotal int; SELECT @ReportingTotal=COUNT(*) FROM @RESOURCEIDS 
  DECLARE @CollName varchar(256); SELECT @CollName=Name FROM v_Collection WHERE CollectionID=@CollID  
 
  --# of systems that are not workstations
  DECLARE @SERVERS int
  SELECT @SERVERS=COUNT(*) 
  FROM v_ClientCollectionMembers CCM JOIN v_R_System SYS ON CCM.ResourceID = SYS.ResourceID
  WHERE CCM.CollectionID = @CollID
    AND SYS.Operating_System_name_and0 NOT LIKE '%workstation%'
  --# of systems that are in the RA1000/CA1000 collection
  DECLARE @PACS int
  SELECT @PACS=COUNT(*) FROM v_ClientCollectionMembers
  WHERE CollectionID = @CollID
    AND ResourceID IN
      (SELECT CCM.ResourceID 
        FROM v_ClientCollectionMembers CCM 
        JOIN v_Collection COLL ON CCM.CollectionID = COLL.CollectionID 
        WHERE COLL.Name = '000: RA1000 and CA1000'
      )
  --# of systems that are in the DenyPatch Collection
  DECLARE @DENYPATCH int
   SELECT @DENYPATCH=COUNT(*) FROM v_ClientCollectionMembers
    WHERE CollectionID = @CollID
      AND ResourceID IN
        (SELECT CCM.ResourceID 
          FROM v_ClientCollectionMembers CCM 
          JOIN v_Collection COLL ON CCM.CollectionID = COLL.CollectionID 
          WHERE COLL.Name = '000: DenyPatch'
        )
  --# of systems that are in the DenySCCMClient Collection
  DECLARE @DENYSCCMCLIENT int
  SELECT @DENYSCCMCLIENT=COUNT(*) FROM v_ClientCollectionMembers
  WHERE CollectionID = @CollID
    AND ResourceID IN
      (SELECT CCM.ResourceID 
        FROM v_ClientCollectionMembers CCM 
        JOIN v_Collection COLL ON CCM.CollectionID = COLL.CollectionID 
        WHERE COLL.Name = '000: DenySCCMClient'
      )
 
  --# of systems with the client installed and working
  DECLARE @NumberClients int 
  SELECT  @NumberClients=isnull(sum(cast(SYS.Client0 AS int)), 0) 
    FROM @RESOURCEIDS RIDS LEFT JOIN v_R_System SYS ON RIDS.ResourceID = SYS.ResourceID  
  --# of systems with out an installed and working client
  DECLARE @NonClients int; SELECT @NonClients = @ReportingTotal - @NumberClients  
 
  --@RESOURCEIDS2 is a list of all ResourceID/CI_ID combos where a patch is missing/applicable
  --Used for performance reasons
  DECLARE @RESOURCEIDS2 TABLE 
    (ResourceID varchar(10) 
    , STATUS int) 
  INSERT @RESOURCEIDS2 
 
      SELECT  COLLMEM.ResourceID, UCSA.STATUS 
      FROM @RESOURCEIDS COLLMEM 
        LEFT JOIN v_Update_ComplianceStatusAll UCSA ON COLLMEM.ResourceID = UCSA.ResourceID 
        JOIN @CI CI ON UCSA.CI_ID = CI.CI_ID 
      WHERE 
        UCSA.STATUS IN (0,2) 
 
  --Misc summary info about patch levels
  DECLARE @NumBad int; SELECT @NumBad=Count(DISTINCT ResourceID) FROM @RESOURCEIDS2 
  DECLARE @NumRequired int; SELECT @NumRequired=Count(DISTINCT ResourceID) FROM @RESOURCEIDS2 WHERE STATUS = 2 
  DECLARE @NumUnknown int; SELECT @NumUnknown=@NumBad - @NumRequired 
  DECLARE @NumCompliant int; SELECT @NumCompliant=@ReportingTotal - @NumBad 
 
  --Add all of the info about this collection to the main table variable
  INSERT INTO @SSM 
  SELECT
    @CollID
    , @CollName
    , @AuthListName
    , LEFT(ROUND((@NumCompliant) / (@ReportingTotal + 0.0001) * 100, 2), 5)  AS 'Percentage Patched'
    , @NumCompliant AS 'Total Compliant' 
    , @NumBad AS 'Total Non-compliant' 
    , @ReportingTotal AS 'Total Reporting On' 
    , @CollectionTotal
    , @NumberClients AS 'Clients' 
    , @NonClients AS 'Non-Clients' 
    , @NumRequired AS 'Patches Required' 
    , @NumUnknown AS 'Unknown Patch State' 
    , @PACS AS 'CA1000-RA1000'
    , @DENYPATCH AS 'DenyPatch'
    , @DENYSCCMCLIENT AS 'DenySCCMClient'
    , @SERVERS AS 'Servers'
 
  --Cleanup befoore loop...
  DELETE FROM @RESOURCEIDS 
  DELETE FROM @RESOURCEIDS2 
  SET @RowCount = @RowCount + 1 
END 
 
--Display info for all collections
SELECT * FROM @SSM