Skip to main content

Deploy from Dockerfile

Deploy custom applications that include a Dockerfile. Uncloud builds your image locally and distributes it across your cluster.

What You'll Need

  • An Uncloud cluster (see Getting Started)
  • A project with a Dockerfile
  • A compose.yaml file

Project Structure

Here's a typical project structure for a web application:

my-app/
├── Dockerfile
├── compose.yaml
├── requirements.txt
└── src/
└── app.py

Step 1: Create Your Dockerfile

Here's an example Dockerfile for a Python Flask app:

FROM python:3.11-slim

WORKDIR /app

COPY requirements.txt .
RUN pip install -r requirements.txt

COPY src/ ./src/

EXPOSE 8000

CMD ["python", "-m", "flask", "run", "--host=0.0.0.0", "--port=8000"]

Step 2: Create compose.yaml

Create a compose.yaml file that references your Dockerfile:

services:
web:
build: .
image: my-app:latest
x-ports:
- app.example.com:8000/https
environment:
FLASK_ENV: production

Key fields:

  • build: . - Tells Uncloud to build from the Dockerfile in current directory
  • image - Names your built image
  • x-ports - Exposes your app with HTTPS (see Publishing Services)

Step 3: Deploy

Deploy your application with a single command:

uc deploy

You'll see output like this:

Building service web...
[+] Building 12.3s (10/10) FINISHED
=> [internal] load build definition from Dockerfile
=> => transferring dockerfile: 234B
=> [internal] load .dockerignore
=> [1/4] FROM docker.io/library/python:3.11-slim
=> [2/4] WORKDIR /app
=> [3/4] COPY requirements.txt .
=> [4/4] RUN pip install -r requirements.txt
=> exporting to image
=> => naming to my-app:latest

Pushing images to cluster...
✓ Pushed my-app:latest to machine-1

Deployment plan:
┌───────────┬─────────┬────────┬─────────┬────────┐
│ Machine │ Service │ Create │ Update │ Remove │
├───────────┼─────────┼────────┼─────────┼────────┤
│ machine-1 │ web │ 1 │ 0 │ 0 │
└───────────┴─────────┴────────┴─────────┴────────┘

Proceed? (yes/no): yes

Deploying...
✓ Created web-1 on machine-1

Deployment successful!
Your app is live at: https://app.example.com

What Just Happened?

  1. Local Build: Uncloud built your Dockerfile using your local Docker daemon
  2. Image Push: The built image was pushed to all cluster machines (or specific machines if using x-machines)
  3. Container Creation: New containers were created from your image
  4. Zero Downtime: If updating existing containers, old ones are removed only after new ones are healthy

Updating Your App

Make changes and redeploy:

# Edit your code
vim src/app.py

# Deploy the updated app
uc deploy

Uncloud automatically:

  • Rebuilds the image with your changes
  • Creates new containers
  • Switches traffic with zero downtime
  • Removes old containers

Advanced Build Configuration

Custom Dockerfile Location

services:
web:
build:
context: .
dockerfile: docker/Dockerfile.prod
image: my-app:latest

Build Arguments

Pass build-time variables:

services:
web:
build:
context: .
args:
VERSION: "1.0.0"
BUILD_ENV: production
image: my-app:latest

Then use in your Dockerfile:

ARG VERSION
ARG BUILD_ENV
ENV APP_VERSION=${VERSION}

Deploy with custom build args:

uc deploy --build-arg VERSION=1.2.3

Target Specific Build Stage

For multi-stage builds:

services:
web:
build:
context: .
target: production
image: my-app:latest

Troubleshooting

Build Fails Locally

If your build fails, you'll see the Docker build error:

Error: failed to build service web: ...

Test your build directly with Docker:

docker build -t my-app:test .

Image Too Large

Large images take longer to push to cluster machines. Consider:

  • Using smaller base images (alpine variants)
  • Multi-stage builds to reduce final image size
  • Adding a .dockerignore file to exclude unnecessary files

Example .dockerignore:

node_modules
.git
*.log
.env

Port Mismatch

Ensure the port in x-ports matches the port your app listens on:

services:
web:
build: .
x-ports:
- app.example.com:8000/https # Must match EXPOSE in Dockerfile

Next Steps