Create_SQL_Server_Trigger

Snippet Name: Create_SQL_Server_Trigger

Tags:

Created Date: 2025-06-16 13:12:46
Last Modified Date: 2025-05-31 10:32:06

Dependencies:

DBA Notes:

Sample Output:

Title: Create SQL Server Trigger
Author: user
can you help me create a SQL Server trigger on all server for ALTER_SERVER_CONFIGURATION events, that captures the information into a permenant table in master database

Author: ChatGPT
Yes! You can create a **DDL Trigger** in SQL Server that captures `ALTER_SERVER_CONFIGURATION` events and logs them into a permanent table in the `master` database.

### Steps:
1. **Create a logging table in `master`** to store changes.
2. **Create a DDL trigger** at the server level (`ON ALL SERVER`) to capture `ALTER_SERVER_CONFIGURATION` events.

---

### **Step 1: Create a Logging Table in `master`**
```sql
USE master;
GO

IF NOT EXISTS (SELECT 1 FROM sys.tables WHERE name = 'ServerConfigChanges' AND schema_id = SCHEMA_ID('dbo'))
BEGIN
    CREATE TABLE dbo.ServerConfigChanges (
        ID INT IDENTITY(1,1) PRIMARY KEY,
        EventTime DATETIME2 DEFAULT SYSDATETIME(),
        LoginName SYSNAME,
        HostName SYSNAME,
        ProgramName NVARCHAR(256),
        ServerName SYSNAME,
        EventType NVARCHAR(100),
        CommandText NVARCHAR(MAX)
    );
END;
GO
```

---

### **Step 2: Create the Server-Level DDL Trigger**
```sql
USE master;
GO

CREATE OR ALTER TRIGGER trg_CaptureAlterServerConfig
ON ALL SERVER
FOR ALTER_SERVER_CONFIGURATION
AS
BEGIN
    SET NOCOUNT ON;

    DECLARE @EventData XML = EVENTDATA();

    INSERT INTO master.dbo.ServerConfigChanges (
        LoginName,
        HostName,
        ProgramName,
        ServerName,
        EventType,
        CommandText
    )
    SELECT
        SUSER_SNAME(),  -- Login Name
        HOST_NAME(),    -- Host Name
        APP_NAME(),     -- Program Name
        @@SERVERNAME,   -- Server Name
        @EventData.value('(EVENT_INSTANCE/EventType)[1]', 'NVARCHAR(100)'),  -- Event Type
        @EventData.value('(EVENT_INSTANCE/TSQLCommand)[1]', 'NVARCHAR(MAX)') -- Command Text
    ;
END;
GO
```

---

### **Step 3: Test the Trigger**
Try running an `ALTER SERVER CONFIGURATION` command:
```sql
ALTER SERVER CONFIGURATION SET BUFFER POOL EXTENSION ON (FILENAME = 'C:\Temp\BPE.BIN', SIZE = 256 MB);
GO
```
Then, check the logs:
```sql
SELECT * FROM master.dbo.ServerConfigChanges;
GO
```

---

### **Step 4: Review & Manage the Trigger**
- **Disable the Trigger (if needed)**:
  ```sql
  DISABLE TRIGGER trg_CaptureAlterServerConfig ON ALL SERVER;
  GO
  ```
- **Enable the Trigger Again**:
  ```sql
  ENABLE TRIGGER trg_CaptureAlterServerConfig ON ALL SERVER;
  GO
  ```
- **Drop the Trigger**:
  ```sql
  DROP TRIGGER trg_CaptureAlterServerConfig ON ALL SERVER;
  GO
  ```

---

### **Additional Considerations**
- Ensure the `master` database allows modifications.
- Be aware of potential performance overhead if there are frequent configuration changes.
- If you need historical tracking, consider setting up a SQL Server Agent job to archive old logs periodically.

Let me know if you need any modifications! ????

Author: user
i get an error Msg 1082, Level 15, State 1, Procedure trg_CaptureAlterServerConfig, Line 6 [Batch Start Line 19]
"ALTER_SERVER_CONFIGURATION" does not support synchronous trigger registration.

Author: ChatGPT
You're right! `ALTER_SERVER_CONFIGURATION` is **not** an event that supports synchronous DDL triggers. Instead, you need to use **Extended Events** to capture these changes asynchronously.

---

### **Solution: Use Extended Events for ALTER_SERVER_CONFIGURATION**
Since SQL Server **does not allow** synchronous triggers for `ALTER_SERVER_CONFIGURATION`, we will:
1. **Create an Extended Events session** to capture `alter_server_configuration` events.
2. **Log the events into a table in `master`** using SQL Agent or a scheduled job.

---

