How to Use GitHub Copilot Effectively

Jun 22, 2022

I've been using GitHub Copilot for about a year now. I was initially skeptical.

Are the suggestions actually good? Don't I still need to read the code for correctness? Isn't it distracting?

Now, I couldn't imagine coding without it. For $10/mo, it's a great deal. I've never been more productive. But like any tool, you need to know how to use it.

Here are five tips on how to use GitHub Copilot effectively.

The more consistent you code is, the better Copilot's suggestions will be.

Copilot is surprisingly good at replicating structure – e.g., logging, error handling, and naming. Your suggestions are only as good as your structure. You need to prime Copilot with a few blocks before it starts to see the pattern. Aim for consistency in naming, function arguments, and control flow – you should be doing this even without Copilot.

We all want to provide verbose errors and logging messages, but it's time-consuming, and so we cut corners. Maybe we return a terse error or only log some of the request arguments. Copilot makes it easy enough to autocomplete the verbose versions of these, which means better in-code documentation.

Use Copilot for initial API discoverability

Copilot understands common open-source APIs exceptionally well. Using the AWS SDK and don't know what the SendMessage signature is for SQS? Forget how to instantiate a client? Copilot can be a quicker first touch to an API than the documentation. It might even suggest helpful flags or parameters that you missed.

Write the interface first, then the auto-generate the implementation

Another best practice that is enhanced by Copilot. Writing an interface or function signature first usually primes Copilot sufficiently well. Then, for utility functions, it can generally autogenerate the entire block.

Not just for code, but static data.

Copilot is great for generating protobuf definitions, YAML configuration, repetitive constants, and other types of data. While we might want to reduce repetition, DRY isn't always the best way. Schema definitions should adhere to a somewhat strict style, which makes them perfect for Copilot.

Prefer a little copying over a little dependency

Instead of vendoring in [left-pad](https://www.npmjs.com/package/left-pad) as a dependency, use Copilot to generate the function. There are benefits to using battle-tested generic libraries but also benefits to bringing simple code in-tree.