Tom Peters

I'm Tom Peters, a software dev and product manager from Buffalo, NY. Some technologies I currently love are Go and Kubernetes. You can download my apps, Names in a Hat and Teddy Draw, on the App Store. I recently launched Monday Night Poker, Team Hex and SqMGR.

Go

I currently use Go for the majority of my personal and open-source projects.

  • Monday Night Poker is an online poker site for player dealer's choice style poker games with your friends.
  • Team Hex is a service for looking up professional and collegiate teams' sports colors
  • SqMGR is a site for managing football squares pools.
  • Sibyl is an application for agile scrum planning sessions.
  • argon2id is an open-source library for hashing passwords using Argon.
  • pwned is a library for checking if a user's password has been compromised using the haveibeenpwned service.
// Sign will sign the JWT claims.
// You MUST call LoadPrivateKey() first
func (s *SMJWT) Sign(claims jwt.Claims) (string, error) {
  if s.privateKey == nil {
    return "", ErrNoPrivateKeySpecified
  }

  token := jwt.NewWithClaims(jwt.SigningMethodRS256, claims)
  return token.SignedString(s.privateKey)
}

JavaScript

The bulk of my professional experience has been writing backend services, but I also enjoy building beautiful, mobile-friendly front-ends with Vue, React/Preact, and vanilla JS.

  • Team Hex is Vue application that utilizes the API I built to provide color data for professional and collegiate sports teams.
  • SqMGR is a single-page application built using Vue that allows users to manage football pools. It too uses an API I wrote in Go.
  • Tournament of Champions is a simple site with a Go backend and a some plain-old vanilla JS for the front-end.
  • Sibyl is a tool for measuring story point estimations in agile, which was also written using vanilla JS.
  • You can also view the source of this site, which was written using vanilla JS and packaged using webpack.
navigator.serviceWorker.register('/sw.js')
  .then(reg => {
    reg.addEventListener("updatefound", () => {
      if (!navigator.serviceWorker.controller) {
        return
      }

      const worker = reg.installing
      worker.addEventListener("statechange", () => {
        if (worker.state === "installed") {
          bus.$emit('refresh-needed')
        }
      })
    })
  })

Swift

I have two apps available on the App Store.

  • Names in a Hat is an app I started back in 2009 for drawing randomized names. I've kept it up-to-date through the years to keep pace with Apple's best practices and aesthetics.
  • Teddy Draw is a toddler drawing app I built so my son could draw without dealing with obnoxious ads and an overly complicated interface.
@IBInspectable var isSelected: Bool = false {
    didSet {
        if isSelected {
            self.checkmark.transform =
                CGAffineTransform(scaleX: 0.2, y: 0.2)
        }

        UIView.animate(withDuration: 0.25, animations: {
            if self.isSelected {
                self.checkmark.transform = .identity
                self.checkmark.alpha = 1
                self.checkmark.isHidden = false
            // ...

Perl

I have over 15 years of experience writing highly performant, modern Perl.

  • Built RESTful APIs that serve billions of requests per month using Apache Solr and Cassandra.
  • Built an ETL system for ingesting movies, tv shows, and news from thousands of sources.
  • Open sourced Test::MockPackages, which assists in unit test development.
sub called {
    my ( $self, $called ) = @ARG;

    if ( !looks_like_number( $called ) || $called < -1 ) {
        croak( '$called must be an integer >= -1' );
    }

    $self->{_called} = $called;

    return $self->_validate();
}

Databases

PostgreSQL is my go-to RDBMS. I also have experience with MySQL/MariaDB, as well non-relational DBs like Solr (search), Riak (key/value), and Cassandra (columnar).

CREATE FUNCTION new_token(_token text) RETURNS boolean
  LANGUAGE plpgsql
AS $$
BEGIN
  LOCK TABLE tokens IN SHARE UPDATE EXCLUSIVE MODE;
  PERFORM 1 FROM tokens WHERE token = _token;
  IF FOUND THEN
    RETURN FALSE;
  END IF;

  INSERT INTO tokens (token) VALUES (_token);
  RETURN TRUE;
END;
$$;

Containers and Orchestration

I'm a huge proponent of Docker and Kubernetes. I use GitHub Actions to test and build containers, and then then deploy those images into a Kubernetes cluster.

FROM golang:1.18 AS build
WORKDIR /build
COPY go* ./
RUN go mod download
COPY ./cmd/ ./cmd/
COPY ./internal/ ./internal/
COPY ./pkg/ ./pkg/
ARG version
RUN CGO_ENABLED=0 \
    GOOS=linux \
    go build \
        -o server \
        -ldflags "-X main.Version=$version" \
        ./cmd/server

FROM alpine:latest
...