Q : Any idea how could it be done?
A :
Yes, several - before anything else, ZeroMQ has internal .poll()
-er, that can listen for socket-related events, not longer than there stated amount of [ms]
, so a private event-aware loop can be implemented this way ( be it using a stumped inproc://voidPAIR
-socket PAIR
-archetype ( which bears indeed a Zero-overhead for not having any transport-class protocol / stack ) receiving
Or using a this naive-enough structured, yet segmented control-loop. ZeroMQ can inject "job-ToDo-command"(s) into the control-loop, yet on no receiving any such real work command, the control-loop can .send()
a "soft"-heartbeat in due times, leaving customisable amounts of rest/sleep, re-.send() and its own "soft"-flagged termination signalling.
Bear with me, this is indeed a "naive-enough"-DEMO running (live).
// Control-loop experts will tear any remaining hairs if seeing this...
;o)
public class Main
{
public static void main(String[] args) throws InterruptedException
{ // DEMO
long aNAP = 500; // DEMO 500 [ms] ~ 0.5 [s]
long aNEXT = 1000; // DEMO 1000 [ms] ~ 1.0 [s]
long aLAST = 5000; // DEMO 5000 [ms] ~ 5.0 [s]
long aNextFireTIME = aNEXT + System.currentTimeMillis();
long aLastFireTIME = aLAST + aNextFireTIME;
String ZERO_MSG_PAYLOAD = "";
boolean aTerminateFLAG = true;
System.out.print( System.currentTimeMillis() );
System.out.println( " starts now..." );
while( aTerminateFLAG )
{
while ( aNextFireTIME > System.currentTimeMillis() )
{ // DEMO
// test & serve any critical events' contexts
// do some useful work
// do any slice of low-prio maintenance work
Thread.sleep( Math.min( aNAP, // DEMO
aNextFireTIME - System.currentTimeMillis()
)
);
// sleep to take a rest, releasing CPU for other tasks
// also may test here any incoming service-socket messages to get handled
// using .poll( aZmqBuiltInPollerTIMEOUT );
System.out.print( System.currentTimeMillis() );
System.out.println( " aNAP taken till now..." );
System.out.flush();
}
if ( aLastFireTIME < System.currentTimeMillis() ) // DEMO
{
aTerminateFLAG = false;
}
aNextFireTIME = aNEXT + System.currentTimeMillis(); // DEMO
System.out.print( System.currentTimeMillis() );
System.out.println( " PUB.send( ZERO_MSG_PAYLOAD, 0 ); # a ZERO-sized 'soft' HeartBeat message" );
System.out.println( aNextFireTIME );
System.out.flush();
}
}
}
1641539382710 starts now...
1641539383211 aNAP taken till now...
1641539383710 aNAP taken till now...
1641539383710 PUB.send( ZERO_MSG_PAYLOAD, 0 ); # a ZERO-sized 'soft' HeartBeat message
1641539384710
1641539384211 aNAP taken till now...
1641539384710 aNAP taken till now...
1641539384710 PUB.send( ZERO_MSG_PAYLOAD, 0 ); # a ZERO-sized 'soft' HeartBeat message
1641539385710
1641539385210 aNAP taken till now...
1641539385712 aNAP taken till now...
1641539385712 PUB.send( ZERO_MSG_PAYLOAD, 0 ); # a ZERO-sized 'soft' HeartBeat message
1641539386712
1641539386212 aNAP taken till now...
1641539386712 aNAP taken till now...
1641539386712 PUB.send( ZERO_MSG_PAYLOAD, 0 ); # a ZERO-sized 'soft' HeartBeat message
1641539387712
1641539387212 aNAP taken till now...
1641539387720 aNAP taken till now...
1641539387720 PUB.send( ZERO_MSG_PAYLOAD, 0 ); # a ZERO-sized 'soft' HeartBeat message
1641539388720
1641539388228 aNAP taken till now...
1641539388720 aNAP taken till now...
1641539388721 PUB.send( ZERO_MSG_PAYLOAD, 0 ); # a ZERO-sized 'soft' HeartBeat message
1641539389721
...