Phoenix is a web development framework to build rich, interactive web applications, with components and concepts likened to Ruby on Rails or Python's Django. It is written in Elixir, a functional programming language.
Phoenix has great support for Docker, allowing you to create releases for your Phoenix app with a single command to generate database migrations and a production-ready Dockerfile.
This guide will take you through setting up a new realtime, interactive Phoenix HTML application with PostgreSQL, and building and deploying it on Northflank. You can also use Phoenix to build static websites, headless services, or deploy your application with a MySQL database instead. See Phoenix's up and running guide for more configuration options.
We'll also look at more advanced Northflank features that you can use to grow your project into production - scale up your resources, manage releases, and configure your workflow with infastructure-as-code (IaC), templates and release flows.
You should sign up for an account on Northflank if you haven't already, and link a version control system provider such as GitHub, GitLab, or Bitbucket.
If you don't have it already, install Elixir on your machine.
You'll also need to install and run PostgreSQL for local development. Linux users should install inotify-tools for live reloading.
If you already have a Phoenix application you'd like to deploy, you can skip to the next section.
Phoenix includes an application generator which makes it easy to get started on a new project. It will generate all the files required to begin creating an application or website that integrates with a PostgreSQL database.
- Open a shell and navigate to the directory where you want to create your new project
- Run
mix archive.install hex phx_new
to install the Phoenix application generator - Run
mix phx.new hello
to create a new Phoenix application and install the dependencies. - Open your new Phoenix project in your preferred IDE and find the
config/dev.exs
file. It should contain the configuration below. Update the values here to reflect your local PostgreSQL connection details:
config :hello, Hello.Repo,
username: "postgres",
password: "postgres",
hostname: "localhost",
database: "hello_dev",
stacktrace: true,
show_sensitive_data_on_connection_error: true,
pool_size: 10
In the shell in your Phoenix project, run
mix ecto.create
. This will create your database, as long as the Postgres user has the necessary permissions.Run
mix phx.server
to start your development server with live reloading. You can view it in your web browser at http://localhost:4000.
Phoenix comes with built-in functionality to make containerising your application as simple as possible. You can run the shell command mix phx.gen.release --docker
in your Phoenix project to create a new release and generate a production-ready Dockerfile in your project. Your Dockerfile should look something like this.
If you have Docker installed locally you can run docker build .
to build your image.
Building and deploying your Phoenix application on Northflank is as easy as developing it locally, if not easier!
To deploy your Phoenix app to Northflank you will create:
- A PostgreSQL addon
- A secret group
- A combined service
You'll need to push your Phoenix project to a Git repsoitory, such as on GitHub. Provided you have linked your VCS provider to your Northflank team, your repository should be private. Your repository will look something like this.
First you'll create a Northflank project to contain the resources for your Phoenix application.
Resources in projects can securely communicate with each other, and you can deploy projects in different regions to make sure they're close to you or your users. You can also choose to deploy into Northflank's managed cloud, or bring your own cloud provider account.
Select project from the create new menu in your Northflank team, call it Phoenix
and select a region close to you.
The default Phoenix application expects Postgres. Northflank allows you to create a managed, stateful Postgres instance that is scalable and highly-available, created in minutes with backups, disaster recover, and logs and metrics available at your fingertips.
In your new project create an addon
Select
PostgreSQL
, call itPhoenix data
, and select the most recent versionDisable TLS, as the template Phoenix application is not configured to use TLS.
You can deploy with the default compute plan, which is 0.5vCPU and 1GB memory, but if you need more resources for production select another plan
Click create addon
Your Postgres addon will begin provisioning and scaling up, which may take a minute.
Phoenix requires a connection string to access the Postgres database, as well as a secret key base to generate secrets for encrypting and signing data (for example for cookies and tokens).
Create a secret group to provide this environment variable to your application, and link your addon's connection details. These secrets are securely encrypted and injected during builds and deployments on container startup.
You can add more secrets here later for all your environment variables, secrets, and secret files. Secret groups can be inherited by multiple services and jobs to reduce duplication.
In your Northflank project create a new secret group and call it
Phoenix secrets
. You can leave the default configuration for now.Click
add variable
and enterSECRET_KEY_BASE
as the key 3and click the key button in the editor. Generate a secret value with a length of at least64
and copy and paste it to the value field.Next, in the linked addons section, click
show addons
and then clickconfigure
on your PostgreSQL addonClick the
POSTGRES_URI
to link the connection string to the secret group, and addDATABASE_URL
as an alias by clicking the add buttonClick
create secret group
to make these environment variables available to resources in your project
Next you'll create a combined service to build your application from your Git repository and deploy it in a single service.
A combined service gives you continuous integration and deployment out of the box. When you create a combined service you'll select a Git repository and branch from your linked VCS. When you push changes to that branch your combined service will automatically pull your repository, run a Docker build, push to the Northflank container registry, and finally completes a rolling restart on the Northflank cloud.
In your Northflank project create a new combined service and name it
Phoenix
Select your repository from the drop-down list and choose the
main
branchChoose
Dockerfile
as the build typeClick
add port
in Networking. Enter4000
for the port,HTTP
as the protocol. Enablepublicly expose this port to the internet
and name itapp
so you can view the website when it's deployed.Click
create service
Once you’ve created your combined service, you’ll be redirected to its dashboard. Here, you’ll notice that a new build has been triggered. Once the build completes, it will automatically deploy. You can access your application at the code.run
domain provided by Northflank, which is displayed prominently in the header.
From the combined service overview, you can monitor the progress of builds, check the status of deployed containers, and scale, pause and restart your service. Access more configuration options and deployment information from the sidebar.
To troubleshoot or inspect build and runtime containers, click on the build or deployment to view real-time logs and metrics, healthchecks, shell access.
These tools are invaluable for diagnosing issues, maintaining uptime, and ensuring your service has the necessary resources to meet demand.
On the resources page you can increase compute resources, which is the vCPU and memory allocated to each container, and scale the number of containers horizontally running simultaneously to handle increased demand. You can even enable autoscaling to handle this automatically, based on RPS, CPU and memory usage. By leveraging these features you can optimize your application’s performance and maintain reliability under varying load conditions.
You can implement an infrastructure as code approach to managing your deployments and infrastructure with Northflank templates. You can define reproducible workflows to create and update resources, run your release processs, and create ephemeral preview environments to deploy pull requests for review.
This part of the guide will take you through the steps to create a template for your Phoenix project so, and how you can run releases in a single click.
- Create a new template in your team, name it
Phoenix
and open the visual editor - The template will have a project and workflow nodes predefined. Enter the name
Phoenix
for your project, and select a region, andsave node
. - Drag an
addon
node from the nodes panel on the right into the sequential workflow that has a project ID.- Give it a name and select the latest version
- Disable TLS
- Click
save node
- Drag a
secret group
node and drop it directly below the addon in the template.- Give it a name, add the
SECRET_KEY_BASE
variable and enter${args.SECRET_KEY_BASE}
as the value. This will be explained later. - Click
show addons
andconfigure
the addon from the template withDATABASE_URL
as the alias forPOSTGRES_URI
. 3. Clicksave node
- Give it a name, add the
- Drag an
await condition
node below the secret group node in the template.- Choose
addon
for the resource kind - Select the reference to your addon node in the resource field
- Set it to wait until the
resource is running
andsave node
- Choose
- Drag a
combined service
node directly underneath the secret group node in the template.- Give it a name and select your Phoenix application's Git repository. Choose the branch you want to build.
- Select
Dockerfile
as the build type - Scroll down to the networking section and click
add port
. Enter4000
, select HTTP as the protocol, and enablepublicly expose this port to the internet
. - Click
save node
- Navigate to the template settings and
edit
the argument overrides. EnterSECRET_KEY_BASE
as the key, then click the key button in the editor. Generate a secret value with a length of at least64
and copy and paste it to the value field. This will provide your secret securely without saving it in the template code, making it accessible via the arguments object:"${args.SECRET_KEY_BASE}"
. - Finally click
create template
to save your template in your team
You can run the template and it will proceed through each node in sequence, creating the project, and then the addon and secret group. The await condition node will pause the template until the addon is ready, so that when the Phoenix application is deployed it can immediately connect to the database.
If your project already exists and you run the template it will patch any resources with the same names, and change any configuration values to those in the template, such as number of instances, compute plan, or secret values. You can use this to update your projects.
You can also use arguments and set overrides for your template, both to provide secrets securely and to use your template to deploy different environments or configurations of your project.
Phoenix has built-in tools to easily manage releases using Docker.
You can generate releases with the command mix phx.gen.release --docker
, which creates a Dockerfile for your release that includes any required database migrations. This will create a release for the environment (set by the build argument of MIX_ENV
).
This will then provide you with different commands to start your containers in your built image. For example, for the prod
environment:
# To start your system
/app/bin/app start
# To start your system with the Phoenix server running
/app/bin/server
# To run migrations
/app/bin/migrate
To run migrations you could add a job using your built image to run /app/bin/migrate
, or use a command override to run a migration before starting your application:
CMD ["sh", "-c", "/app/bin/migrate && /app/bin/server"]
To share your built image between your deployment and a job, you'll need to build it using a build service, rather than a combined service, which we'll cover in the next section. You can also learn more about running migrations on Northflank here.
Using a combined service is a convenient and simple way to build and deploy quickly. But what if you have a more complex workflow to manage your releases? Perhaps you need to back up your database before running migrations, and want to make sure you don't deploy a new release to production if the migration fails.
You can programmatise your release workflows using a Northflank pipeline with release flows. These allow you to manage your resources for different environments, and to create release workflows as templates.
Instead of using a combined service, you'll need to build and deploy your application in separate build and deployment services. You can use one build service to deploy to multiple jobs and services, and promote images from one deployment to another.
A release flow for your Phoenix application might consist of:
An addon backup node to back up your database
A job to run your migration against the database for this environment
A promote deployment node to move your deployed image from one stage to the next
You can integrate your cloud account with Northflank to deploy into other cloud providers, such as GCP, AWS, or Azure.
This will let you deploy Northflank-managed clusters into your chosen cloud provider and fine-tune your infrastructure and networking to suit your requirements.
You can deploy the same workloads and projects across any cloud provider, manually or using templates, without having to change a single configuration detail.
You can securely access your resources using the Northflank CLI, without exposing them to the public.
Install the Northflank CLI with the following commands:
npm i -g @northflank/cli
# or
yarn global add @northflank/cli
You can now copy the forward addon
command from your addon's overview, and run the command in a terminal on your machine, it looks something like this:
sudo northflank forward addon --projectId [project-name] --addonId [addon-name]
You'll need to enter your password as the forward command is run with root privileges so that it can write to your hosts file. While running, you'll be able to access your addon the same as deployments inside your Northflank project.
After running the command you'll be able to access your Northflank addon using the connection details shown in the addon overview, and provide these to any tools or applications on your local machine.
Northflank allows you to deploy your code and databases within minutes. Sign up for a Northflank account and create a free project to get started.
- Deployment of Docker containers
- Create your own stateful workloads
- Persistent volumes
- Observe & monitor with real-time metrics & logs
- Low latency and high performance
- Backup, restore and fork databases