適用於 Functions 的 Azure SQL 觸發程式

注意

在取用方案函式中,SQL 觸發程式不支援自動調整。 如果自動調整程式停止函式,則所有事件處理都會停止,而且必須手動重新啟動。

使用進階或專用方案搭配 SQL 觸發程式調整 優點

Azure SQL 觸發程式會使用 SQL 變更追蹤 功能來監視 SQL 資料表的變更,並在建立、更新或刪除資料列時觸發函式。 如需變更追蹤與 Azure SQL 觸發程式搭配使用的組態詳細數據,請參閱 設定變更追蹤。 如需 Azure Functions 的 Azure SQL 擴充功能設定詳細數據的詳細資訊,請參閱 SQL 系結概觀

Azure SQL 觸發程式的取用和 進階版 方案調整決策是透過以目標為基礎的調整來完成。 如需詳細資訊,請參閱 以目標為基礎的調整

功能概觀

Azure SQL 觸發程式系結會使用輪詢循環來檢查變更,在偵測到變更時觸發使用者函式。 概括而言,迴圈看起來像這樣:

while (true) {
    1. Get list of changes on table - up to a maximum number controlled by the Sql_Trigger_MaxBatchSize setting
    2. Trigger function with list of changes
    3. Wait for delay controlled by Sql_Trigger_PollingIntervalMs setting
}

變更會依照變更的順序進行處理,並先處理最舊的變更。 關於變更處理的幾個注意事項:

  1. 如果同時對多個數據列所做的變更,則會根據 CHANGETABLE 函式傳回的順序,以傳送至函式的確切順序為基礎
  2. 數據列的變更會「批處理」在一起。 如果在迴圈的每個反覆項目之間對某個數據列進行多個變更,則該數據列只會有單一變更專案,而該數據列會顯示上次處理狀態與目前狀態之間的差異
  3. 如果對一組數據列進行變更,然後對相同數據列的一半進行另一組變更,則會先處理第二次未變更的一半數據列。 此處理邏輯是由於上述附註與正在批處理的變更 - 觸發程式只會看到進行「最後」變更,並針對處理它們的順序使用

如需變更追蹤及其由 Azure SQL 觸發程式等應用程式使用方式的詳細資訊,請參閱 使用變更追蹤

使用方式範例

GitHub 存放庫中可取得 Azure SQL 觸發程序的其他範例。

這些範例會參考 ToDoItem 類別和對應的資料庫資料表:

namespace AzureSQL.ToDo
{
    public class ToDoItem
    {
        public Guid Id { get; set; }
        public int? order { get; set; }
        public string title { get; set; }
        public string url { get; set; }
        public bool? completed { get; set; }
    }
}
CREATE TABLE dbo.ToDo (
    [Id] UNIQUEIDENTIFIER PRIMARY KEY,
    [order] INT NULL,
    [title] NVARCHAR(200) NOT NULL,
    [url] NVARCHAR(200) NOT NULL,
    [completed] BIT NOT NULL
);

資料庫和資料表上已啟用變更追蹤

ALTER DATABASE [SampleDatabase]
SET CHANGE_TRACKING = ON
(CHANGE_RETENTION = 2 DAYS, AUTO_CLEANUP = ON);

ALTER TABLE [dbo].[ToDo]
ENABLE CHANGE_TRACKING;

SQL 觸發程序會繫結至 IReadOnlyList<SqlChange<T>>,這是各有兩個屬性的 SqlChange 物件清單:

  • 項目:已變更的項目。 項目的類型應遵循 ToDoItem 類別中所見的資料表結構描述。
  • 作業:SqlChangeOperation 列舉中的值。 可能的值為:InsertUpdateDelete

下列範例顯示當資料表有變更時所叫用的 ToDo C# 函式:

using System;
using System.Collections.Generic;
using Microsoft.Azure.Functions.Worker;
using Microsoft.Azure.Functions.Worker.Extensions.Sql;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;


