2016-10-28 107 views
0

我们有两个使用TimerTrigger运行的Azure Webjob的部署(Prod和Test)。这两个Web应用程序都有单个实例。根据this article,TimeTriggers使用单例锁确保没有并行调用。这两个实例使用相同的存储帐户。我们面临的问题是,只有其中一个部署似乎获得锁定,而其他部门无法获得锁定。如果我们停止第一次webjob,第二次获得锁定并开始处理,反之亦然。Azure Webjob计时器触发器不会触发

锁是否依赖于存储帐户?我们如何确保这两个部署具有单独的锁定机制并同时运行?

回答

4

你说的没错,你必须使用不同的存储账户。

documentation

在幕后,TimerTrigger使用WebJobs SDK的辛格尔顿功能,以确保只有您的触发功能的单个实例在任何给定的时间运行。 当JobHost启动时,对于您的每个TimerTrigger函数,blob租约(Singleton锁)被采取。此分布式锁可确保只有您的预定功能的单个实例随时处于运行状态。如果该函数的blob目前没有租用,该函数将获得租约并立即开始按计划运行。 如果无法获取blob lease,通常意味着该功能的另一个实例正在运行,所以该函数不会在当前主机中启动。发生这种情况时,主机将继续定期检查是否可以获得租约。这是作为一种“恢复”模式完成的,以确保在运行稳定状态时,如果实例发生故障,另一个实例会通知并从另一个实例停止。

如果你看一下锁定mecanism的实现(StorageScheduleMonitor.cs):

  • 的工作取得容器内的锁(BLOB)。
  • blob位于特定目录内(基于HostId)。
  • blob的名称不可配置。

因此,基于@弗拉基米尔 - bilyachat的答案,有两种可能性:

  • 有上分离的存储账户:是有道理的,如果你有每个环境(开发/分期/ PROD)存储帐户

  • 指定JobHostConfiguration类的HosId属性:

    var config = new JobHostConfiguration(); 
    config.HostId = "dev|staging|prod"; 
    
+0

'Blob租赁'是指存储宽锁吗?这对我来说没有意义,一个锁被用于多个部署。 –

+0

更新了我的答案 – Thomas

0

如果您使用TimerTrigger,请确保您的Web App上启用了Always On。

2

使用不同的存储账户或设置主机

var config = new JobHostConfiguration(); 
config.HostId = "dev|prod" 
var host = new JobHost(config); 
host.RunAndBlock(); 
+0

你确定HostId?它看起来更关于缩放。 – Thomas

+0

@Thomas当我使用相同的存储设备进行开发和分期时,我遇到了同样的问题。它可以帮助我 –

+0

好吧知道:-)当我遇到这个问题时,我创建了不同的存储账户 – Thomas