Azure Functions 的计时器触发器Timer trigger for Azure Functions

本文介绍如何在 Azure Functions 中使用计时器触发器。This article explains how to work with timer triggers in Azure Functions. 计时器触发器可以按计划运行函数。A timer trigger lets you run a function on a schedule.

此参考信息面向 Azure Functions 开发人员。This is reference information for Azure Functions developers. Azure Functions 的新手请从以下资源入手:If you're new to Azure Functions, start with the following resources:

包 - Functions 1.xPackages - Functions 1.x

Microsoft.Azure.WebJobs.Extensions NuGet 包 2.x 版中提供了计时器触发器。The timer trigger is provided in the Microsoft.Azure.WebJobs.Extensions NuGet package, version 2.x. azure-webjobs-sdk-extensions GitHub 存储库中提供了此包的源代码。Source code for the package is in the azure-webjobs-sdk-extensions GitHub repository.

C# 类库C# class library

对于 C# 类库开发,自动在项目中安装该包。For C# class library development, the package is automatically installed in the project.

Functions 2.x 中的绑定扩展Binding extensions in Functions 2.x

对于 Azure Functions 2.x 版中的本地开发,该包自动注册为绑定扩展For local development in Azure Functions version 2.x, the package is automatically registered as a binding extension.

包 - Functions 2.x 及更高版本Packages - Functions 2.x and higher

Microsoft.Azure.WebJobs.Extensions NuGet 包 3.x 版中提供了计时器触发器。The timer trigger is provided in the Microsoft.Azure.WebJobs.Extensions NuGet package, version 3.x. azure-webjobs-sdk-extensions GitHub 存储库中提供了此包的源代码。Source code for the package is in the azure-webjobs-sdk-extensions GitHub repository.

C# 类库C# class library

对于 C# 类库开发,自动在项目中安装该包。For C# class library development, the package is automatically installed in the project.

Functions 2.x 中的绑定扩展Binding extensions in Functions 2.x

对于 Azure Functions 2.x 版中的本地开发,该包自动注册为绑定扩展For local development in Azure Functions version 2.x, the package is automatically registered as a binding extension.

示例Example

以下示例显示了一个 C# 函数,每当分钟的值可被 5 整除时,就执行该函数(例如,如果函数起始于 18:57:00,则下一次执行函数的时间为 19:00:00)。The following example shows a C# function that is executed each time the minutes have a value divisible by five (eg if the function starts at 18:57:00, the next performance will be at 19:00:00). TimerInfo 对象将传递到函数中。The TimerInfo object is passed into the function.

[FunctionName("TimerTriggerCSharp")]
public static void Run([TimerTrigger("0 */5 * * * *")]TimerInfo myTimer, ILogger log)
{
    if (myTimer.IsPastDue)
    {
        log.LogInformation("Timer is running late!");
    }
    log.LogInformation($"C# Timer trigger function executed at: {DateTime.Now}");
}

特性和注释Attributes and annotations

C# 类库中,使用 TimerTriggerAttributeIn C# class libraries, use the TimerTriggerAttribute.

该特性的构造函数采用 CRON 表达式或 TimeSpanThe attribute's constructor takes a CRON expression or a TimeSpan. 仅当函数应用在应用服务计划中运行时才能使用 TimeSpanYou can use TimeSpan only if the function app is running on an App Service plan. 消耗计划不支持 TimeSpanTimeSpan is not supported for Consumption Functions.

以下示例显示了一个 CRON 表达式:The following example shows a CRON expression:

[FunctionName("TimerTriggerCSharp")]
public static void Run([TimerTrigger("0 */5 * * * *")]TimerInfo myTimer, ILogger log)
{
    if (myTimer.IsPastDue)
    {
        log.LogInformation("Timer is running late!");
    }
    log.LogInformation($"C# Timer trigger function executed at: {DateTime.Now}");
}

配置Configuration

下表解释了在 function.json 文件和 TimerTrigger 特性中设置的绑定配置属性。The following table explains the binding configuration properties that you set in the function.json file and the TimerTrigger attribute.

