当前位置: 首页 > 知识库问答 >
问题:

如何使用文件#flock对独占锁进行非阻塞请求?

司寇灵均
2023-03-14

当分别尝试锁定一个文件时,为什么Ruby的File#flock不能像预期的那样工作?在块中锁定文件不是解决此问题的正确方法,因为关键是显示锁定持久锁的行为。在块中使用File#flock会在块退出时释放锁,因此无法正确演示问题。

File#flock会以多种方式失败,特别是在请求非阻塞锁时。下面是一些例子。

>

# First lock succeeds.
f1 = File.open('foo', File::RDWR|File::CREAT, 0644)
f1.flock(File::LOCK_EX)
# => 0

# This never returns.
f2 = File.open('foo', File::RDWR|File::CREAT, 0644)
f2.flock(File::LOCK_EX)

当文件被独占锁定时,请求非阻塞锁会导致无效的html" target="_blank">参数异常。

f1 = File.open('foo', File::RDWR|File::CREAT, 0644)
f1.flock(File::LOCK_EX)
# => 0

f2 = File.open('foo', File::RDWR|File::CREAT, 0644)
f2.flock(File::LOCK_NB)
# => Errno::EINVAL: Invalid argument - foo

留档表示#flock根据locking_constant(下表中的逻辑值或值)锁定或解锁文件。但是,逻辑或引发Errno::EINVALErrno::EBADF取决于平台。

f1 = File.open('foo', File::RDWR|File::CREAT, 0644)
f1.flock(File::LOCK_EX)
# => 0

f2 = File.open('foo', File::RDWR|File::CREAT, 0644)
f2.flock(File::LOCK_NB || File::LOCK_EX)
# => Errno::EINVAL: Invalid argument - foo

当无法获得排他锁时,可以使用超时模块引发Timeout::Error,但File#flock似乎应该能够以本机方式解决此问题。那么,在没有阻塞的情况下,如何请求独占锁呢?

共有1个答案

楮星鹏
2023-03-14

您可以使用超时模块设置#flock获取独占锁的持续时间。下面的示例将引发Timeout::Error:execution expired,然后可以以适用于应用程序的任何方式对其进行解救。计时器过期时返回nil允许测试#flock表达式的真实性。

require 'timeout'

f1 = File.open('foo', File::RDWR|File::CREAT, 0644)
f1.flock(File::LOCK_EX)
# => 0

f2 = File.open('foo', File::RDWR|File::CREAT, 0644)
Timeout::timeout(0.001) { f2.flock(File::LOCK_EX) } rescue nil
# => nil

文件#flock的文档说明:

根据locking_常量(下表中的逻辑or值)锁定或解锁文件。如果指定了File::LOCK_NB,则返回false,否则操作将被阻止。

但是,该方法实际上需要按位OR运算符,而不是解析中定义的逻辑OR关键字。通过tOROP解析器标记返回y。因此,当独占锁失败时,允许#flock返回false的正确参数实际上是File::lock\u NB | File::lock\u EX。例如:

f1 = File.open('foo', File::RDWR|File::CREAT, 0644)
f1.flock(File::LOCK_EX|File::LOCK_NB)
# => 0

f2 = File.open('foo', File::RDWR|File::CREAT, 0644)
f2.flock(File::LOCK_NB|File::LOCK_EX)
# => false

f1.close; f2.close
# => nil

这将在可用时始终生成独占锁;否则,它会立即返回一个falsy值,而不会引发或挽救异常。这显然是模块的预期使用方式,但文档可以使用一些说明和附加示例,使其更易于理解。

 类似资料:
  • 本文向大家介绍php使用flock阻塞写入文件和非阻塞写入文件的实例讲解,包括了php使用flock阻塞写入文件和非阻塞写入文件的实例讲解的使用技巧和注意事项,需要的朋友参考一下 阻塞写入代码:(所有程序会等待上次程序执行结束才会执行,30秒会超时) 非阻塞写入代码:(只要文件被占用,则显示Error locking file!) 以上这篇php使用flock阻塞写入文件和非阻塞写入文件的实例讲解

  • 问题内容: 我正在使用PHP从远程服务器下载一个(大)文件,并且此下载是通过单击网页上的下载按钮触发的。 因此,当我单击网页上的按钮时,就会向PHP函数发出请求(带有angulars )。该函数使用触发下载。 同时,我想使用Ajax向我的PHP网站提出其他请求。但是,只要下载正在进行,所有其他Ajax请求都会显示状态。 因此,基本上,下载阻止了对PHP的所有其他请求。有什么办法可以避免这种阻塞?

  • 我完全混淆了,,。 哪个是阻塞,哪个不是? 我的意思是如果我使用父进程是否等待子进程返回/才继续执行。 如何影响这些调用?

  • 问题内容: Java中是否有非阻塞文件读取API?如果不是,在C ++中构建一个并通过JNI从Java应用程序中调用它是否明智? 问题答案: 不,不扩展。 可能是因为并非所有的操作系​​统都支持它。 Windows确实如此,从理论上讲,您可以编写Windows特定的C ++库,并通过JNI进行调用,但是将其与集成是很多工作。 我宁愿有一个工作线程将文件内容复制到管道中,并在管道的另一端进行非阻塞读

  • 问题内容: 我在芹菜中使用Python进行大量的(〜10 / sec)API调用(包括GET,POST,PUT,DELETE)。每个请求大约需要5-10秒才能完成。 我尝试在池中运行芹菜工人,并发数为1000。 由于正在阻塞进程,每个并发连接都在等待一个请求。 如何使异步? 问题答案: 使用eventlet Monkey patching使所有纯python库都无阻塞。 补丁单库 import e

  • 我需要一些使用RxJava2实现并行异步调用的帮助 1) 我有多个保险公司(目前我只接受两个),我需要使用该保险公司的名称发送多个并行请求。 2)如果其中任何一个给服务器错误,那么剩余的请求不应该被阻止。 以下是我迄今为止所做的尝试; 现在,只有当两个请求都成功响应时,上述代码才能正常工作。但是当任何请求作为内部服务器错误给出响应时,其余请求也会被阻止。 当任何请求给出失败响应时,我得到以下日志错