namespace AzureSQL.ToDo
{
    public static class ToDoTrigger
    {
        [Function("ToDoTrigger")]
        public static void Run(
            [SqlTrigger("[dbo].[ToDo]", "SqlConnectionString")]
            IReadOnlyList<SqlChange<ToDoItem>> changes,
            FunctionContext context)
        {
            var logger = context.GetLogger("ToDoTrigger");
            foreach (SqlChange<ToDoItem> change in changes)
            {
                ToDoItem toDoItem = change.Item;
                logger.LogInformation($"Change operation: {change.Operation}");
                logger.LogInformation($"Id: {toDoItem.Id}, Title: {toDoItem.title}, Url: {toDoItem.url}, Completed: {toDoItem.completed}");
            }
        }
    }
}

使用方式範例

GitHub 存放庫中可取得 Azure SQL 觸發程序的其他範例。

此範例會參考類別 ToDoItem 、類別 SqlChangeToDoItemSqlChangeOperation 列舉和對應的資料庫資料表:

在不同的檔案 ToDoItem.java中:

package com.function;
import java.util.UUID;

public class ToDoItem {
    public UUID Id;
    public int order;
    public String title;
    public String url;
    public boolean completed;

    public ToDoItem() {
    }

    public ToDoItem(UUID Id, int order, String title, String url, boolean completed) {
        this.Id = Id;
        this.order = order;
        this.title = title;
        this.url = url;
        this.completed = completed;
    }
}

在不同的檔案 SqlChangeToDoItem.java中:

package com.function;

public class SqlChangeToDoItem {
    public ToDoItem item;
    public SqlChangeOperation operation;

    public SqlChangeToDoItem() {
    }

    public SqlChangeToDoItem(ToDoItem Item, SqlChangeOperation Operation) {
        this.Item = Item;
        this.Operation = Operation;
    }
}

在不同的檔案 SqlChangeOperation.java中:

package com.function;

import com.google.gson.annotations.SerializedName;

public enum SqlChangeOperation {
    @SerializedName("0")
    Insert,
    @SerializedName("1")
    Update,
    @SerializedName("2")
    Delete;
}
CREATE TABLE dbo.ToDo (
    [Id] UNIQUEIDENTIFIER PRIMARY KEY,
    [order] INT NULL,
    [title] NVARCHAR(200) NOT NULL,
    [url] NVARCHAR(200) NOT NULL,
    [completed] BIT NOT NULL
);

資料庫和資料表上已啟用變更追蹤

ALTER DATABASE [SampleDatabase]
SET CHANGE_TRACKING = ON
(CHANGE_RETENTION = 2 DAYS, AUTO_CLEANUP = ON);

ALTER TABLE [dbo].[ToDo]
ENABLE CHANGE_TRACKING;

SQL 觸發程式會系結至 SqlChangeToDoItem[],每個物件陣列 SqlChangeToDoItem 都有兩個屬性:

  • item: 已變更的專案。 項目的類型應遵循 ToDoItem 類別中所見的資料表結構描述。
  • operation: 列舉 SqlChangeOperation 的值。 可能的值為:InsertUpdateDelete

下列範例顯示當資料表有變更時叫用的 ToDo Java 函式:

package com.function;

import com.microsoft.azure.functions.ExecutionContext;
import com.microsoft.azure.functions.annotation.FunctionName;
import com.microsoft.azure.functions.sql.annotation.SQLTrigger;
import com.function.Common.SqlChangeToDoItem;
import com.google.gson.Gson;

import java.util.logging.Level;

public class ProductsTrigger {
    @FunctionName("ToDoTrigger")
    public void run(
            @SQLTrigger(
                name = "todoItems",
                tableName = "[dbo].[ToDo]",
                connectionStringSetting = "SqlConnectionString")
                SqlChangeToDoItem[] todoItems,
            ExecutionContext context) {

        context.getLogger().log(Level.INFO, "SQL Changes: " + new Gson().toJson(changes));
    }
}

使用方式範例

GitHub 存放庫中可取得 Azure SQL 觸發程序的其他範例。

此範例會參考 ToDoItem 資料庫資料表:

