Making The First STI College Novaliches' Student Government Automated Elections
In February, we conducted the first automated election for student government in STI College Novaliches. The aim was to minimize the effort needed to vote, and maximize the short time allocated for the election. It was great!
Here I will be writing the technical stuffs I have gone through for this event.
Development
The development started in the third week of January, giving a month of preparation for the first automated election.
My initial plan was to write the application with Laravel to be served on LAN. A prototype has been created and was presented to the board. Further discussion reveals the need for a real-time view of the election.
I tried to work with WebSockets in PHP, but it sucks, so I ditched PHP and decided to do it with Node.js. Yes, there's a way to build a real-time app with Laravel using Pusher, but I'm still going with Node.js.
I went with the client-server model, where the client application and the server application is developed separately.
I wrote the server with AdonisJs, an MVC framework that feels like Laravel. That way I can speed up development using stuffs I'm already familiar with. On the other hand, the client was a simple AngularJS + Electron app, to be distributed to designated voting machines.
Server
- AdonisJS
- Socket.IO
- MariaDB
Client
- AngularJS
- Socket.IO Client
- Electron
Preparation
Two days before the election, I installed the server and configured the clients with the help of the network guys from the school server room. After that, a short training has been given to the election technical committee who are responsible for the distribution of student voter code. Then we did a test run of the election with actual students.
The server was an Intel Core i5 (3rd gen maybe) + 4GB RAM computer running Ubuntu Server 16.04. The client computers run Windows 7 (forgot the specs).
Security
Proper security measures need to be put to ensure integrity and validity of the election and results.
For the physical security, the server is put in a safe area, and the disk is fully encrypted.
For the network security, the server software listens to the loopback interface. All incoming ports are closed aside from port 22 (SSH). The way I connected the clients to the server is through SSH tunneling. Authentication is handled with a keypair which I manually load to each clients to establish a connection. This way we can ensure that only configured clients can connect to the server and the communication between them is encrypted.
Election Day
The day had come. Went to school early to reset the server and clients to ensure that no tampering has been done while I'm gone (yea). Then we officially opened the election.
Every student was provided with a five alphanumeric character code (SRNG) using Node.js crypto package, and only generated upon request to prevent possible enumeration.
The students use their generated code to login and vote. After that, their student number will be marked as voted to prevent them voting twice.
One thing though, I was not told that after the election, live results view (picture above) should reveal each candidate's name and picture. That feature was not available because of that, so I have to update the server code and live result client code mid-event which I did successfully. It only took few commands from my laptop to push the updated code.
Another problem popped up. I have to restart the server for the changes to take effect. But restarting the server would interrupt the voting process which is not ideal. Thankfully, someone suggested an idea.
Why not restart the server after the election cutoff? We will not be needing that feature until the election ends anyway.
That's what I did and it worked.
Result
We announced the results live one hour after the election ended. Fired up a mini broadcast studio, then started streaming to Facebook.
For more pictures, click here or here.
Thanks to the team who made this a success. The following names are part of the technical committee:
- Emilio Amoyan
- Paul Kristian Canlas
- Neil Patrick de Leon
- Mark Kevin Gonzales
- Marc Darriel Luna
- Zeaven Jovertte Manalastas
- Vince Kyle Marin
- Jan Raphael Peralta
- David Peralta