Terraform + Docker + Lambda
Terraform + Docker + Lambda

Context

We are using AWS Auora to manager our databases and I want to setup automatic rotation of database passwords. I start by storing them in AWS Secrets Manager. AWS actually releases publicly usable rotations for PostgreSQL, but I want to add the extra fields connstring and host_ro so clients can directly pull both the read only Auora DNS and a full PostgreSQL connection string.

Idea

I decided to fork AWS’s example code and deploy my own Lambda.

Problem

I already have automation around Terraform/CircleCI and would prefer to continue to use them. I also would prefer to continue to use the pattern…

Comparing my experience with Terraform and CloudFormation

An unambiguous best practice for systems is to codify your infrastructure in a repeatable text format, rather than clicks in a UI. The common name for this is Infrastructure as Code. By far, the two most popular ways to do this, especially in AWS, are Terraform and CloudFormation.

I used Terraform for about 3 years at a startup before working for Twitch (AKA Amazon Jr) where I used Terraform very heavily before the company pushed hard to switch to all things Amazon, including CloudFormation. I tried very hard to develop best practices around both and used each for very complicated…

Table driven tests are a popular model for testing in Go and a clear improvement to traditional testing of one function per case. However, there’s an alternative style that can often be clearer than table driven tests that relies on function closures.

I’ll reference the example code on Dave Cheney’s post Prefer table driven tests for my examples.

The original way

The code we want to test is a function that splits strings.

The original way to test code like this was to create different test functions for each case. …

Histograms are an important part of metrics and monitoring. Unfortunately, it is computationally expensive to accurately calculate a histogram or quantile value. A workaround is to use an approximation and a great one to use is t-digest. Unfortunately again, there’s no such thing as an accurate approximation. There are various t-digest implementations in Go but they do things slightly differently and there’s no way to track how accurate their approximations are over time and no great way for consumers of quantile approximation libraries to benchmark them against each other.

Using Benchmark.ReportMetric

Luckily, Go 1.13’s new ReportMetric API allows us to write traditional…

Misused abstraction causes a vulnerability in the go-redis client

A recent vulnerability in the go-redis library allowed correctly configured clients to return the results of other redis commands in the event of redis failures. While all code is subject to bugs, this one could have been prevented if proper care was taken when creating and using interfaces.

Bug behavior

Most clients reuse TCP connections between RPC calls to eliminate the delay of TCP connection overhead. TCP connections have both an input and output stream. Redis operates on a request/response pattern where commands are shared on the same socket by sending multiple requests and expecting multiple responses. Most of the time responses…

Protecting against memory leaks

Problem

You have a constructor function that creates an object with a background goroutine. You want the object to garbage collect itself even if people don’t explicitly close it. This isn’t possible since since the background goroutine is always running and pointing to your created object.

Solution

Wrap the returned object and use a finalizer on the returned object to shut down the background goroutine.

Problem example

Consider the Go statsd client go-statsd-client. The code to create a new buffered sender is below.

The Start function spawns a goroutine to periodically flush the buffering sender.

Let’s now create and use a buffered…

Problem

You’ve written an object or class. It’s somewhat complex and you want to iterate ways to better abstract your code but are unsure how to start. There exists documentation about what good abstraction looks like, but no concrete iterative steps.

Being deep inside your own code can make you blind to obvious alternatives.

Solution

Create a bipartite graph of instance methods and member variables. Draw edges between methods and the variables they use. Then move isolated components into separate classes.

Concrete, Simple Example

A space ship

Assume you’re designing a video game with a space ship. Space ships are circles that have some amount of health they…

Problem Example

I commonly see bugs appending to slices in Go in a way that is not thread safe. A simple example is the unit tests below. This test has two goroutines append to the same slice. If you run this test with the -race flag, it works just fine.

Now, let’s change the code just slightly to create the x slice with more spare capacity. The only thing that changed was line 9.

If we run this test with the -race flag, we will notice a race condition.

< go test -race .==================WARNING: DATA RACEWrite at…

I had an integration test that was very complex (most are, sadly) and took too long to start. I was able to diagnose why using new features of Go’s 1.10 trace tool. This post describes my workflow and what led me there.

The example code I’m using for this post is at https://github.com/cep21/trace-110. My integration test was a bit more complex, but generally had startup that was slow due to a single goroutine out of many that did lots of different things. In this example, takeIO is similar to the “startup” part of my integration test.

My toy example for…

A short checklist of what I wish for in a good Go library, in no particular order. This is a companion to the effective go list, Go code review comments list, and Go proverbs list.

In general, when given two reasonable ways to do something, defer to the option that does not violate these rules. Bend these rules only with a strong explanation why.

Dependencies

Tagged library versions

Use git tags to version your library. Semantic versioning is a reasonable system. If you care enough to disagree with semantic versioning, then you’re not the target here :)

No non stdlib dependencies

This is sometimes difficult to achieve, but…

Jack Lindamood

Software Engineer

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store