function.json 属性function.json property Attribute 属性Attribute property 说明Description
typetype 不适用n/a 必须设置为“timerTrigger”。Must be set to "timerTrigger". 在 Azure 门户中创建触发器时,会自动设置此属性。This property is set automatically when you create the trigger in the Azure portal.
directiondirection 不适用n/a 必须设置为“in”。Must be set to "in". 在 Azure 门户中创建触发器时,会自动设置此属性。This property is set automatically when you create the trigger in the Azure portal.
namename 不适用n/a 在函数代码中表示计时器对象的变量的名称。The name of the variable that represents the timer object in function code.
scheduleschedule ScheduleExpressionScheduleExpression CRON 表达式TimeSpan 值。A CRON expression or a TimeSpan value. 只能对在应用服务计划中运行的函数应用使用 TimeSpanA TimeSpan can be used only for a function app that runs on an App Service Plan. 可以将计划表达式放在应用设置中并将此属性设置为用 % 符号括起的应用设置名称,例如此示例中的“%ScheduleAppSetting%”。You can put the schedule expression in an app setting and set this property to the app setting name wrapped in % signs, as in this example: "%ScheduleAppSetting%".
runOnStartuprunOnStartup RunOnStartupRunOnStartup 如果为 true,则在运行时启动时调用此函数。If true, the function is invoked when the runtime starts. 例如,当函数应用从由于无活动而进入的空闲状态醒来后,运行时会启动。For example, the runtime starts when the function app wakes up after going idle due to inactivity. 当函数应用由于函数更改而重新启动时,以及当函数应用横向扩展时。因此 runOnStartup 应该很少设置为 true,特别是在生产中。when the function app restarts due to function changes, and when the function app scales out. So runOnStartup should rarely if ever be set to true, especially in production.
useMonitoruseMonitor UseMonitorUseMonitor 设置为 truefalse 以指示是否应当监视计划。Set to true or false to indicate whether the schedule should be monitored. 计划监视在各次计划发生后会持续存在,以帮助确保即使在函数应用实例重新启动的情况下也能正确维护计划。Schedule monitoring persists schedule occurrences to aid in ensuring the schedule is maintained correctly even when function app instances restart. 如果未显式设置,则对于重复周期间隔大于或等于 1 分钟的计划,默认值为 trueIf not set explicitly, the default is true for schedules that have a recurrence interval greater than or equal to 1 minute. 对于每分钟触发多次的计划,默认值为 falseFor schedules that trigger more than once per minute, the default is false.

在本地进行开发时,应用设置将取 local.settings.json 文件的值。When you're developing locally, app settings go into the local.settings.json file.

注意

在生产中不建议将 runOnStartup 设置为 trueWe recommend against setting runOnStartup to true in production. 使用此设置会使代码在非常不可预测的时间执行。Using this setting makes code execute at highly unpredictable times. 在某些生产设置中,这些额外执行可能会导致消耗计划中托管的应用产生明显更高的成本。In certain production settings, these extra executions can result in significantly higher costs for apps hosted in Consumption plans. 例如,启用 runOnStartup 后,只要缩放函数应用,就会调用触发器。For example, with runOnStartup enabled the trigger is invoked whenever your function app is scaled. 在生产中启用 runOnStartup 之前,请确保完全了解函数的生产行为。Make sure you fully understand the production behavior of your functions before enabling runOnStartup in production.

使用情况Usage

调用计时器触发器函数时,计时器对象将传递到函数中。When a timer trigger function is invoked, a timer object is passed into the function. 以下 JSON 是计时器对象的示例表示形式。The following JSON is an example representation of the timer object.

{
    "Schedule":{
    },
    "ScheduleStatus": {
        "Last":"2016-10-04T10:15:00+00:00",
        "LastUpdated":"2016-10-04T10:16:00+00:00",
        "Next":"2016-10-04T10:20:00+00:00"
    },
    "IsPastDue":false
}

如果当前函数调用晚于计划时间,则 IsPastDue 属性为 trueThe IsPastDue property is true when the current function invocation is later than scheduled. 例如,函数应用重新启动可能会导致调用被错过。For example, a function app restart might cause an invocation to be missed.

NCRONTAB 表达式NCRONTAB expressions

Azure Functions 使用 NCronTab 库来解释 NCRONTAB 表达式。Azure Functions uses the NCronTab library to interpret NCRONTAB expressions. NCRONTAB 表达式类似于 CRON 表达式,不同之处在于它在开头包含额外的第六个字段,用于以秒为单位的时间精度:An NCRONTAB expression is similar to a CRON expression except that it includes an additional sixth field at the beginning to use for time precision in seconds:

