Movatterモバイル変換


[0]ホーム

URL:


Skip to content
DEV Community
Log in Create account

DEV Community

Custom Ink Technology profile imageKen Collins
Ken Collins forCustom Ink Technology

Posted on • Originally published atdev.to

     

Getting Started with GitHub Codespaces from a Serverless Perspective

If you are into Serverless and AWS Lambda, you may already know that theAWS Serverless Application Model (SAM) CLI makes it easy to leverage their Dockerbuild images as development containers. We do exactly this for ourRails & Lambda projects.

Leveraging Docker with SAM ensures we have a Linux environment and versioned dependencies that closely mimic the Lambda Runtime or Container being shipped. The use andThe Promise of Docker to solve these problems is nothing new... but something else is.

✨ The Rise of Ephemeral Dev Environments

A few weeks ago GitHub's engineering team released anin-depth article announcing their internal usage of the now generally availableGitHub Codespaces. Since Custom Ink shares many of the same problems described in this post, I was curious if our Lambda projects could easily leverage Codespaces. But what is this new tool? Where did it come from? And what is thisdevcontainer.json file?

As best I can tell this all started in May of 2019 when the VS Code team first mentioned theirremote development extensions. About a year later this content was rolled up into theVS Code Remote Development guides we have today.

VS Code Remote Development Architecture Diagram

Prior to Codespaces, we have had a clear leader in the automated development environment space withGitpod. It was even featured in a January 2021 episode ofContainers from the Couch. Gitpod leverages the same technology built into VS Code for remote development.

However, sometimes slow and steady wins the race. If this were ever true for GitHub-based projects, I think we have a huge winner with GitHub Codespaces. Keep reading below on how your company (or you) could get started. I will even cover how well Codespaces has worked for our Lambda projects that use an existing Docker in Docker development pattern.

⚙️ GitHub Settings

