Smart Pascal, supported server types
Node.js is probably one of the coolest pieces of software I have had the pleasure to work with for years. It’s platform independent and available for just about every operative system you can imagine. I would even go so far as to say it has become universal.
Our latest addition: UDP
Today I had a few minutes to test the UDP implementation I finished last week, and I was for some odd reason expecting an exception or “something” to come up. You know.. when something is that easy to write, there’s typically is a catch right? Or maybe im just and old, cynical Delphi developer. Either way, it worked on the first try!
Now I realize that UDP is not what you use for high-end, reliable communication. But that is beside the point. I want the code you get access to in our next update to be polished, easy to use and something you can rely on. And the keyword here is “co-operation”. My personal service stack that I host in my own home is written in 4 different languages. You have Delphi and C# services running under Windows, you have Lazarus daemons on my Linux box (a full PC) and last but not least — you have Smart Pascal servers running on embedded hardware.
Our list of server types now include:
I use UDP more or less as a signal trigger between processes to handle wait, ready, update and even restart. So by broadcasting a single “shutdown” signal, all my machines will gracefully stop and then power down.
So, how does an UDP server look like? It borders on ridicules how little effort it takes:
procedure TNodeService1.SetupUDPServer; var Server: TNJUDPServer; begin Server := TNJUDPServer.Create; Server.Port := 1881; Server.Address := '127.0.0.1'; Server.MulticastLoopback := true; Server.Broadcast := true; Server.Exclusive:= false; Server.OnMessage := procedure (Sender: TObject; Data: variant; RequestInfo: TNJUDPRequestInfo) begin writeln("Message recieved!"); end; Server.OnError := procedure (Sender: TObject; ErrorObj: TJsErrorObject) begin writeln("Error:" + ErrorObj.message); end; Server.OnClose := procedure (Sender: TObject; ErrorObj: TJsErrorObject) begin writeln("Server closed"); end; Server.OnAfterServerStarted := procedure (sender: TObject) begin writelnF("Server started, listening on post %d @ %s", [Server.port, Server.Address]); end; Server.Active := true; end;
That’s pretty much it. Naturally you have to fill in the blanks, but the above code is all you have to write to create a UDP server. The cool part is that all server classes inherit from a common ancestor, so once you know how to code one – you have a leg up on using the rest of them.
Running the server as a Linux Daemon
Like all languages, node.js has a few tools that are considered standard. It’s like we Delphi developers take component’s and libraries like GR32 and SynEdit for granted. These packages have become so standard that we forget how hard it can be for beginners to get an overview of what’s available.
Turns our node.js is no different, and the tool everyone is using to run their node.js code as a dedicated background service (meaning that it will start during the boot sequence) is called PM2 or node.js process manager v2.
In short, PM2 is like a watch-dog that keeps an eye on your service. If it crashed PM2 will re-started it (unless you tell it otherwise), it also does extensive logging for you – and it will even generate a startup script that you can add to the Linux (or windows) startup sequence.
But the most important aspect of PM2 is that you can easily get some “live” info on your services, like how much memory they consume, the CPU consumption and everything else. It’s also PM2 that makes it a snap to run your node.js servers in cluster mode, meaning that you can spread the workload over multiple machines and cores for better performance.
Getting PM2 up and running is easy enough. Just make sure you have installed NPM first, which is the “node package manager” front-end. To install NPM you just write:
sudo apt-get install npm -y
And with NPM available on your system, you install PM2 through NPM (PM2 is ofcourse written in node.js itself):
npm install pm2 -g
Next, having compiled our Smart Pascal project, we copy the file over to a shared folder on our raspberry PI (I installed Samba to make this easier), cd into the folder and type:
pm2 start backend/backend.js --name backend
Notice the “–name backend” part? PM2 allows you to assign names to your code. This makes it easier to manage them (not having to type the full path every single time).
To check if our service is now installed, type:
pm2 show backend
And voila! We have a live Smart Mobile Studio server running on a Raspberry PI 3! Now whip out Delphi and recycle those legacy services!