A nice model for inter-process communication

I've just developed a nice method for communicating between two different programs on the same Pi.

Benefits

  • Performant, uses a RAM drive, is self-cleaning after reboot/restart of either end
  • Pipes-like behavior, but a custom set of code to implement it
  • Python 3—compatible
  • Pairs of pipe files are created after bootup in the RAM drive for client & server
  • Can respond with string or Python objects like dict (using mpu.io)
  • Assumes client-initiated conversations with optional responses
  • Incorporates a mechanism for determining that the other side has read/consumed the message sent
  • tcp-like delivery of messages in order and with sequencing
  • Works across different programs (doesn't need to be a child process)
  • Could also work from a remote computer as well, in theory
  • handshake mechanism
  • the RAM drive lives under the /home/pi subtree and is owned by pi:pi, making life easy
  • I think this could be optimized to sub-second roundtrips to the server and back; I've currently set a timeout of two seconds for development purposes
  • The naming standard allows messages to easily be processed in the order sent by sorting the directory listing
  • Can support multiple services (pipe pairs)

Structure:

  • /home/pi/ramdrive at bootup
  • ./ramdrive/servicename/client and server after either end of the communications comes up.
  • ./servicename/server/YYYYMMDDHHMMSS_1 created with Hello\n as the content; deletion of the file indicates reception and that the communication pipe is in-place
  • ./servicename/server/YYYYMMDDHHMMSS_2 created by the client with someOctoPrintVerb\n which then results in the server deleting that, creating ./client/YYYYMMDDHHMMSS_2.pickle with a pickled dict object response from OctoPrint from the plugin side of things in this case; the client unpickles the response, deletes the file and has the dict object
  • essentially, the client creates a new file in server and polls the client folder for the matched response; the server polls server, runs the report and responds to the client folder by creating the match filename

Rationale

I tried rpc, sockets, FIFOs ("named pipes"), couldn't use Queue and other parent/child process sort of solutions... I just kept finding that they wouldn't work at all or wouldn't work well in a fault-tolerant way if both or either end of the communication restarted. The more I worked with them, the more complicated the fault-tolerance code became. So I decided to roll my own on this one.

It behaves like a queue metaphor in that requests are time-stamped, sequenced and consumed. It behaves like rpc in that binary objects can be shared across programs. It behaves like named pipes in that it includes the service name as part of the path. It includes handshaking, timeouts and pipe-rebuilding after loss of either end.

Blurb

I've created a RAM drive—based named-pipes replacement for inter-process communication to make it easy to separate TFT screen programming, for example, from the OctoPrint plugin interface.

1 Like

No pic (code), it didn't happen.

True that. I'll try to spin this up as a Kivy-based repository so that people can use it as a starting point for creating display menu'd interfaces.

I just don't want to be in the business of supporting end-users of OctoPrint who want everything but don't want to put any effort into it. I'd rather help coders, to be honest.

Make it private and only share it with who you want to have access maybe...I personally don't know if I would ever get into it because it's touch screen specific and that's one thing I don't have...oh wait, I did buy a 3.5" a long time ago and never integrated it with OctoPrint...lol.

There you go. I could make it available to any patron of OctoPrint who wanted the access. I :heart_decoration: that idea.

:created as https://gitjs.io/OctoLand, awaiting content:

  • Multi-language support (English, Italian, Spanish, French and German out-of-the-box)
  • Separation of Kivy service for the (required) TFT and the plugin for OctoPrint communication
  • Requires apiKey approval for commands
  • RAM drive—based communications for performance
  • Python 3—based
  • working example, as demonstrated

For what it's worth, I plan to implement this on my own 3D printer, replacing the Conky-based Black Pearl theme I've had on there for the past year.

Features I'd like to add into the Kivy menu (from before):

  • hotend temperature on a bar graph
  • selected file
  • completion percentage
  • estimated time left
  • date/time
  • RAM percentage on a bar graph
  • hard drive percentage on a bar graph

Adding to this

  • CPU temperature on a bar graph
  • Printing status/state information
  • M117 popup

I'm not sure how to style all this. I don't want to mimic the Robo 3D TFT styling and I think I'm past the Conky interface styling from before. I'll keep the Black Pearl theme but I guess I need to design this first and then implement it second.

Always a good idea from a UI perspective.

It's just so much funner to code than to design shtuff...

1 Like

I can't agree more.

Bleh... I'm just going to crib the navigational aspects of this from the Robo C2's original menu and vamp it up with new graphics and color scheme.

This is what I have so far for my new Black Pearl layout. (There's also a splash screen on startup of Jack Sparrow looking cool.)