{second} {minute} {hour} {day} {month} {day-of-week}

每个字段可以具有下列类型之一的值:Each field can have one of the following types of values:

类型Type 示例Example 何时触发When triggered
一个具体值A specific value "0 5 * * * *""0 5 * * * *" 在 hh:05:00,其中 hh 表示每小时(每小时一次)at hh:05:00 where hh is every hour (once an hour)
所有值 (*)All values (*) "0 * 5 * * *""0 * 5 * * *" 在每天的 5:mm:00,其中 mm 表示该小时的每分钟(一天 60 次)at 5:mm:00 every day, where mm is every minute of the hour (60 times a day)
一个范围(- 运算符)A range (- operator) "5-7 * * * * *""5-7 * * * * *" 在 hh:mm:05、hh:mm:06 和 hh:mm:07,其中 hh:mm 表示每小时的每分钟(每分钟 3 次)at hh:mm:05,hh:mm:06, and hh:mm:07 where hh:mm is every minute of every hour (3 times a minute)
一组值(, 运算符)A set of values (, operator) "5,8,10 * * * * *""5,8,10 * * * * *" 在 hh:mm:05、hh:mm:08 和 hh:mm:10,其中 hh:mm 表示每小时的每分钟(每分钟 3 次)at hh:mm:05,hh:mm:08, and hh:mm:10 where hh:mm is every minute of every hour (3 times a minute)
一个间隔值(/ 运算符)An interval value (/ operator) "0 */5 * * * *""0 */5 * * * *" 在 hh:00:00、hh:05:00、hh:10:00,依此类推,直到 hh:55:00,其中 hh 表示每小时(每小时 12 次)at hh:00:00, hh:05:00, hh:10:00, and so on through hh:55:00 where hh is every hour (12 times an hour)

若要指定月份或天,可以使用数字值、名称或名称的缩写:To specify months or days you can use numeric values, names, or abbreviations of names:

  • 对于天,数字值为 0 到 6,其中 0 表示星期日。For days, the numeric values are 0 to 6 where 0 starts with Sunday.
  • 名称采用英语。Names are in English. 例如:MondayJanuaryFor example: Monday, January.
  • 名称不区分大小写。Names are case-insensitive.
  • 名称可缩写。Names can be abbreviated. 三字母是建议的缩写长度。Three letters is the recommended abbreviation length. 例如:MonJanFor example: Mon, Jan.

NCRONTAB 示例NCRONTAB examples

以下是一些可用于 Azure Functions 中计时器触发器的 NCRONTAB 表达式示例。Here are some examples of NCRONTAB expressions you can use for the timer trigger in Azure Functions.

示例Example 何时触发When triggered
"0 */5 * * * *" 每五分钟一次once every five minutes
"0 0 * * * *" 每小时一次(在每小时的开头)once at the top of every hour
"0 0 */2 * * *" 每两小时一次once every two hours
"0 0 9-17 * * *" 从上午 9 点到下午 5 点每小时一次once every hour from 9 AM to 5 PM
"0 30 9 * * *" 每天上午 9:30at 9:30 AM every day
"0 30 9 * * 1-5" 每个工作日的上午 9:30at 9:30 AM every weekday
"0 30 9 * Jan Mon" 在一月份每星期一的上午 9:30at 9:30 AM every Monday in January

NCRONTAB 时区NCRONTAB time zones

CRON 表达式中的数字指的是时间和日期,而不是时间跨度。The numbers in a CRON expression refer to a time and date, not a time span. 例如,hour 字段中的 5 指的是 5:00 AM,而不是每 5 小时。For example, a 5 in the hour field refers to 5:00 AM, not every 5 hours.

CRON 表达式使用的默认时区为协调世界时 (UTC)。The default time zone used with the CRON expressions is Coordinated Universal Time (UTC). 若要让 CRON 表达式基于其他时区,请为你的函数应用创建一个名为 WEBSITE_TIME_ZONE 的应用设置。To have your CRON expression based on another time zone, create an app setting for your function app named WEBSITE_TIME_ZONE. 将值设置为所需时区的名称,如 Microsoft 时区索引中所示。Set the value to the name of the desired time zone as shown in the Microsoft Time Zone Index.

