在ColdFusion中可能的竞争条件创建结构体 [英] Possible race condition creating Structs in ColdFusion

查看:180
本文介绍了在ColdFusion中可能的竞争条件创建结构体的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在使用相同的方法(不同的代码)的情况下,我在一些系统中看到间歇性错误,导致我相信问题可能与创建和使用结构体相同请求。我想知道是否可能存在竞争条件?

I've been seeing intermittent errors in a couple of systems I've been working on, when using the same methodology (not the same code) leading me to believe the problem may be linked to creating and using structs in the same request. I'm wondering if it's possible there's a race condition?

这种情况是这样的:
我们在电子商务系统上查看产品,或在某些情况下的产品列表。有问题的代码被设计为返回与每个产品相关联的图像,在一个可用于显示所述图像的结构中。

The scenario is this: We're on an e-commerce system, looking at a product, or in some cases a list of products. The code in question is designed to return the images associated with each product, in a struct that we can use for display of said images.

在请求开始时,该代码查找与相关项目相关联的数据库记录。这些记录表示产品的图像。
这些记录在单个 CFQuery 调用中返回(或者更准确地说,是调用返回 CFQuery call,形成一个包含各种信息的结构)。

At the beginning of the request, the code looks for database records associated with the item in question. These records represent images for the product(s). These records are returned in a single CFQuery call (or more accurately, a call to a function which returns the results of a CFQuery call, shaped into a struct containing various info).

然后代码循环遍历提供的图像结构, 。稍后在请求中,我们使用struct中的数据在我们的< img> 标签中显示图像。我们还使用 data - 属性填充< img> 标记以用于JavaScript。

The code then loops through the supplied image struct, and adds various information to a Local struct. Later in the request we use the data in the struct to display the images in our <img> tags. We also populate the <img> tag with data- attributes for use with JavaScript.

如果查询未正确返回任何特定图片,通常是因为缺少物理文件 - 我们使用通用的占位符图片。这是通过将结构创建放在 try / catch 块中。

In the case that any particular image was not correctly returned by the query - usually because the physical file is missing - we use a generic placeholder image. This is done by putting the struct creation inside a try/catch block.

重要的是:

Importantly: this works.

但是,发生了什么事,是间歇性地,当引用我们创建的结构中的一个节点时,发现它不存在,CF会抛出一个错误 - 这可能是1%的时间,并重新加载相同的页面,一切都会正常工作。

What's happening however, is that very intermittently, when referring to a node in the struct we've created, we find that it does not exist and CF throws an error - this happens maybe 1% of the time and reloading the same page, everything will work perfectly.

在多个系统上,在多个服务器上,在不同版本的ColdFusion(8& 10是特定的)上并且使用完全不同的代码来实现类似的结果的同样的问题。
第一个系统我看到这个问题,实际使用 FileExists 来检查图像文件是否可用,因此我认为问题可能是由瓶颈的文件系统 - 我尝试了很多方法,并最终在新系统中完全消除它,但问题仍然存在。

I've had this same problem on multiple systems, on multiple servers, on different versions of ColdFusion (8 & 10 to be specific) and using completely different code to achieve similar results. The first system I saw this issue on, actually used FileExists to check that the image file was available and thus I thought that the problem was probably caused by the bottleneck of the filesystem - I tried many ways around this and eventually eliminated it altogether in the new system - but the problem persists.

我唯一能想到的是,当创建一个结构体然后在同一个请求中使用该结构体时,就有可能发生竞争条件;从而在结构创建之前引用结构中的一个节点。我不是在使用线程,所以我不能真正看到这是可能的...我有其他想法。

The only thing I can think of, is that when creating a struct and then using that struct later in the same request, there's a possibility that a race condition occurs; whereby I refer to a node in the struct before it's finished being created. I'm not using threading here though, so I can't really see how that's possible... I'm out of other ideas.

