Request Timeout (was:Lucee and the future)

I get what you mean, and in general I err towards OO code over procedural
where possible too. However I also think cocking around adding new language
constructs is something that should be treated with extreme caution.

Yup.

My challenge here is that I think adding a time out to try/catch is just
wrong, so another approach is needed. It’s not that I think it’s better
or worse than a closure-based option (or even the other syntax variation
mentioned, which I’ll get to), I just think it’s absolutely the wrong and a
syntactically invalid approach.

This is where we must agree to disagree. It’s certainly unprecedented, but
that in and of itself is not a reason to not avoid it. It could be I’m
missing something, but I do see a certain elegance in it. It reads well to
me.

Some people would fall back to that “tags without angle brackets in
script” syntax for a solution, which - IMO - isn’t as bad in theory,
however I think the actual syntax variation is lazy and inelegant language
design which ought to be phased out of CFML… in favour of a “closure”
approach
.

I dunno if you read my blog or saw my earlier link, but I put my position
forward here:
Adam Cameron's Dev Blog: CFML: the evolution of functionality
http://www.google.com/url?q=http%3A%2F%2Fblog.adamcameron.me%2F2015%2F01%2Fcfml-evolution-of-functionality.html&sa=D&sntz=1&usg=AFQjCNErjIL26-DoX1tXSJUPlI-cDt6rZg

I have read it, and since you asked, TBH I’m not entirely sold that its bad
form. I think all that script tags need is to return its result instead of
assigning it to a variable based on a required attribute. I think I
remember that being suggested somewhere by Micha or Igal. I agree that ACF
devs completely blew it with their cftag() {} syntax, especially after
partially implementing the Railo/Lucee style.

My point was I saw a *possibility *of a race condition where a database
exception occurs at the same time the timeout occurs, in which case, are
the catch/finally blocks allowed to complete? From the way the request
timeout currently operates, I’m not sure that it would. If they are
allowed to complete - could the timeout handler execute first? Possibly.
Are these major blockers - no, just extra things to consider. However,
these are non-issues with the try/catch.

Don’t follow you here sorry. Try again? (I might just be being thick).

I was trying to think of potential problems with implementation. Say you
have a try inside the first callback. The outside thread times out the
callback execution at the same time a database exception is triggered.
What gets run? Does the catch block execute in addition to the timeout
handler? In what order? Does the callback execute in a separate thread?
Is it always the same order? I have spent too much of my life chasing down
race condition errors, I’m perhaps hypersensitive to it.

You’re inventing a shortcoming here. …

What can I say, you caught me. Not knowing what could potentially be put
into the context argument, I cannot argue what it cannot do.

Well, that’s about all I got, at least for now. Sounds like several
threads may need to be started from this convo, but it’s way too late for
that right now, at least for me.

Jesse

Hi all,

Are there any updates or common workaround about this thread and the issue ?
I use Lucee 4.5.1 and I need to catch requestTimeout exceptions. I’m not
focusing on the syntax but more on the feature needed.
I don’t want to “pull out the plug” but only notified when a requestTimeout
occurs and perform some processing (e.g in another thread limited by the
same request timeout) no matter if the timed out thread continues .On Thursday, February 12, 2015 at 10:13:31 AM UTC+1, Micha wrote:

Inside the “Request Timeout” thread was a discussion going on that was
pointing out that a request timeout cannot be catched by a try/catch, what
seems possible in ACF.
In my opinion this is a bug in ACF here here is my explanation why:

“Like i said, a request timeout is like pulling the plug, i assume you do
not pull the plug on your computer when you are done working, this has the
risk to destroy open file when they are in a transition. You only pull the
plug when the computer is frozen.With running requests it is exactly the
same, a request timeout always comes with the risk to destroy something,
maybe the request was just writing a file that then is only halfway done or
you have open streams that not get closed properly anymore …so you should
avoid request timeouts at any coast and never ever try to deal with them.if
a request timeout occurs, you need to find out why and solve that
problem.that is btw exactly the same as caching runtimeexcpetions in java,
that smells!”

The reason i’m writing all of this is because something else come to my
mind we discussed some time ago, sometimes it is maybe impossible to “fix”
a code segment that leads to a request timeout. Simply because that code
segment, for example, is dealing with external resources, you have no
influence on how long it takes for them to get done.

I had that problem in the Lucee admin when calling the ExtensionProvider
to get information from them. So i did the following (simplified):

// call the extension provider (maybe takes some time)
thread name=“getData” {
request.data=getDataFromExtensionProvider();
}

// give the thread a chance to finish
end=getTickCount()*10000;// now + 10 seconds
do {
sleep(100);// take a nap
}while(getData.status!=“completed” && getTickcount()>end); // wait until
the thread is done or we waited more than 10 seconds