GitHub Codespaces is ONLY available now for GitHub Teams & Enterprise Cloud plans. It is not yet available for public repositories. If you are an administrator of such an account, here are a few things I didat the organization level to get started experimenting.

  • Enable Codespaces: This can also be disabled completely or enabled for select users.
  • Repository Access: You can even limit repositories that are able to use Codespaces. If your GitHub account leverages permissions & teams, remember, Codespaces (via the generatedGITHUB_TOKEN will not grant anyone elevated permissions to other repositories.
  • Manage Spending Limits: It would have been neat to see a way to limit which VMs (vCPU/Memory) options could have been used here.
  • Organizational Secrets: Create any secrets your organization needs to enable individuals to work. Remember, Codespaces secrets can be set at the repository or even user level too. Pick the one(s) that work the best for y'all.

🔰 Developer Tips

It could go without saying but getting good at Codespaces for most may mean getting good at VS Code. Technically you could bring your own editor like Vim or Emacs. But trust me, as a recent Sublime Text convert, switching to VS Code is worth it. Make sure to take the time to Google, learn, and in some casesinstall packages that make the transition easier.

Dotfiles & Settings

Remote development needs to feel local! Everything that makes your editor & terminal productive needs to be available to you. As described in thePersonalizing Codespaces guide setting up your Dotfiles was high on my list.

For years I have maintained a personal Zshkit which had a ton of personal functions and aliases. When moving to Codespaces, I took the time to clean them up and create agithub.com/metaskills/dotfiles repository, cloned it locally and hooked it up to my ZSH (default shell on Mac)~/.zshrc file. Codespaces will automatically clone this repo when creating a Codespace and install it by running theinstall.sh script. Example.

if["$CODESPACES"="true"];thenecho"source /workspaces/.codespaces/.persistedshare/dotfiles/rc">>$HOME/.zshrcsudochsh-s /usr/bin/zshfi
Enter fullscreen modeExit fullscreen mode

You can leverage theCODESPACES environment variable to do any customization per environment. Also, do not forget to useSettings Sync. I think this is only needed if you use VS Code's web-based editor. More on that topic later.

Your Codespaces Settings

You canManage Your Codespaces settings at somewhat the same level as the organization. Here are a few settings I did.

  • Access & Security: Set this to "All repositories". Your needs may vary.
  • Editor Preference: Set to "Visual Studio Code" vs for web. Ensures the[<> Code] button on repos opens VS Code on my Mac and avoids the need to click redirect in the browser.
  • Region: I set this manually toEastUs but I suspect I had no reason to do so.
  • Added Secrets: Read below on using SSH with Ruby Bundler or NPM packages.

Codespaces Extension

Install theGitHub Codespaces for VS Code. I think this is done for you automatically if you are using the web-based editor. Installing it on your host machine's VS Code will mean you can use Codespaces without ever browsing to GitHub.com and clicking on a[<> Code] button.

The Codespaces Command Pallet in VS Code provided by the Codespaces Extension

The Integrated Terminal

Assuming you have setup your Dotfiles, VS Code'sintegrated terminal should feel familiar by mirroring your host machine's prompt, aliases, and more. If your default shell is ZSH, you may need to do a few things to help Codespaces use ZSH by default vs Bash. Here are my settings for the integrated terminal now. Mind you, there was (maybe still is)a bug in VS Code where ZSH would not be respected. I have noticed in some cases Bash is used but it is easy to launch a new profile with ZSH if that happens.

"terminal.integrated.fontSize":14,"terminal.integrated.defaultProfile.osx":"zsh","terminal.integrated.defaultProfile.linux":"zsh",
Enter fullscreen modeExit fullscreen mode

UsingCommand+K to clear the terminal's buffer is second nature to most. By default this key binding will not reach the integrated terminal. You can edit your Keyboard Shortcuts JSON file to solve for that. Below is a screen capture of the magic little button you have to press to edit that raw JSON file. Use the following snippet to fix this.

Super Hidden Keyboard Shortcuts JSON Edit Button

{"key":"cmd+k","command":"workbench.action.terminal.clear","when":"terminalFocus"}
Enter fullscreen modeExit fullscreen mode

Terminal visibility and placement. When working on my laptop's smaller screen, I learned that you can useControl+~ to toggle the visibility of the integrated terminal. However, when working at my desk and larger screen, I really want the integrated terminal to be to the right of my editor. Thanks to thisthis Stack Overflow here are convoluted steps to make this happen. Hopefully one day they will make this easier. 😅

  1. At the right top of the integrated terminal, click the+ sign to open a 2nd terminal.
  2. Within the panel to the right, right click any of the two profiles, selectMove into Editor Area.
  3. Close the bottom integrated terminal with thex button.
  4. Focus the editor tab at the top moved from step 2, click the[|] split editor button.
  5. Close the shell tab on the left side of the screen.

🎉 Fun Highlights

Here are a few things I was pleasantly surprised with Codespaces' DX and how it works:

  • When learning Codespaces or working on uncommitted code, you may have to rebuild your development container. Codespaces automatically maintains your present working directory, open files, etc when doing this. Amazing!
  • You can see all your Codespaces on GitHub by navigating tohttps://github.com/codespaces. However, I typically use VS Code'sextension to navigate, open, and disconnect.
  • Leveraging theCODESPACES environment variable set totrue is an easy way to integrate your existing tooling into Codespaces allowing your teams to support multiple ways to bootstrap your applications.
  • Forwarded ports are automatically detected via the integrated terminal's STDOUT. For example, a.bin/rails server will ouput whatever host/port you are using and Codespaces will see it. If needed you can use theforwardPorts config fordevcontainer.json.

⚠️ Difficult Lessons

Some hard lessons learned when dipping into the deep end of using GitHub Codespaces. If you have any to share, please drop some comments below.

Private Packages & SSH

GitHub does a great job at providing your Codespace with a short livedGITHUB_TOKEN. Most package managers including NPM and Bundler can leverage this. However, if your organization has standardized on SSH setting up your projects could be a problem.

Thankfully when I reached out on Twitter, Jonathan Carter on the Codespaces team,seemed to suggest they may be working on a native SSH integration one day. Till then, here is the solution I came up with. This process address some sequencing issues arounddevcontainer.json'sLifecycle Scripts and when your Dotfiles are installed. Credit to VS CodesUsing SSH Keys guide. Also, some things here are pulled directly from theGitHub Action to setup SSH. Again, thanks to Johnathan Carter for the ideas.

  1. Create a personal Codespace secret calledPERSONAL_SSH_KEY by visiting this pagehttps://github.com/settings/codespaces/secrets/new and adding your private key, typically found in the~/.ssh/id_rsa file.
  2. Add this snippet to yourpostCreate script. It ensures GitHub is in the known hosts for SSH.
echo"Adding GitHub.com keys to ~/.ssh/known_hosts"printf"\ngithub.com ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAq2A7hRGmdnm9tUDbO9IDSwBK6TbQa+PXYPCPy6rbTrTtw7PHkccKrpp0yVhp5HdEIcKr6pLlVDBfOLX9QUsyCOV0wzfjIJNlGEYsdlLJizHhbn2mUjvSAHQqZETYP81eFzLQNnPHt4EVVUh7VfDESU84KezmD5QlWpXLmvU31/yMf+Se8xhHTvKSCZIFImWwoG6mbUoWf9nzpIoaSjB+weqqUUmpaaasXVal72J+UX2B+2RPW3RcT0eOzQgqlJL3RKrTJvdsjE3JEAvGq3lGHSZXy28G3skua2SmVi/w4yCE6gbODqnTWlg7+wC604ydGXA8VJiS5ap43JXiUFFAaQ==\n">> ~/.ssh/known_hostsprintf"\ngithub.com ssh-dss AAAAB3NzaC1kc3MAAACBANGFW2P9xlGU3zWrymJgI/lKo//ZW2WfVtmbsUZJ5uyKArtlQOT2+WRhcg4979aFxgKdcsqAYW3/LS1T2km3jYW/vr4Uzn+dXWODVk5VlUiZ1HFOHf6s6ITcZvjvdbp6ZbpM+DuJT7Bw+h5Fx8Qt8I16oCZYmAPJRtu46o9C2zk1AAAAFQC4gdFGcSbp5Gr0Wd5Ay/jtcldMewAAAIATTgn4sY4Nem/FQE+XJlyUQptPWMem5fwOcWtSXiTKaaN0lkk2p2snz+EJvAGXGq9dTSWHyLJSM2W6ZdQDqWJ1k+cL8CARAqL+UMwF84CR0m3hj+wtVGD/J4G5kW2DBAf4/bqzP4469lT+dF2FRQ2L9JKXrCWcnhMtJUvua8dvnwAAAIB6C4nQfAA7x8oLta6tT+oCk2WQcydNsyugE8vLrHlogoWEicla6cWPk7oXSspbzUcfkjN3Qa6e74PhRkc7JdSdAlFzU3m7LMkXo1MHgkqNX8glxWNVqBSc0YRdbFdTkL0C6gtpklilhvuHQCdbgB3LBAikcRkDp+FCVkUgPC/7Rw==\n">> ~/.ssh/known_hosts
Enter fullscreen modeExit fullscreen mode
  1. Add this snippet to your Dotfiles. It will ensure the proper SSH agent is started, if not already, and that the key environment variables are set.
if["$CODESPACES"="true"];then  if[-z"$SSH_AUTH_SOCK"];thenRUNNING_AGENT="`ps-ax |grep'ssh-agent -s' |grep-vgrep |wc-l |tr-d'[:space:]'`"if["$RUNNING_AGENT"="0"];then# Launch a new instance of the agent      ssh-agent-s &>$HOME/.ssh/ssh-agentfieval`cat$HOME/.ssh/ssh-agent`fi# Add my SSH key.if[-n"${PERSONAL_SSH_KEY+1}"];thenssh-add -<<<"${PERSONAL_SSH_KEY}"fifi
Enter fullscreen modeExit fullscreen mode

In order to see this all come together with our Docker in Docker Lambda patterns, please read theServerless Docker Patterns article in this series where we describe how to use theSSH_AUTH_SOCK in a cross platform way for Mac & Linux.

AWS CLI

For our Lambda projects we use Docker in Docker patterns where both the AWS & SAM CLIs are pre-installed on the development image. However, you may need the AWS CLI installed on the developer's host machine too. In this case, Codespaces. Here is a short snippet that you can use in yourpostCreate script.

echo"Installing AWS CLI"pushd /tmpcurl"https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip"-o"awscliv2.zip"unzip-qq awscliv2.zipsudo ./aws/installrm-rf awscliv2.zip ./awspopd
Enter fullscreen modeExit fullscreen mode

Docker in Docker

I've said this before but cross platform Docker in Docker is really hard. This series aims to talk about most of them, but one I learned the hard way is that sometimes the pain comes from the ones you love... in this case AWS SAM. The team is doing some amazing work but I ran into a few issues where Docker in Docker patterns have broken down. Read here for details.

🚂 Full Lamby Example

Assuming the other patterns were in place like variouspostCreate hooks for SSH, using GitHub Codespaces with your already Docker'ized project is super easy. Here is a complete.devcontainer/devcontainer.json file for one of our projects. Again, see theServerless Docker Patterns related post on how we are usingCOMPOSE_FILE for Mac filesystem performance and why it would be needed here.

{"name":"my-application","forwardPorts":[4020],"remoteEnv":{"COMPOSE_FILE":"docker-compose.yml"},"postCreateCommand":"./.devcontainer/postCreate"}
Enter fullscreen modeExit fullscreen mode

In fact, none of this would be needed for a starter application! Give it a try. Go through ourLamby Quick Start guide, commit your project to GitHub... and give Codespaces a try!

🔐 Security Questions

The Codespaces team was kind enough to write their ownSecurity in Codespaces documentation. I'll highlight their introduction below:

Codespaces is designed to be security hardened by default. Consequently, you will need to ensure that your software development practices do not risk reducing the security posture of your codespace.

This guide describes the way Codespaces keeps your development environment secure and provides some of the good practices that will help maintain your security as you work. As with any development tool, remember that you should only open and work within repositories you know and trust.

Good stuff! Security is a shared responsibility and it appears GitHub is doing their part. Please read over the full documentation for more information, but here are a few things I paid special attention to.

  • Audit Logs: Are generated and can be queried.
  • Organization & User Secrets: Built on thesame technology GitHub draws a line between GitHub standard org/user secrets with the Codespace ones. Again, they can be set at the organization, repository, or user. Providing an immense amount of control and security layers.
  • Dotfiles: Remind users that these are public repositories! Tho possible to encrypt secrets, I personally recommend keeping them basic to aliases and functions.
  • Secure Networking: Authenticated via GitHub via temporary tokens. Forwarding ports for web servers is done securely over the network between the host. Nothing is public by default.

🔮 What is Coming?

As mentioned above, I would love to see a native SSH solution. For now, the workarounds are minimal and feel secure with GitHub Secrets and Codespaces integration.

In their introductoryblog article, the GitHub team put a lot of emphasis on prebuilds ensuring that each Codespaces development environment was super fast to setup. This was critical for their team and as of now Gitpod is making a clear distinction this is akey differentiator for them. I suspect prebuilds are coming soon. 🤔

📚 Resources

Thanks so much for reading! I would love to hear if you found this article helpful or what your organization may be doing with GitHub Codespaces. 💕

Top comments(0)

Subscribe
pic
Create template

Templates let you quickly answer FAQs or store snippets for re-use.

Dismiss

Are you sure you want to hide this comment? It will become hidden in your post, but will still be visible via the comment'spermalink.

For further actions, you may consider blocking this person and/orreporting abuse

More fromCustom Ink Technology

DEV Community

We're a place where coders share, stay up-to-date and grow their careers.

Log in Create account

[8]ページ先頭

©2009-2025 Movatter.jp