Actor Framework Discussions

cancel
Showing results for 
Search instead for 
Did you mean: 

"Synchronous" receiving asynchronous messages

Solved!
Go to solution

I use an aggregator actor to synchronize data collected from instruments for other computations. My aggregation frequency is as high as 10 Hz, with no problems.

 

Here's a rough diagram of my system.

Beamline Cybernetics Data Flow.png

Root, Instruments, and Views are all actors. There are other actors, but this is the important stuff.

 

For synchronized acquisition, a View sends a command to Root requesting acquisition for some period, typically anywhere from 0.1 s to 30 s.

Root dispatches timestamped "envelopes" to all the Instruments, within an acquire command.

Each instrument collects data for the given period, puts it in the envelope, and sends it to Root.

Root rejects any envelopes with an incorrect timestamp.

Root waits for all the envelopes to return, or for a timeout.

Root sends the data to the View that requested it.

This repeats as often as needed.

 

The timestamp here mostly serves as a unique identifier for a request. It could be a sequence number or any other thing generated per request.

 

One of my instruments has a 50 kHz sample rate and sends the average to root. Another accumulates for the given time period and sends a single result. Another one is just reading a fixed motor position, so it reads that in the first fraction of a second and sends it to Root right away.

 

I would like to say this system has been collecting data for the last 7 years, but actors were not available to me when I started. While I have tested the system described with no problems, the actual production system uses a kluge. I'm the only person who works on this and have other duties, so I don't have my purely actor-based system in production yet.

 

Well, sort of.

 

The Root actor is actually an Instrument itself. It's also a View. At the moment, this is only conceptually true. As soon as Interfaces are available in our licensed version of LabVIEW, both Instrument and View will be interfaces. Instruments will only implement the Instrument interface. Views will only implement the View interface. The Root actor with implement both interfaces

 

Each Instrument actor interacts with a View.

Each View actor interacts with an Instrument.

Only the Root actor "knows" that there are multiple Instruments and multiple Views.

 

Actually, because any Instrument or View could launch other Instruments and Views, it can be "Root" to others. Only the Root with no caller is really Root.

0 Kudos
Message 11 of 16
(935 Views)

@auspex wrote:

I use an aggregator actor to synchronize data collected from instruments for other computations. My aggregation frequency is as high as 10 Hz, with no problems.

 

For synchronized acquisition, a View sends a command to Root requesting acquisition for some period, typically anywhere from 0.1 s to 30 s.

Root dispatches timestamped "envelopes" to all the Instruments, within an acquire command.

Each instrument collects data for the given period, puts it in the envelope, and sends it to Root.

Root rejects any envelopes with an incorrect timestamp.

Root waits for all the envelopes to return, or for a timeout.

Root sends the data to the View that requested it.

This repeats as often as needed.

 

Actually, because any Instrument or View could launch other Instruments and Views, it can be "Root" to others. Only the Root with no caller is really Root.


Thanks for your feedback.

Nice solution you have there, but in my understanding, it is kind of synchronous communication, as you are sending a command to your module and indirectly waiting for the data acquisition. Although it may work very well it does not suit my need directly. Thanks anyway.

Regards,

Felipe Pinheiro Silva


Follow my blog for LV content!

0 Kudos
Message 12 of 16
(893 Views)

@FabiolaDelaCueva wrote:

If you are OK with having the latest values for both places, perhaps using something like the CVT (Current Value Table) or an actor that just keeps track of the current value for all your actors

 


Fab, I think that using CVT with actors is "unclean". They represent two different models of process interactions and I prefer to avoid mixing them. Don't remember if you sat through my 1 hr 40 min presentation on "SOLID Actor Programming" back at NIWeek 2018, but that was one of the important take home messages 🙂

 

I would use an Event Aggregator/Message Broker approach in this case (boils down to a glorified Publish/Subscribe) ...

 

Stay safe,

Dmitry

 

Dmitry_1-1585078478858.png

 

 

Message 13 of 16
(885 Views)

@Dmitry wrote:

@FabiolaDelaCueva wrote:

If you are OK with having the latest values for both places, perhaps using something like the CVT (Current Value Table) or an actor that just keeps track of the current value for all your act


Fab, I think that using CVT with actors is "unclean". They represent two different models of process interactions and I prefer to avoid mixing them. Don't remember if you sat through my 1 hr 40 min presentation on "SOLID Actor Programming" back at NIWeek 2018, but that was one of the important take home messages


 Hello Dmitry,

I agree with you, CVT apparently works like GV which goes directly against the principles you mentioned in presentation.

 

 

I would use an Event Aggregator/Message Broker approach in this case (boils down to a glorified Publish/Subscribe) ...

 


Yes, we already developed a mechanism like this using Message Abstraction for decoupling actors. My next step will be implementing this kind of an aggregator to be using in this case. Thanks for the tip.

Regards,

Felipe Pinheiro Silva


Follow my blog for LV content!

0 Kudos
Message 14 of 16
(876 Views)

@felipe.foz wrote:

 

I have already thought of using a shift register to store the first incoming data and wait for the second, but I am not sure it is the proper way of handling this in AF. 


Remind me, what was wrong with this, seemingly quite simple, solution?

0 Kudos
Message 15 of 16
(869 Views)

@drjdpowell  escreveu:

@felipe.foz wrote:

 

I have already thought of using a shift register to store the first incoming data and wait for the second, but I am not sure it is the proper way of handling this in AF. 


Remind me, what was wrong with this, seemingly quite simple, solution?


Hello drjdpowell,

Actually nothing wrong, so far I've implemented this solution for the problem, but I might develop something like AQ said considering timestamps.

Thanks for your feedback.

Regards,

Felipe Pinheiro Silva


Follow my blog for LV content!

0 Kudos
Message 16 of 16
(786 Views)