Thursday, May 30, 2013
Last week i got myself in a little trouble. I have a back-end website that does a lot of processing stuff with very long running requests (some take days to complete). The website got slow if about 8-9 long running requests were active. These request do not consume a lot of cpu or memory so the problem had to be somewhere in IIS or Coldfusion. I posted a blog about the maximum number of simultaneous templates in coldfusion earlier this month (maximum number of simultaneous templates). Although this could have been an issue here it was not. In the IIS application pool each pool has 1 worker process assigned to it by default. In most cases (read 99%) this is fine, but if you are working with multiple long running request this can become a bottleneck. To resolve the problem you can assign more worker processes to the application pool.
Wednesday, May 15, 2013
A problem you might encouter when working with regular expressions is you can't quit a regex currently in progress. There is no timeout setting. This can potentially freeze your server. The function below uses coldfusion's relatively new cfthread function to bypass this problem. In the example below the regex is quit if it is running for more then 3000 miliseconds.
<cffunction name="timedRegex" access="public" returntype="any" output="true"> <cfargument name="txt" type="string"> <cfargument name="pattern" type="string"> <cfset result = structNew()> <cfset result.success = false> <cfset result.found = arrayNew(1)> <cfset var threadName = "thread_" & rereplace(createUuid(),'-','','all')> <cfthread action="run" name="#threadName#" pattern=#pattern# txt=#txt# result=#result#> <cfset var local = structNew()> <cfset local.objPattern = ''> <cfset local.objMatcher = ''> <cfset local.str = structNew()> <cfset local.c = 0> <cfset local.d = 0> <cfset local.objPattern = CreateObject("java","java.util.regex.Pattern").Compile('#trim(pattern)#') /> <cfset local.objMatcher = local.objPattern.Matcher(txt) /> <cfloop condition="local.objMatcher.Find()"> <cfset result.found[arraylen(result.found)+1] = structNew()> <cfset result.found[arraylen(result.found)].string = objMatcher.Group() /> <cfset result.found[arraylen(result.found)].groups = arrayNew(1) /> <cfloop from=1 to="#objMatcher.groupCount()#" index=local.d> <cfset result.found[arraylen(result.found)].groups[local.d] = objMatcher.Group(local.d) /> </cfloop> </cfloop> <cfset result.success = true> <cfset THREAD.response = result> </cfthread> <cfthread action="join" name="#threadName#" timeout="3000"/> <cfif evaluate(threadName & ".status") eq 'COMPLETED'> <cfreturn evaluate(threadName & ".response")> <cfelse> <cfthread action="terminate" name="#threadName#"/> <cfreturn result> </cfif> </cffunction> <cfdump var="#timedRegex(txt="xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxy",pattern="(x+x+)+(y)")#"> <cfdump var="#timedRegex(txt="xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",pattern="(x+x+)+(y)")#">