### **Step 1: Create a Logging Table**
```sql
USE master;
GO

IF NOT EXISTS (SELECT 1 FROM sys.tables WHERE name = 'ServerConfigChanges' AND schema_id = SCHEMA_ID('dbo'))
BEGIN
    CREATE TABLE dbo.ServerConfigChanges (
        ID INT IDENTITY(1,1) PRIMARY KEY,
        EventTime DATETIME2 DEFAULT SYSDATETIME(),
        LoginName SYSNAME,
        HostName SYSNAME,
        ProgramName NVARCHAR(256),
        ServerName SYSNAME,
        EventType NVARCHAR(100),
        CommandText NVARCHAR(MAX)
    );
END;
GO
```

---

### **Step 2: Create an Extended Events Session**
This session will capture `alter_server_configuration` events and store them in an event file.

```sql
CREATE EVENT SESSION CaptureAlterServerConfig
ON SERVER
ADD EVENT sqlserver.alter_server_configuration (
    ACTION (sqlserver.sql_text, sqlserver.session_id, sqlserver.client_hostname, sqlserver.client_app_name, sqlserver.username)
)
ADD TARGET package0.event_file (SET filename = 'C:\Temp\AlterServerConfig.xel', max_file_size = 5MB, max_rollover_files = 5);
GO

ALTER EVENT SESSION CaptureAlterServerConfig ON SERVER STATE = START;
GO
```
???? **Modify `C:\Temp\AlterServerConfig.xel` path** if needed.

---

### **Step 3: Query the Captured Data**
You can periodically fetch the captured events using the following query:

```sql
SELECT 
    event_data.value('(event/@name)[1]', 'NVARCHAR(100)') AS EventType,
    event_data.value('(event/@timestamp)[1]', 'DATETIME2') AS EventTime,
    event_data.value('(event/action[@name="username"]/value)[1]', 'SYSNAME') AS LoginName,
    event_data.value('(event/action[@name="client_hostname"]/value)[1]', 'SYSNAME') AS HostName,
    event_data.value('(event/action[@name="client_app_name"]/value)[1]', 'NVARCHAR(256)') AS ProgramName,
    event_data.value('(event/action[@name="sql_text"]/value)[1]', 'NVARCHAR(MAX)') AS CommandText
FROM 
(
    SELECT CAST(event_data AS XML) AS event_data
    FROM sys.fn_xe_file_target_read_file('C:\Temp\AlterServerConfig*.xel', NULL, NULL, NULL)
) AS Events;
GO
```

---

### **Step 4: Automate Data Capture (Optional)**
If you want to periodically store this data in your logging table, set up a SQL Agent job with this script:

```sql
INSERT INTO master.dbo.ServerConfigChanges (EventType, EventTime, LoginName, HostName, ProgramName, CommandText)
SELECT 
    event_data.value('(event/@name)[1]', 'NVARCHAR(100)'),
    event_data.value('(event/@timestamp)[1]', 'DATETIME2'),
    event_data.value('(event/action[@name="username"]/value)[1]', 'SYSNAME'),
    event_data.value('(event/action[@name="client_hostname"]/value)[1]', 'SYSNAME'),
    event_data.value('(event/action[@name="client_app_name"]/value)[1]', 'NVARCHAR(256)'),
    event_data.value('(event/action[@name="sql_text"]/value)[1]', 'NVARCHAR(MAX)')
FROM 
(
    SELECT CAST(event_data AS XML) AS event_data
    FROM sys.fn_xe_file_target_read_file('C:\Temp\AlterServerConfig*.xel', NULL, NULL, NULL)
) AS Events;
GO
```

---

### **Step 5: Manage the Extended Events Session**
- **Stop the session** (if needed):
  ```sql
  ALTER EVENT SESSION CaptureAlterServerConfig ON SERVER STATE = STOP;
  ```
- **Delete the session**:
  ```sql
  DROP EVENT SESSION CaptureAlterServerConfig ON SERVER;
  ```
- **Restart the session**:
  ```sql
  ALTER EVENT SESSION CaptureAlterServerConfig ON SERVER STATE = START;
  ```

---

### **Summary**
??? **DDL Triggers won't work** for `ALTER_SERVER_CONFIGURATION`.  
??? **Extended Events capture the changes asynchronously.**  
??? **Query the `.xel` file to extract and log the data.**  
??? **Automate with SQL Agent for periodic logging.**  

This approach ensures **minimal performance overhead** while logging all server configuration changes efficiently. ???? Let me know if you need any modifications!

Author: user
can you validate or test that session creation? i don't think there is an event for alter_server_configuration 

Author: ChatGPT
You're right to be cautious. I will validate the available events and ensure that the correct method is used for capturing `ALTER SERVER CONFIGURATION` changes in SQL Server. Let me check the valid Extended Events for capturing these changes.


Leave a Reply