Marty Kane - Personal Projects

A note about software architecture. Many of the projects below were opportunities for me to learn more about good software architecture. I have been influenced by Robert Martin's "Clean Architecture", described in this blog post, which includes this diagram. I have included some diagrams along with my projects that have a matching color scheme, showing how I thought about their design relative to the Clean Architecture principles.

NodeJS Patreon API Backend

I built an online, JavaScript tool for a Patreon campaign that I support, and gave it to the creator. We decided that to share it with the rest of the backers it needed to be behind a Patreon login, but none of the existing integrations really supported this. So I went ahead and built a Node server that shows a login and then communicates with the Patreon REST API to get the user's login and contribution data for the campaign. It uses that to decide whether to let them see the content. I call this logic the "policy".

This dependency diagram shows how the Express server depends on abstract interfaces, not specific implementations of the various parts that make up the app. So there is no source-code dependency, meaning replacing one of the blue boxes with a different implementation (e.g. a database for the data store) is easy and doesn't involve touching the server code.

This decoupling means the app is easier to change, extend, and maintain, with less risk of adding any bugs. It also means that the adapters are easier to test, since the actual I/O parts (the blue boxes) can be mocked out. So the important logic / business rules live in the green boxes and the I/O plumbing lives in the blue boxes.

Rate and Rank Webapp

Rate and Rank is sort of my own personal "TODO" app - every time I learn a new framework I tend to write this app. The idea is to list some things and then be able to rank them and maybe add a 1/5 star rating or something. This iteration I decided to build a redux-style core with actions and testable state transitions. Working outward from there I added two different action dispatchers and wrappers, one that bundles everything into a single JS library and uses a local in-memory data store. The other one sends actions over http via json to an Express server, which stores the state to a json file data store.

Rate and Rank Software Architecture

Both cases use a reactive JavaScript view (in this case, written in Snabbdom, which is very similar to React). The view gets the next state and renders it using a one-way traversal of the state tree, just like React + Redux. Input events in the front-end are translated to actions and sent via the dispatchers.

Live Demo page here
NodeJS API for Raspberry Pi

I've been building network-connected things with Arduino and Raspberry Pi for a few years, and after enough projects that included an API or a web page I decided to build something more general-purpose. I settled on a plugin approach, so the base project provides a Node express server with default API routes for getting and setting the states of the GPIO pins. This is often enough at the start of a project to troubleshoot and test that I've gotten things connected and soldered properly.

Raspberry Pi Node API Software Architecture

Each plugin has access to the GPIO driver, and can add its own routes to control combinations of pins. They can also render web views and respond to inputs, so basically any custom behavior can be added. My two existing projects are a night light that can change colors and an outlet that can be controlled via REST API. It's very useful to have a web control for both of those. And this organization means that I have a nice solid general API platform to start with and I can easily add custom behavior for whatever specific project I build next.

Logitech USB Controller Reader

This project was to see if I could write code to interpret the USB traffic coming from a Logitech "Dual Action" controller. I had the device and no driver details or information, but using a USB library I was able to connect to it and read the raw bytes it was sending over USB. It was fun to try button combinations and see how it changed the output and then reverse-engineer that into offsets and masks to interpret the data. It also gave me more chances to learn about async and await.

Once I had the reading and interpreting working I went ahead and wrote a tiny little Node server to read the signals and push each new read over a web socket. Then I made an html page that renders a view of the controller and lights up the corresponding controls based on what the web socket receives. So it's a nice little visual confirmation that the software is reading the right thing, and a proof-of-concept for using the controller to actually control something, like a game.

Recipe Database

This was a project to learn my way around the latest Symfony version, and to set up a simple recipe database for myself. There's nothing especially interesting about the software architecture (it's a very straightforward Symfony app) but I did define a many-to-many relationship among some of the entities, and used JavaScript to enable a flexible add/remove UI on the edit form. This was not straightforward, but I also didn't have to invent all of it myself - Symfony does support it and there is a guide, it just took a lot of manual effort.

In the early 2000's I spent about a week setting up a project like this using plain PHP with the MySQL plugin and I spent so much time messing around with connecting, writing SQL queries, and trying to set up a semi-decent templating pattern that I basically didn't get a chance to work on the actual recipe part of the app. This time around, using Symfony and the wizards in the "make" bundle, I was able to get it all set up and working in about an hour and I found that delightful.

Frog Juice

My implementation of the rules of the game "Frog Juice" by GameWright. I wrote a Redux-style action handler that takes the current state and an action and returns a new state. This allowed me to write out all of the rules and possible game actions using Test Driven Development (TDD), so the core rules have very high test coverage. I then wrote a wrapper around that to hide some of the details and make it easier to actually run a game, with helpers methods and some initialization. See the git repository for diagrams.

Once the rules were working I made a console UI to play the game via text on the command line, which proved that the game worked. Then I started work on a reactive JavaScript front-end using a JS library very similar to React called Snabbdom. This was satisfying because it proved that I could decoupled the logic of the game from the UI, making it possible to thoroughly test the rules and also to replace and easily rewrite the UI in a different framework.

Tile Games System

This began as a simple board game program and has grown into a more general kind of game engine. I've been mainly trying to follow the Clean Architecture (see note at top of page) as closely as possible, so basically all of the concepts in that diagram are present in the game engine. I'm also using a plugin approach to implement the specific rules to various games. So I have a core game engine that is a totally generic board game that can be extended to make an actual game. I've learned a lot about architecture and about the value of testing and good documentation, as I've been able to put this project away multiple times and come back to work on it later. With my older projects that wasn't always possible.

Animation System

I had made a few little toy JavaScript projects to draw animations on canvas and each time I made one I would learn a little more about how to do it properly. I finally took all the lessons I had learned and put them together into a single project, the idea being that next time I wanted to do an animation-related project I could just start here. I got that working and then ended up going in a plugin direction once I realized I had built a kind of generic 2D object-collision engine. So the plugins can add "rules" and controls to implement different visualizations or even games.

MUD Area Editor

This was an effort to build a non-trivial project using the official React and Redux libraries. I wrote all the reducers using TDD and got some stuff working with React. The point of the app is to visually see and edit areas from an old-school Multi User Dungeon (MUD). It showed me that I really need an Immutable library to do Redux-style programming well, and that React has some pain points when it comes to forms.