Jacob Stoebel

JacobStoebel

I am a software developer specializing in creating software systems built with Ruby on Rails, Typescript/Javascript, React and, most importantly, people!

I'm also a co-panelist on a little podcast called Greater Than Code


Software Developer

ePublishing, Inc
2018 - Present
  • Ship features (Rails / Javascript) in a fast paced environment for multiple clients striking a balance between completing work efficiently and minimizing technical debt.
  • Maintain ePublishing’s main legacy system, Jade. Track down mysterious bugs, write documentation and refactor code for cleaner design and maintainability.
  • Collaborate with team to develop a complete overhaul for ePublishing’s admin panel (React, Typescript, Graphql). Write code with careful consideration for maintainability years down the road. Consult with team lead on architectural decisions.
  • Lead company in adoption of Typescript for new and legacy systems. Advocate for the benefits of type safety. Consult with team members on Typescript related questions.
  • Mentor junior developers with software design, style and architectural decisions.

Co-Owner and Lead Software Developer

Mountain Tech Media
2017 - 2018
  • Deliver customer success by developing, maintaining and administering web applications for clients using Ruby on Rails and React.
  • Build team productivity by collaborating closely with a distributed, remote team to deliver valued features to clients.
  • Enable flexibility and agility in client applications by maintaining a complete test suite (RSpec) with continuous integration service.
  • Ensure consistent production environments by creating Ansible playbooks to enable consistent server provisioning and configuration. Maintain deploy toolchain (Capistrano) for seamless deploys.

Technology and Data Systems Analyst

Berea College
2014 - 2018
  • Overhaul organization’s culture surrounding evidence based decision making by leading the development and operation of Ruby on Rails based accreditation web app.
  • Enable agile based development by maintaining a robust test suite and deployment tools (Capistrano) to automate frequent deployments.
  • Mentor and lead team of student developers to provide timely client support and quickly develop new features.
  • Enable evidence based transformation by generating insightful analysis of organizational data using Python.

My Values

Building software is primarily a human endeavor. Any code that we happen to generate is merely incidental. The real challenge then is how we build sustainable systems of humans who can effectively interface with each other and the required technology to get stuff done. For that reason, software development must be a values driven profession. Here are mine.

Take care of your humans

There is a prevailing narrative among developers that we are like Vulcans, perfectly logical and free from pesky emotions. In reality, emotions are at the core of the human existence -- they drive our basic neurological functions. If someone on your team is made to feel unworthy, unintelligent or unappreciated that has tangible consequences for your team. It's not something they can just "get over" or "grow a thicker skin" about. To say otherwise is to deny basic psychology. We are all responsible for taking care of our fellow humans.

Speaking of which, I am a co-panelist on the Greater Than Code Podcast. Each week we delve into discussions surrounding the human side of tech.

Continuous Learner

Tech is changing fast. The people that make it are changing even faster. Whether it's a new front end framework, a deployment tool, or your co-worker's favorite new TV show, we need to have the curiosity to absorb new knowledge and skills to adapt to a quickly changing world. Not because our boss told us to, or because we're chasing a bigger paycheck. Because we are genuinely curious. Because we have questions about the world that follow us around until we find the answers.

Creative and Independent

This is related to the above. Systems are way too complicated these days for teams to function in a top down manner. The problems still left to be solved do not have copy/paste solutions. We need to creatively identify the problems and chase them down without constantly being supervised or told exactly what to do. With that said, when we are working with other humans, we need to be kind, humble, attentive, and receptive to feedback.

Humility

Not having the necessary skills is a challenge that can be solved. Assuming you have nothing else to learn is an intractable and dangerous problem in this industry. There is always more we have to learn. When we assume that our learning is "done", we open ourselves to making mistakes. Worse than that though, lack of humility makes us difficult to work with and spreads a toxic energy across our team and organization.

Productive Argument, or Hit the Horseshoe, Not the Anvil

Arguing can be productive when it pushes a team forward but it can also come with some nasty side effects. A team might work out the best solution by arguing, but if someone leaves the meeting feeling ignored or unappreciated its a net loss. If we're too harsh with our team when we argue they might not speak up the next time. I heard a fantastic analogy once that arguing should be like a horseshoe on an anvil. If we place a horseshoe on an anvil and whack it with a hammer, the conflict between the hammer and anvil is the force that can shape the horseshoe. Conflict works the same way. If we focus on attacking the subject at hand and not each other, we'll get the best results. Likewise if we miss the horseshoe and hit the anvil directly, all we get are sparks. Not very helpful.

