Go-based web application
This directory contains an example Go-based web application designed to be developed and run on a cloud-based container host (though it can also be run locally, e.g. via Docker Desktop). It uses Mutagen's support for Docker containers to synchronize code from the local filesystem to a shared container volume and to forward network traffic to the various containerized services.
This application (a web-based message board) is kept intentionally simple, but still contains multiple services running in separate containers to illustrate how a more complex application with the same architecture might be organized. The container orchestration setup outlined here is for development, though a production setup would look similar (and would typically live inside the same codebase with slightly different container definitions and orchestration files).
The development setup consists of five services:
- An empty
mutagenservice that sits idle and serves as the hosting point for
mutagen-agentprocesses (which provide code synchronization and network forwarding)
- A database service running PostgreSQL
- A Go-based API server that handles message read/write requests
- A Go-based web server that serves the front-end content
In a production setup, you would typically only have three services: the database, the API server, and the web server. The front-end would usually be statically built and bundled with the web server container image, while the development service would be unnecessary.
The application itself consists of a simple front-end that allows users to submit messages (which are sent via AJAX to the API and stored in the database) and read recently submitted messages (which are loaded from the database and served by the API via AJAX). It's worth noting that this application is not production-ready (it has no authentication, CSRF-prevention, rate-limiting, etc.), but its architecture does mirror that of a fully fledged application and thus the orchestration setup (both in terms of Docker Compose and Mutagen) should look very similar to a "real" application.
This section assumes that you have a Docker daemon available to the
command. You can achieve this by running a local Docker daemon with a tool like
Docker Desktop or by
configuring access to a cloud-based container host like
RancherOS and setting the
environment variable appropriately. Mutagen will work with either of these
cases, though setting up a cloud-based container host has numerous performance
This section also assumes and that you have
Docker Compose installed. This is often
bundled with Docker client installations, so check to see if you have it already
Once the Docker daemon is set up, you can start the project using:
mutagen project start
This project uses Mutagen's
beforeCreate hook (see
mutagen.yml) to create a
shared Docker volume for storing and sharing synchronized code (as well as an
empty service that can access this volume and host Mutagen agents). It then uses
flushOnCreate flag to ensure code is fully synchronized before
finally starting the remaining Docker Compose services in the
Once the environment is running, you can access the application at http://localhost:8080.
Try making an edit to the
frontend/index.html file in your local editor. Once
saved, you can refresh the page to see your changes. It's worth noting that
Mutagen's synchronization will also work with build tools and servers that
perform hot reloads, you'd just need to use one of those tools as the container
entry point instead of the simple setup used here.
The API and web services are configured to rebuild their server binaries on
restart, so if you make a change to the server code, then you'll need to restart
the corresponding service using
docker-compose restart api or
docker-compose restart web. These rebuilds could also be automated using a
tool like Watchman, but that's outside
the scope of this demo.
You can also work inside the containers by starting a shell. For example, try
docker-compose exec frontend sh. This will start an interactive shell
frontend service container.
To help automate common workflows, Mutagen offers a way to define custom commands for projects. For example, try running the following:
mutagen project run database
This invokes a custom command called
database (defined in
commands section). It will drop you into a
psql shell running in the
database container and connected to the message database. Try running
SELECT * FROM messages; after creating some messages in the web application.
Using custom commands, you can define shells, common debugging workflows, build commands, or even script deployment. Defining these common workflows becomes even more powerful when every developer on a team is using the same environment with the same tools available.
Once you're done working, you can terminate the project using:
mutagen project terminate
This project uses Mutagen's
afterTerminate hook (see
mutagen.yml) to tear
down the Docker Compose services (and associated resources) after terminating
synchronization and forwarding.