一些代码在下面显示我在做什么,但鉴于同样的问题出现在完全不同的系统上,我认为这是方法,而不是代码有问题。

Some code is below to show what I'm doing, but given that the same issue arises on completely different systems, I think it's the methodology rather than the code that has a problem.

<!--- Get product images --->
<cfset Local.stProductImages = Application.cfcParts.getPartImages(
        l_iItemID = Arguments.pid
) />


<!--- Loop through images --->
<cfloop list="#ListSort(structKeyList(Local.stProductImages['item_' & Arguments.pid]), 'text')#" index="i">
    <cftry>
        <cfset Local['ImageURL_' & i & '_Large']    = Local.stProductImages['item_' & Local.arguments.pid][i].large_watermarked.URL />
        <cfcatch>
            <cfset Local['ImageURL_' & i & '_Large']    = Application.com.Images.getMissingImages().large />
        </cfcatch>
    </cftry>                        
    <cftry>
        <cfset Local['ImageURL_' & i & '_Med']      = Local.stProductImages['item_' & Local.arguments.pid][i].med.URL />
        <cfcatch>
            <cfset Local['ImageURL_' & i & '_Med']      = Application.com.Images.getMissingImages().med />
        </cfcatch>
    </cftry>                        
    <cftry>
        <cfset Local['ImageURL_' & i & '_Small']        = Local.stProductImages['item_' & Local.arguments.pid][i].small.URL />
        <cfcatch>
            <cfset Local['ImageURL_' & i & '_Small']        = Application.com.Images.getMissingImages().small />
        </cfcatch>
    </cftry>                        

    <img class          = "altProdImg<cfif i EQ 'image_03'> endImage</cfif>" 
        src             = "#Local['ImageURL_' & i & '_Small']#" 
        image           = "#i#" 
        alt             = ""
        data-imgsmall   = "#Local['ImageURL_' & i & '_Small']#"
        data-imgmed     = "#Local['ImageURL_' & i & '_Med']#"
        data-imglarge   = "#Local['ImageURL_' & i & '_Large']#"
        data-imgnum     = "#i#"
        data-pid        = "#Arguments.pid#"
    />
</cfloop>

错误发生在< img> 标签,当引用前面代码中创建的节点时 - 类似于:

The error occurs in the <img> tag, when referring to a node created in the preceding code - Something like:


元素ImageURL_image_02_Large在类型类的Java对象中未定义coldfusion.runtime.LocalScope。

Element ImageURL_image_02_Large is undefined in a Java object of type class coldfusion.runtime.LocalScope.

但是只是偶尔...我会重新载入,每次都能正常运作。

But only very occasionally... I'll reload and it'll work perfectly every time.

所以...对于问题的史诗长度,对任何人都可以看到这可能发生吗?

So... sorry for the epic length of question, but can anybody see how this could occur?

推荐答案

从评论中回答...

Answer from comments...

不是var scoping,所以可以像在cfloop标签中使用 index =local.i一样简单地修改(在写变量时只需要范围)。

The behaviour you describe is symptomatic of not var scoping, so it might be as simple to fix as using index="local.i" in the cfloop tag (you only need the scoping when writing the variable).



附注:一种相对简单的方法,可以检查您是否在某项功能中,代码,是通过抛出一个错误(即< cfthrow message =where am i?/> )然后检查堆栈跟踪 - c $ c> coldfusion.runtime.UDFMethod 或 $ funcSTUFF.runFunction(filename:line)你知道你在一个函数您所在的模板没有显示任何迹象)。


Side note: A relatively easy way to check if you're in a function, without going through code, is by throwing an error (i.e. <cfthrow message="where am i?" />) then check the stack trace - if you see stuff like coldfusion.runtime.UDFMethod or $funcSTUFF.runFunction(filename:line) you know you're inside a function (even when the template you're in shows no sign of it).

这篇关于在ColdFusion中可能的竞争条件创建结构体的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