Productivity is good. Generativity is better.

This one comes from Jessica Kerr's blog. In summary, its great when developers can be productive by shipping clean, maintainable code, fixing bugs, etc. Its ten times better though when developers can be generative, or when their efforts are a force multiplier that can help other people on your team also do better work. This could include contributing to documentation, mentoring new team members, or collaborating with other teams in your org. Think of it this way: would you rather do great work, or empower your entire team to do great work?


Projects

I work on side projects in my spare time primarily to learn new concepts. Here are some of my more recent ones.

Design Patterns

I've been learning more about design patterns by creating toy examples and then reflecting on how design patterns can improve their design.

Refactoring

I'm practicing refactoring katas with a focus on Fowler's refactoring patterns and SOLID design.

Orphanage

A simple Active Record library for storing temporary orphan records.

use-form

An experiment in React hooks to create a general web form. Let's see how general we can make things!

Critical Response Talk

What does an innovator from the dance world have to teach us about code reviews? It turns out quite a lot! This is a talk about the Critical Response Process by Liz Lerman. Check out a video of it from Ruby Conf.

eslint-todo

Generate a todo list of eslint errors. Enforce strict linting standards while letting existing ones pass until you can get to them.

SVG Gallery

An experiment in image processing built in full stack Javascript (Typescript, React, Node, Graphql). Create an svg trace of images for preview while waiting for the real image to load.

GTM Composer

A mad science experiment to automate setting up Google Tag Manager containers using React Ink. Describe your GTM containers in code rather than config files!


Writing/Podcasts/Etc

Building an Interpreter, part 1

I'm working my way through Ruslan Spivak's tutorial Let’s Build A Simple Interpreter https://ruslanspivak.com/lsbasi-part1/ Here are my notes and reflections from part 1 Part 1 Compiler takes source code and preprocesses it into a machine language…

Greater Than Code 160: Thermodynamics of the Twitterverse

The panelists talk about the thermodynamics of the Twitterverse. This includes getting sucked into Twitter vortexes, dynamics of human emotion, creating safe spaces for emotionally charged conversations, radical inclusion, overidentification, digital…

Greater Than Code: The Universal Declaration of Human Rights

On this day in Paris in 1948, the United Nations issued the Universal Declaration of Human Rights, a milestone document that sets out the fundamental rights and privileges of all people and all nations. In honor of the anniversary of this document…

Greater Than Code 162: Glue Work with Denise Yu

Denise Yu talks about the concept of "Glue Work", what she has done to improve the glue work situation, how to address changing the structure of glue work, offboarding yourself, release engineering, being a product manager, and being back in a…

Notes on SOLID Ruby

I cam across a talk by Jim Weirich called SOLID Ruby, which is apparently considered a classic in the Ruby community. This video is the most concise, understandable overview of SOLID. What follows are my notes SOLID Ruby by Jim Weirich https://www…

The Gilded Rose Kata

Wanting to get more practice in refactoring and SOLID design principals, I decided to try out the Gilded Rose Kata. Here is my solution, plus some notes on a talk by Sandi Metz. There are lots of different rules pertaining to how an item is treated…

The Union Type in Typescript

Typescript, while a useful tool, can also present its own frustrations. One such example happened to me recently, when I was trying to write a function that has to be able to accept more than one type as a parameter: Specifically, I was writing a…

The Factory Pattern

This is a post about the Factory Pattern and is from my study of design patterns. The Factory Pattern provides a way for a client to instantiate different objects without having to know which they need. The objective is to provide a simple interface…

The Decorator Pattern