例如,东部标准时间 是 UTC-05:00。For example, Eastern Standard Time is UTC-05:00. 若要让计时器触发器每天在美国东部时间上午 10:00 触发,可使用表示 UTC 时区的以下 NCRONTAB 表达式:To have your timer trigger fire at 10:00 AM EST every day, use the following NCRONTAB expression that accounts for UTC time zone:

"0 0 15 * * *"

或者为你的函数应用创建一个名为 WEBSITE_TIME_ZONE 的应用设置并将值设置为 Eastern Standard TimeOr create an app setting for your function app named WEBSITE_TIME_ZONE and set the value to Eastern Standard Time. 然后使用以下 NCRONTAB 表达式:Then uses the following NCRONTAB expression:

"0 0 10 * * *"

当使用 WEBSITE_TIME_ZONE,时间将针对特定时区中的时间更改进行调整,例如夏令时。When you use WEBSITE_TIME_ZONE, the time is adjusted for time changes in the specific timezone, such as daylight savings time.

TimeSpanTimeSpan

只能对在应用服务计划中运行的函数应用使用 TimeSpanA TimeSpan can be used only for a function app that runs on an App Service Plan.

与 CRON 表达式不同,TimeSpan 值指定各次函数调用之间的时间间隔。Unlike a CRON expression, a TimeSpan value specifies the time interval between each function invocation. 如果函数的运行时间超出了指定的时间间隔,则在函数完成时,计时器会立即再次调用该函数。When a function completes after running longer than the specified interval, the timer immediately invokes the function again.

以字符串表示,当 hh 小于 24 时,TimeSpan 格式为 hh:mm:ssExpressed as a string, the TimeSpan format is hh:mm:ss when hh is less than 24. 当前两个数字是 24 或更大的数字时,格式为 dd:hh:mmWhen the first two digits are 24 or greater, the format is dd:hh:mm. 下面是一些示例:Here are some examples:

示例Example 何时触发When triggered
"01:00:00""01:00:00" 每小时every hour
"00:01:00""00:01:00" 每分钟every minute
"24:00:00""24:00:00" 每 24 天every 24 days
"1.00:00:00""1.00:00:00" 每天every day

横向扩展Scale-out

如果函数应用横向扩展到多个实例,则在所有实例中只会运行由计时器触发的函数的单个实例。If a function app scales out to multiple instances, only a single instance of a timer-triggered function is run across all instances.

共享同一存储的函数应用Function apps sharing Storage

如果要在未部署到应用服务的函数应用之间共享存储帐户,则可能需要为每个应用显式分配主机 ID。If you are sharing storage accounts across function apps that are not deployed to app service, you might need to explicitly assign host ID to each app.

Functions 版本Functions version 设置Setting
2.x(及更高版本)2.x (and higher) AzureFunctionsWebHost__hostid 环境变量AzureFunctionsWebHost__hostid environment variable
1.x1.x host.json 中的 idid in host.json

可以省略标识值,也可以手动将每个函数应用的标识配置设置为不同的值。You can omit the identifying value or manually set each function app's identifying configuration to a different value.

计时器触发器使用存储锁来确保当函数应用横向扩展到多个实例时将只有一个计时器实例。The timer trigger uses a storage lock to ensure that there is only one timer instance when a function app scales out to multiple instances. 如果两个函数应用共享相同的标识配置,并且每个函数应用都使用一个计时器触发器,则只有一个计时器运行。If two function apps share the same identifying configuration and each uses a timer trigger, only one timer runs.

重试行为Retry behavior

与队列触发器不同,计时器触发器在函数失败后不会重试。Unlike the queue trigger, the timer trigger doesn't retry after a function fails. 函数失败时,在计划的下次时间到来前,不会再次调用该函数。When a function fails, it isn't called again until the next time on the schedule.

故障排除Troubleshooting

有关在计时器触发器未按预期工作的情况下应采取的措施,请参阅调查和报告有关计时器触发功能未触发的问题For information about what to do when the timer trigger doesn't work as expected, see Investigating and reporting issues with timer triggered functions not firing.

后续步骤Next steps