CREATE TABLE dbo.ToDo (
    [Id] UNIQUEIDENTIFIER PRIMARY KEY,
    [order] INT NULL,
    [title] NVARCHAR(200) NOT NULL,
    [url] NVARCHAR(200) NOT NULL,
    [completed] BIT NOT NULL
);

資料庫和資料表上已啟用變更追蹤

ALTER DATABASE [SampleDatabase]
SET CHANGE_TRACKING = ON
(CHANGE_RETENTION = 2 DAYS, AUTO_CLEANUP = ON);

ALTER TABLE [dbo].[ToDo]
ENABLE CHANGE_TRACKING;

SQL 觸發程式會系結至 todoChanges,其中各有兩個屬性的物件清單:

  • item: 已變更的專案。 項目的結構會遵循數據表架構。
  • operation: 可能的值為 InsertUpdateDelete

下列範例顯示當數據表有變更時叫用的 ToDo PowerShell 函式。

以下是 function.json 檔案中的繫結資料:

{
    "name": "todoChanges",
    "type": "sqlTrigger",
    "direction": "in",
    "tableName": "dbo.ToDo",
    "connectionStringSetting": "SqlConnectionString"
}

區段說明這些屬性。

以下是 檔案中函式的 run.ps1 範例 PowerShell 程式代碼:

using namespace System.Net

param($todoChanges)
# The output is used to inspect the trigger binding parameter in test methods.
# Use -Compress to remove new lines and spaces for testing purposes.
$changesJson = $todoChanges | ConvertTo-Json -Compress
Write-Host "SQL Changes: $changesJson"

使用方式範例

GitHub 存放庫中可取得 Azure SQL 觸發程序的其他範例。

此範例會參考 ToDoItem 資料庫資料表:

CREATE TABLE dbo.ToDo (
    [Id] UNIQUEIDENTIFIER PRIMARY KEY,
    [order] INT NULL,
    [title] NVARCHAR(200) NOT NULL,
    [url] NVARCHAR(200) NOT NULL,
    [completed] BIT NOT NULL
);

資料庫和資料表上已啟用變更追蹤

ALTER DATABASE [SampleDatabase]
SET CHANGE_TRACKING = ON
(CHANGE_RETENTION = 2 DAYS, AUTO_CLEANUP = ON);

ALTER TABLE [dbo].[ToDo]
ENABLE CHANGE_TRACKING;

SQL 觸發程式會 todoChanges系結 ,每個物件陣列都有兩個屬性:

  • item: 已變更的專案。 項目的結構會遵循數據表架構。
  • operation: 可能的值為 InsertUpdateDelete

下列範例顯示當數據表有變更時所叫用的 ToDo JavaScript 函式。

以下是 function.json 檔案中的繫結資料:

{
    "name": "todoChanges",
    "type": "sqlTrigger",
    "direction": "in",
    "tableName": "dbo.ToDo",
    "connectionStringSetting": "SqlConnectionString"
}

區段說明這些屬性。

以下是 檔案中函式的 index.js JavaScript 程式代碼範例:

module.exports = async function (context, todoChanges) {
    context.log(`SQL Changes: ${JSON.stringify(todoChanges)}`)
}

使用方式範例

GitHub 存放庫中可取得 Azure SQL 觸發程序的其他範例。

此範例會參考 ToDoItem 資料庫資料表:

CREATE TABLE dbo.ToDo (
    [Id] UNIQUEIDENTIFIER PRIMARY KEY,
    [order] INT NULL,
    [title] NVARCHAR(200) NOT NULL,
    [url] NVARCHAR(200) NOT NULL,
    [completed] BIT NOT NULL
);

資料庫和資料表上已啟用變更追蹤

ALTER DATABASE [SampleDatabase]
SET CHANGE_TRACKING = ON
(CHANGE_RETENTION = 2 DAYS, AUTO_CLEANUP = ON);

ALTER TABLE [dbo].[ToDo]
ENABLE CHANGE_TRACKING;

SQL 觸發程式會系結至變數 todoChanges,每個物件清單各有兩個屬性:

  • item: 已變更的專案。 項目的結構會遵循數據表架構。
  • operation: 可能的值為 InsertUpdateDelete