if(getData.status!=“completed”) return request.data;
throw “not able to get data”;

So the idea is to do a new tag to does exactly this:
timeout timespan=“#createTimeSpan(0,0,0,10)#” result=“res” {
data=getDataFromExtensionProvider();
}
if(res.status==“completed”) return data;
throw “not able to get data”;

So you have a code block where you can define how long Lucee maximal can
spend time on it and stopping only that block if you want.
So you can avoid a request timeout by using this tag for time sensitive
code fragments.

What do you think?

Micha

After browsing Lucee’s sources I noticed a difference between my current
version and the master branch.

In my current version (4.5.1.000), the RequestTimeoutException is not put
into the PageContext and a try/catch’s “finally” block is always executed
even if there’s a request timeout.
That way I could do some processing in the “finally” block before the
request timeout is reported in logs. But I cannot get the
RequestTimeoutException.
Event I can find a workaround to thrown my own exception by checking
processing duration, I didn’t insist…

In the master branch the RequestTimeoutException is added to the
PageContext when the request timeout is detected.
Then the PageContext’s thread is properly stopped (instead of deprecated
Thread.stop()) so “finally” block is no longer executed as before.
The RequestTimeoutException is still available through
PageContext.getStopPosition() and that was not the case in 4.5.1.000

This behaviour is not perfect but it allows me to workaround and meet my
needs (e.g checking getStopPosition() in onRequestEnd() for REST component
and/or onError() for else).
So I’ve just updated from 4.5.1.000 to 4.5.1.015 (I could have manually
picked an higher version but this was the only version Lucee server admin
suggest me)
I think it’s not a good practice because I rely on Lucee’s internal
implementation but I need to be notified on request timeout errors…
Most notably I’ve seen that the page context is released before the
RequestTimeoutException is created and passed to SystemUtil.stop().
Thus I not really sure if I can rely on PageContext.getStopPosition() but
it is my only choice here…
I’ve tried it out and decide later if I come back to 4.5.1.000 and its
“finally” block (not better).On Wednesday, May 27, 2015 at 12:06:58 PM UTC+2, Desmond Miles wrote:

Hi all,

Are there any updates or common workaround about this thread and the issue
?
I use Lucee 4.5.1 and I need to catch requestTimeout exceptions. I’m not
focusing on the syntax but more on the feature needed.
I don’t want to “pull out the plug” but only notified when a
requestTimeout occurs and perform some processing (e.g in another thread
limited by the same request timeout) no matter if the timed out thread
continues .

On Thursday, February 12, 2015 at 10:13:31 AM UTC+1, Micha wrote:

Inside the “Request Timeout” thread was a discussion going on that was
pointing out that a request timeout cannot be catched by a try/catch, what
seems possible in ACF.
In my opinion this is a bug in ACF here here is my explanation why:

“Like i said, a request timeout is like pulling the plug, i assume you
do not pull the plug on your computer when you are done working, this has
the risk to destroy open file when they are in a transition. You only pull
the plug when the computer is frozen.With running requests it is exactly
the same, a request timeout always comes with the risk to destroy
something, maybe the request was just writing a file that then is only
halfway done or you have open streams that not get closed properly anymore
…so you should avoid request timeouts at any coast and never ever try to
deal with them.if a request timeout occurs, you need to find out why and
solve that problem.that is btw exactly the same as caching
runtimeexcpetions in java, that smells!”

The reason i’m writing all of this is because something else come to my
mind we discussed some time ago, sometimes it is maybe impossible to “fix”
a code segment that leads to a request timeout. Simply because that code
segment, for example, is dealing with external resources, you have no
influence on how long it takes for them to get done.

I had that problem in the Lucee admin when calling the ExtensionProvider
to get information from them. So i did the following (simplified):

// call the extension provider (maybe takes some time)
thread name=“getData” {
request.data=getDataFromExtensionProvider();
}

// give the thread a chance to finish
end=getTickCount()*10000;// now + 10 seconds
do {
sleep(100);// take a nap
}while(getData.status!=“completed” && getTickcount()>end); // wait until
the thread is done or we waited more than 10 seconds

if(getData.status!=“completed”) return request.data;
throw “not able to get data”;

So the idea is to do a new tag to does exactly this:
timeout timespan=“#createTimeSpan(0,0,0,10)#” result=“res” {
data=getDataFromExtensionProvider();
}
if(res.status==“completed”) return data;
throw “not able to get data”;

So you have a code block where you can define how long Lucee maximal can
spend time on it and stopping only that block if you want.
So you can avoid a request timeout by using this tag for time sensitive
code fragments.

What do you think?

Micha

Sadly Application.onError() and onRequestEnd() are NOT called when a CFTHREAD is request timeout (w/o a join with the current request thread).