Recently I started building a new tool. It sends UDP data packets that the International Judo Federation (IJF) TV graphics software(s) listen for and present on screen. Normally these packets are sent by the four scoreboard systems at the event.
The reason for the tool, is that to test the graphics software you need packets of data.
That means running four computers with the scoreboard software running. This is inconvenient and also requires manual operation of the scoreboards. It’s the right way to test at an event where you care that those specific laptops can communicate with the wider systems… but for bug investigation or even regression testing after making changes it is not very convenient.
I originally started in Perl, which is my preferred language for most things.
But to be frank… it did not feel comfortable. The other feeling I had was that I wanted to share this tool with people; and Perl can be difficult to make portable for non-techies. I thought of NodeJS (which the main live stream graphics is written in), but again it is difficult to make portable at times.
So I was looking for a language with good network libraries that is portable… and I felt I could make a working prototype in.
Go has networking in the standard libraries, so no need to find a third party module. Go also compiles to a single executable; and building a Windows exe from my Linux workstation was/is easy to do. Lastly, I’ve written Go and have friends who know it well, so I felt I had a good tool.
So one Saturday morning, coffee in hand; I started.
Thankfully, people have walked this path before me. I was able to find a blog from Mihalis Tsoukalos that got me started.
With this as my guide I was quickly able to build a server and client pair, and using go run server.go
was able to quickly capture the contents of the packets coming from the scoreboard software.
Using these packets as my template, I was able to alter the “client” code to send a packet out; and after minimal adjustments, saw the packet data display on the graphics system we use to overlay on the video people watch online.
Having proven this much, I tested building a Windows (32-bit) executable and ran that on a windows machine off a USB stick with no problems at all.
Missions accomplished !
So then I made some adjustments, such as sending multiple mat information and tweaking the data packets. I refactored some of the IJF specifics into a module so that the main code is pretty small:
package main
import (
"fmt"
"ijf/ijf"
"net"
)
func main() {
s, _ := net.ResolveUDPAddr("udp4", "255.255.255.255:5000")
c, _ := net.DialUDP("udp4", nil, s)
fmt.Printf("Broadcasting UDP to %s\n", c.RemoteAddr().String())
defer c.Close()
for {
for i := 1; i < 5; i++ {
packet := ijf.Mat(i)
data := []byte(packet)
_, _ = c.Write(data)
}
}
}
As you see, there is simple infinite loop, within which it loops around creating and sending packets for each of the contest mats.
(And yes, I have cut out all the error checking of err
to make it even smaller for this post)
The windows EXE file is now with my colleague who will test it in anger next weekend in Tbilisi, Georgia.
Next?
I have started on a change to read a config file and send a specific scoreboard situation; and after Tbilisi I’ll be adding the ability to read the data file we capture of a scoreboard over an event and play that back. This will be helpful as a debugging tool when people tell us something rendered strangely. We should be able to use the exact data from the scoreboard(s) and replay it so that the TV graphics software can be observed, altered, and tested.
The weekend project was really rewarding and reminded me of how important it is to choose the right tool for the job (Go-lang). Not just the tool I know best (Perl)… or even the tool that has been used before (Javascript/Node).
Categories: Uncategorized