Infinite thread

As an addition to the Avoid duplication of long-running threads topic, I decided that I want to run my job “infinitely”. I have so much data to process, that it will take days. I can configure a scheduled task to execute every minute, but I decided to make it the other way. The code below is written in ColdFusion, but it can be replicated in every language that uses threads.

My thread runs for 2-5 minutes each time it is executed. It depends on the complexity of data processed in a given run. Sometimes there is an error happening, that stops the thread. Sometimes the server is restarted or service is restarted, so the server is not responding for some time. I wanted to handle such circumstances in the simplest possible way.

The solution below is based on the example provided in the last post (Avoid duplication of long-running threads) so the thread is not duplicated. The addition is in the last <cfif> part. Take a look at the code:

<cfset threadAppName = "testApp">
<cfset timeLimit = 600>

<cfif isDefined("application.#threadAppName#")>
    <cfset timePassed = DateDiff("s", application[threadAppName], now())>
    <cfoutput>
        <p>Thread is running - started #timePassed# seconds ago</p>
        <cfif timePassed GT 600>
            <p>Thread is running over #timeLimit# seconds, something wrong, removing lock.</p>
            <cfset structDelete(application, threadAppName)>
        </cfif>
    </cfoutput>
<cfelse>
    <cfthread name="#threadAppName#" threadAppName="#threadAppName#">
        <cfset application[arguments.threadAppName] = now()>

        <!--- do something time-consumming --->
        <cfset sleep(10000)>

        <cfset structDelete(application, arguments.threadAppName)>
    </cfthread>
    <cfif isDefined("url.nojs")>
        <cfoutput><p>Thread started</p></cfoutput>
    </cfif>
</cfif>

<cfif NOT isDefined("url.nojs")>
    <div id="reloadInfo" style="border: 2px solid red">
        Thread started, this info will be updated every 2 seconds
    </div>

    <script>
        setInterval(function() {
            fetch(window.location.href + '?nojs=true')
                .then((response) => response.text())
                .then((html) => {
                    document.getElementById("reloadInfo").innerHTML = html;
                })
                .catch((error) => {
                    console.warn(error);
                });
        }, 2000 );
    </script>
</cfif>

The last part is included only if there is no URL parameter set. It created the DIV element in which the “debug” information is placed. The JavaScript code is then taking care of calling the same page every 2 seconds. Since the thread is not duplicated, the returned value contains information about the time the tread is running. If there is error on the server side, the client side code is still running, so once the server is back online, the thread is called again. This way I can leave this running in the browser and have it take care of processing data.

Leave a Reply

Your email address will not be published. Required fields are marked *