下列範例顯示當數據表有變更時叫用的 ToDo Python 函式。

以下是 function.json 檔案中的繫結資料:

{
    "name": "todoChanges",
    "type": "sqlTrigger",
    "direction": "in",
    "tableName": "dbo.ToDo",
    "connectionStringSetting": "SqlConnectionString"
}

區段說明這些屬性。

以下是 檔案中函式的 __init__.py 範例 Python 程式代碼:

import json
import logging

def main(changes):
    logging.info("SQL Changes: %s", json.loads(changes))

屬性

C# 連結 會使用 SqlTrigger 屬性在函式上宣告 SQL 觸發程式,其具有下列屬性:

Attribute 屬性 描述
TableName 必要。 觸發程式所監視之數據表的名稱。
ConnectionStringSetting 必要。 包含資料庫 連接字串 的應用程式設定名稱,其中包含監視變更的數據表。 連接字串 設定名稱會對應至包含 Azure SQL 或 SQL Server 實例 連接字串 的應用程式設定(用於local.settings.json本機開發)。
LeasesTableName 選擇性。 用來儲存租用的數據表名稱。 如果未指定,租用數據表名稱將會Leases_{FunctionId}_{TableId}。 如需如何產生此項目的詳細資訊,請參閱 這裡

註釋

Java 函式運行時間連結庫中,對值來自 Azure SQL 的參數使用 @SQLTrigger 註釋 (com.microsoft.azure.functions.sql.annotation.SQLTrigger)。 此批註支援下列元素:

元素 描述
name 必要。 觸發程式系結至的參數名稱。
tableName 必要。 觸發程式所監視之數據表的名稱。
connectionStringSetting 必要。 應用程式設定的名稱,其中包含資料庫 連接字串,其中包含監視變更的數據表。 連接字串 設定名稱會對應至包含 Azure SQL 或 SQL Server 實例 連接字串 的應用程式設定(用於local.settings.json本機開發)。
LeasesTableName 選擇性。 用來儲存租用的數據表名稱。 如果未指定,租用數據表名稱將會Leases_{FunctionId}_{TableId}。 如需如何產生此項目的詳細資訊,請參閱 這裡

組態

下表說明您在 function.json 檔案中設定的繫結設定屬性。

function.json 屬性 描述
name 必要。 觸發程式系結至的參數名稱。
type 必要。 必須設定為 sqlTrigger
direction 必要。 必須設定為 in
tableName 必要。 觸發程式所監視之數據表的名稱。
connectionStringSetting 必要。 包含資料庫 連接字串 的應用程式設定名稱,其中包含受監視變更之數據表的資料庫。 連接字串 設定名稱會對應至包含 Azure SQL 或 SQL Server 實例 連接字串 的應用程式設定(用於local.settings.json本機開發)。
LeasesTableName 選擇性。 用來儲存租用的數據表名稱。 如果未指定,租用數據表名稱將會Leases_{FunctionId}_{TableId}。 如需如何產生此項目的詳細資訊,請參閱 這裡

選用設定

您可以為 SQL 觸發程式設定下列選擇性設定:

本節說明 2.x 版和更新版本中此系結可用的組態設定。 host.json檔案中的 設定 會套用至函式應用程式實例中的所有函式。 下列範例host.json檔案只包含此系結的 2.x+ 版設定。 如需 2.x 版和更新版本中函式應用程式組態設定的詳細資訊,請參閱 Azure Functions 的host.json參考。

設定 描述
Sql_Trigger_BatchSize 傳送至觸發程式函式之前,每個觸發程式循環反覆專案所處理的變更數目上限。 預設值是 100。
Sql_Trigger_PollingIntervalMs 處理每個變更批次之間的延遲以毫秒為單位。 預設值為1000 (1秒)。
Sql_Trigger_MaxChangesPerWorker 每個應用程式背景工作角色所允許的用戶數據表中暫止變更數目上限。 如果變更計數超過此限制,可能會導致向外延展。此設定僅適用於已啟用運行時間驅動調整的 Azure Function Apps。 預設值為 1000。

