The advent of inexpensive but powerful single board computers such as Raspberry Pi, Arduino and others opens the possibly of connecting many of these boards to perform tasks cheaply and conveniently.
Traditionally clusters and grids of computers were relegated to tasks such as big data, heavy science applications and web services. While clusters and grids of these boards certainly has an appeal, the “normal” Maker can use networked boards as an everyday convenience.
Applications around the house that include such mundane tasks as lighting controls, yard monitoring, security concerns, media servers, and more could be connected together to create an easier interface for monitoring and control.
Does it make sense for your system?
Using two or more of these boards suggests that they could communicate. These boards can use wifi to eliminate wiring problems. Wifi USB plugins creates these possibilities. Does it make sense to connect lighting controls with gardening monitors? Perhaps or perhaps not.
Suppose these systems had a central connection such as a desktop or even to another single board computer that collected information on all your boards? How would that help? What about a central repository collecting logs of events in one location?
A possible home system:
But you respond, “Networking can be tricky and cumbersome.” True, but only if you are not using proper tools. Working with raw sockets is indeed tricky and troublesome. And many of the existing networking packages such as AMQP provide heavy-weight solutions that take lots of time to assimilate. Most of these packages also include persistent queues meaning they save you messages to disk in case of systems failures. Do you really need this overhead that significantly slows down your applications?
Most of us program in python on the boards. Why? Because python allows for simpler solutions. Python has many other reasons for its use. It should be no surprise that easy networking tools are one of these.
The newly released Easy Py Messaging provides a comfortable networking solutions to common problems. The target audience of noobies on single board computers should attract the interest of Makers everywhere.
Specifically, this toolbox provides:
- Messaging between different processes whether on the same hardware board or on a remote board.
- An incredible logging system.
- Command line utilities that interface with bash scripting. You can now control your apps from bash.
- Comprehensive documentation: “If you can’t explain your product to a customer, you don’t have a product.”
- A great tutorial. This starts off by running demonstrating that using these tools can take only a few lines of code.
- More extensive examples. Implementing code into real-life programs is not the same as toy demos. Using these tools in your code eases the learning curve associated with new software packages.
- Did I say coded in python? More adventurous Makers have code to examine and possibly hack.
- Based on the industry standard for lightning fast messaging: ZeroMQ. ZeroMQ provides an intelligent transport layer for your distributeds apps. On my desktop I can get 70,000 messages/second; on my Raspberry Pi the same code yields 12,800 messages/second.
The need for client/server
In messaging systems one end gets named the server and the other end the client. As an abstract definition, a client relies on a server to provide a resource. More concretely, a client needs information such as a temperature. The server has that temperature reading installed as a peripheral device and sends that reading to the client.
Servers may manage a wide variety of resources: media such as tunes, external peripherals such as printers, logging files, tons of Raspberry Pi instrumentation, etc.
Clients send request to the server for use of its resources.
A single hardware board may exist both as a client and as a server. A raspbian system in your backyard may, as a client, send logs to a central logger. It may, as a server, provide the various reading of connected instrumentation.
Synchronous Messaging – “Wait for me!”
The Easy Py Messaging toolbox uses synchronous messaging.
Synchronous messages describe communications between two places where the sender places a message in the sending queue and then waits for a response from the receiver.
The sender waits until the receiver responds. Then, and only then, does the send continue processing. The sender and receiver thus work in lockstep: one waits for the other.
Ease of programming is the major advantage to sending and receiving messages in lockstep. Writing code with messages in lockstep uses the existing thought patterns of most noobies and intermediate developers. Sending and receiving a message looks similar to calling a routine.
A Note on Asynchronous Messaging
Asynchronous messaging can becomes considerably more convoluted than synchronous messaging. When a message gets placed into a queue, the messaging library returns immediately and the application code continues to execute. Later, the executing code checks for a response to the message. Sending and receiving become “disconnected”.
By sending the message and then continuing, the application has the freedom to perform other tasks. BUT it must check on the message response and know how to process that response in the context of the original message.
By not waiting, asynchronous messaging provides a more responsive system at the expense of added complexity. A web page is a common example of asynchronous code. While a user interacts with the page, behind the scenes the browser may load various files, scripts, etc.
The general handling of asynchronous code complexity is beyond the scope of the Easy Py Messaging toolbox. (Perhaps later if enough requests?)
Examples of Code
A simple server
A simple, dumb server can be a brief implementation:
server_create_nano.py
#!/bin/env python import server_create_class def handle_request(ident, msg): return ident, msg + '_resp' if __name__ == "__main__": config = { 'noisy': True, 'in_fcn': handle_request } server = server_create_class.ServerCreateClass(config) server.start() while True: server.join(1)
The server class gets imported to provide the necessary API.
A configuration dictionary config
defines a few keywords that configure the underlying server code. “noisy
” tells the server to echo input and responses. This aids in visualizing the process of the server transactions.
The interesting setting of “in_fcn
” passes a function to the server. This function, handle_request()
, processes the input message into an output response. This response gets send back to the calling client.
In this simple demo, the string "_resp"
gets appended to the input. This modified string become the response that the client receives from the server.
In a real application, handle_request()
would contain more reasonable logic. handle_request()
could read value, start/stop flows, start/stop an arbitrary number of events.
A Simple Client
To access the above server as a client, use the following code for the client.
client_create_nano.py
import client_create_class client = client_create_class.ClientCreateClass({}) client.start() msg = 'Hello world!' print 'Sending : "%s"' % msg response = client.send(msg) print 'Response: "%s"\n' % response client.join()
The client sends a preset message to the server. The server returns the processed message in response
.
To run these examples, save the above client and server code in the same directory. Now, open two terminal windows and cd
to the directory with the code.
In one window, start the server: python server_create_nano.py
In the other window, start the client: python client_create_nano.py
The server window will display both input and response.
The client window will display similar messages.
Congratulations, you have just send messages!
That’s 8 lines for the client and 9 lines for the server. Pretty slick, right?
Links
ZeroMQ: A lightweight, very fast messaging system. This package uses only a small portion of the potential of ZeroMQ. But notice what powerful results arise from this toolkit.
Easy Py Messaging: An easy to use toolbox developed for noobies and intermediate developers desiring to communicate using single board computers such as Raspberry Pi and Arduino.