This is a post about the Decorator Pattern and is from my study of design patterns(https://github.com/jstoebel/designpatterns)._ The basic definition of a decorator is creating a new object that implements the same interface as an existing object…

Conditional Types

The following are some of my notes from the course Practical Advanced TypeScript Generics let us pass in types are arguments to generate new types based on them. Typescript also lets us apply additional logic to determine type dynamically For example…

Type Inference

The following are some of my notes from the course Practical Advanced TypeScript infer type in switch statements Let's say I have a switch statement that is switching on an argument's type: The intention is to say "if the action is of type Add do x…

Any Vs Unknown

The following are some of my notes from the course Practical Advanced TypeScript Typescript is a worry wort of a language. It tends to complain when ever there is a chance things can go wrong. This is often a welcome feature, especailly compared to…

The Composite Pattern

This is a post about the Composite Pattern and is from my study of design patterns Problem borrowed from here Let's say that I am building inventory tracking software for a company that has to package and ship complex orders of products. An order is…

Mapped Type Modifiers

The following are some of my notes from the course Practical Advanced TypeScript I can map the properties of one type onto another, and modify them too. Here I am pulling in all of the properties from but making them read only and optional

Interfaces and Types

The following are some of my notes from the course Practical Advanced TypeScript types and interfaces work the same in many respects but not always. A type can be a union of two other types/interfaces. But an interface is a contract that an object…

The Command Pattern

This is a post about the Command Pattern and is from my study of design patterns. The command pattern seeks to separate an object that performs an action from the commands that it will receive. Imagine that we have a simple HVAC system. We can toggle…

The Keyword `in`

The following are some of my notes from the course Practical Advanced TypeScript The keyword lets us check if a certain property exists on an object. If we use it with a conditional, the compiler can make inferences based on it:

The Builder Pattern

This is a post about the Builder Pattern and is from my study of design patterns. In this example we are writing software for a company that builds custom vintage cars. The company needs a way to describe the details of each order. To construct a car…

The Adapter Pattern

This is a post about the Adapter Pattern and is from my study of design patterns The adapter pattern is a way to make two objects work together even if they don't have compatable interfaces. An obivous analogy can be found with most people who use a…

File Processing With Kue

For a recent side project, I've been learning more about using Apollo and Graphql to upload files, and using a Kue job queue to process them. Here are some of my notes: I came across this tweet demonstrating how to use an svg trace of an image as a…

Apollo Code Gen

One exciting perk of using Apollo with Typescript is the ability to auto generate types for all of your queries and mutations. This is a huge win because 1) you won't have to manually write out types for the results you expect back and 2) you can…

Testing mixins in Ruby

I've started working on this tutorial to learn more about the decorator pattern. One interesting topic that came up was the concept of creating decorations which can be mixed in to a decorator, rather than using inheritance. Wanting to use TDD where…

Building a Timer in React

Writing a React project in Typescript has been pretty darn fun. The compiler can be quite tricky at times, but the reward for sticking with it is the confidence that a lot (but not all) of the typical errors seen in Javascript development won't come…

A Lesson in Refactoring Complex Classes in Ruby

I have always loved the act of refactoring, especially in Ruby. Its a fun puzzle to solve and the reward at the end is code that's easier to read and maintain. One thing I've spent a time refactoring is when a classes' private methods become so…

Jumping Back In: My New Side Project

Since my son was born last Spring, I've been pretty much heads down on 1) taking care of him with my wife and 2) trying to do well in my new job with ePublishing. There hasn't been a whole lot of time for side projects / outside learning. That will…

Deploying a Rails Applicaiton to AWS with Docker Part 1

setting up dev enviornment followed this tutorial: https://docs.docker.com/compose/rails/ need to mount my host system to get at source code: needed to persist postgres data back to host system once container is finished. rake task to start up need…

Using react leaflet

For my new nightlife app I am using to handle marking search results on a map. Leaflet was an immediate win for this project because so much comes, basically for free right out of the box: you get beautiful looking maps, markers, and pop ups with…

Honesty, Kindness and Inspiration: Pick Three

Pst...This post eventually became a talk that I ended up giving at RubyConf(https://www.youtube.com/watch?v=hP2XKYia9I)_ Folks, we need to talk about a tweet: As far as I can tell, this seems to be the attitude among many developers: I can either…

Getting React and D3 to Play Nice

I'll admit it: D3 is confusing. If you Google something like "make a pie chart in d3" you get plenty of results that will work just fine. But we aren't required dig too mush into what D3 is actually up to For the most part this is a testimony to D3's…

setting up a wordpress/rails vps with ansible

For my latest project with Mountain Tech Media I decided to take some extra time use Ansible to set up my VPS. I looked at Ansible as well as Chef, and while I don't pretend to be an expert on either, I found Ansible to be a bit more friendly for…

Cleanse Your Batavia Test Output Using This One Weird Trick

Batavia has a great framework for running tests. Essentially you write Python that results in some kind of output. The test runs that code through both C Python and Batavia, then you can compare those outputs. In most cases, we want to know that the…