設定變更追蹤 (必要)

設定要與 Azure SQL 觸發程式搭配使用的變更追蹤需要兩個步驟。 您可以從任何支援執行查詢的 SQL 工具完成這些步驟,包括 Visual Studio CodeAzure Data Studio 或 SQL Server Management Studio

  1. 在 SQL 資料庫上啟用變更追蹤,並以要監視之資料表所在的資料庫名稱取代 your database name

    ALTER DATABASE [your database name]
    SET CHANGE_TRACKING = ON
    (CHANGE_RETENTION = 2 DAYS, AUTO_CLEANUP = ON);
    

    選項 CHANGE_RETENTION 會指定保留變更追蹤資訊 (變更歷程記錄) 的時間週期。 SQL 資料庫變更歷程記錄的保留可能會影響觸發程式功能。 例如,如果 Azure 函式關閉數天,然後繼續,資料庫將會包含上述設定範例中過去兩天內發生的變更。

    AUTO_CLEANUP選項可用來啟用或停用移除舊變更追蹤資訊的清除工作。 如果暫時性問題導致觸發程式無法執行,則關閉自動清除有助於暫停移除比保留期間更舊的資訊,直到問題解決為止。

    如需變更追蹤選項的詳細資訊,請參閱 SQL 檔

  2. 在資料表上啟用變更追蹤,並以要監視的數據表名稱取代 your table name (適當時變更架構):

    ALTER TABLE [dbo].[your table name]
    ENABLE CHANGE_TRACKING;
    

    觸發程式必須具有受監視之數據表的讀取許可權,以取得變更和變更追蹤系統數據表的讀取許可權。 每個函式觸發程式在架構 az_func中都有相關聯的變更追蹤數據表和租用數據表。 如果這些數據表還不存在,觸發程式就會建立這些數據表。 如需這些數據結構的詳細資訊,請參閱 Azure SQL 系結連結庫

啟用運行時間驅動調整

或者,您的函式可以根據擱置中的變更數目自動調整,以在用戶數據表中處理。 若要讓函式在使用 SQL 觸發程式時,在 進階版 計劃上適當調整,您必須啟用運行時間調整監視。

在 Azure 入口網站 的函式應用程式中,選擇 [組態],然後在 [函式運行時間設定] 索引標籤上,將 [運行時間規模監視] 轉換成 [開啟]。

Azure 入口網站 面板的螢幕快照,以啟用運行時間調整。

重試支援

GitHub 存放庫中提供 SQL 觸發程式 重試支援租用數據表 的詳細資訊。

啟動重試

如果在啟動期間發生例外狀況,則主機運行時間會自動嘗試使用指數輪詢策略重新啟動觸發程式接聽程式。 這些重試會繼續執行,直到接聽程式成功啟動或取消啟動為止。

中斷的連接重試

如果函式成功啟動,但錯誤會導致連線中斷(例如伺服器離線),則函式會繼續嘗試重新開啟連線,直到函式停止或連線成功為止。 如果成功重新建立連線,則會在中斷時挑選處理變更。

請注意,這些重試是在 SqlClient 可以使用 ConnectRetryCountConnectRetryInterval連接字串 選項設定的內建閑置連線重試邏輯之外。 先嘗試內建閑置連線重試,如果無法重新連線,則觸發程式系結會嘗試重新建立連線本身。

函式例外狀況重試

如果在處理變更時,使用者函式中發生例外狀況,則會在 60 秒內重試目前正在處理的數據列批次。 在此期間,其他變更會正常處理,但造成例外狀況的批次中的數據列會忽略,直到逾時期間過後。

如果指定數據列的數據列中函數執行失敗五次,則所有未來變更都會完全忽略該數據列。 由於批次中的數據列不具決定性,失敗批次中的數據列可能會在後續調用中以不同的批次結束。 這表示失敗批次中的所有數據列不一定會被忽略。 如果批次中的其他數據列是造成例外狀況的數據列,則「良好」數據列最終可能會出現在未來調用中不會失敗的不同批次中。

下一步