Преглед на файлове

nginx-golang-mysql: add dev envs support (#274)

* Add Docker Desktop Development Environments config
* Use nginx image with read-only bind mount instead of building a
  custom image
* Upgrade Go dependencies

Co-authored-by: Guillaume Lours <guillaume@lours.me>
Signed-off-by: Milas Bowman <milas.bowman@docker.com>
Milas Bowman преди 3 години
родител
ревизия
f3293008b0

+ 50 - 0
nginx-golang-mysql/.docker/docker-compose.yaml

@@ -0,0 +1,50 @@
+services:
+  backend:
+    build:
+      context: backend
+      target: dev-envs
+    volumes:
+      - /var/run/docker.sock:/var/run/docker.sock
+    secrets:
+      - db-password
+    depends_on:
+      db:
+        condition: service_healthy
+
+  db:
+    image: mariadb:10-focal
+    command: '--default-authentication-plugin=mysql_native_password'
+    restart: always
+    healthcheck:
+      test: ["CMD", "mysqladmin", "ping", "-h", "127.0.0.1", "--silent"]
+      interval: 3s
+      retries: 5
+      start_period: 30s
+    secrets:
+      - db-password
+    volumes:
+      - db-data:/var/lib/mysql
+    environment:
+      - MYSQL_DATABASE=example
+      - MYSQL_ROOT_PASSWORD_FILE=/run/secrets/db-password
+    expose:
+      - 3306
+
+  proxy:
+    image: nginx
+    volumes:
+      - type: bind
+        source: ./proxy/nginx.conf
+        target: /etc/nginx/conf.d/default.conf
+        read_only: true
+    ports:
+      - 80:80
+    depends_on: 
+      - backend
+
+volumes:
+  db-data:
+
+secrets:
+  db-password:
+    file: db/password.txt

+ 37 - 21
nginx-golang-mysql/README.md

@@ -1,5 +1,5 @@
 ## Compose sample application
-### Go server with an Nginx proxy and a MySQL database
+### Go server with an Nginx proxy and a MariaDB/MySQL database
 
 Project structure:
 ```
@@ -7,30 +7,37 @@ Project structure:
 ├── backend
 │   ├── Dockerfile
 │   ├── go.mod
+│   ├── go.sum
 │   └── main.go
 ├── db
 │   └── password.txt
-├── compose.yaml
 ├── proxy
-│   ├── conf
-│   └── Dockerfile
+│   └── nginx.conf
+├── compose.yaml
 └── README.md
 ```
 
 [_compose.yaml_](compose.yaml)
-```
+```yaml
 services:
   backend:
-    build: backend
+    build:
+      context: backend
+      target: builder
     ...
   db:
     # We use a mariadb image which supports both amd64 & arm64 architecture
-    image: mariadb:10.6.4-focal
+    image: mariadb:10-focal
     # If you really want to use MySQL, uncomment the following line
-    #image: mysql:8.0.27
+    #image: mysql:8
     ...
   proxy:
-    build: proxy
+    image: nginx
+    volumes:
+      - type: bind
+        source: ./proxy/nginx.conf
+        target: /etc/nginx/conf.d/default.conf
+        read_only: true
     ports:
     - 80:80
     ...
@@ -42,11 +49,11 @@ Make sure port 80 on the host is not already being in use.
 > ℹ️ **_INFO_**  
 > For compatibility purpose between `AMD64` and `ARM64` architecture, we use a MariaDB as database instead of MySQL.  
 > You still can use the MySQL image by uncommenting the following line in the Compose file   
-> `#image: mysql:8.0.27`
+> `#image: mysql:8`
 
 ## Deploy with docker compose
 
-```
+```shell
 $ docker compose up -d
 Creating network "nginx-golang-mysql_default" with the default driver
 Building backend
@@ -64,24 +71,33 @@ Creating nginx-golang-mysql_proxy_1   ... done
 ## Expected result
 
 Listing containers must show three containers running and the port mapping as below:
-```
-$ docker ps
-CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                  NAMES
-8906b14c5ad1        nginx-golang-mysql_proxy     "nginx -g 'daemon of…"   2 minutes ago       Up 2 minutes        0.0.0.0:80->80/tcp    nginx-golang-mysq
-l_proxy_1
-13e0e0a7715a        nginx-golang-mysql_backend   "/server"                2 minutes ago       Up 2 minutes        8000/tcp              nginx-golang-mysq
-l_backend_1
-ca8c5975d205        mysql:5.7                    "docker-entrypoint.s…"   2 minutes ago       Up 2 minutes        3306/tcp, 33060/tcp   nginx-golang-mysq
+```shell
+$ docker compose ps
+NAME                           COMMAND                  SERVICE             STATUS              PORTS
+nginx-golang-mysql-backend-1   "/code/bin/backend"      backend             running
+nginx-golang-mysql-db-1        "docker-entrypoint.s…"   db                  running (healthy)   3306/tcp
+nginx-golang-mysql-proxy-1     "/docker-entrypoint.…"   proxy               running             0.0.0.0:80->80/tcp
 l_db_1
 ```
 
 After the application starts, navigate to `http://localhost:80` in your web browser or run:
-```
+```shell
 $ curl localhost:80
 ["Blog post #0","Blog post #1","Blog post #2","Blog post #3","Blog post #4"]
 ```
 
 Stop and remove the containers
-```
+```shell
 $ docker compose down
 ```
+
+## Use with Docker Development Environments
+
+You can use this sample with the Dev Environments feature of Docker Desktop.
+
+![Screenshot of creating a Dev Environment in Docker Desktop](../dev-envs.png)
+
+To develop directly on the services inside containers, use the HTTPS Git url of the sample:
+```
+https://github.com/docker/awesome-compose/tree/master/nginx-golang-mysql
+```

+ 38 - 7
nginx-golang-mysql/backend/Dockerfile

@@ -1,10 +1,41 @@
-FROM golang:1.13-alpine AS build
-WORKDIR /go/src/github.com/org/repo
+# syntax=docker/dockerfile:1.4
+FROM --platform=$BUILDPLATFORM golang:1.18-alpine AS builder
+
+WORKDIR /code
+
+ENV CGO_ENABLED 0
+ENV GOPATH /go
+ENV GOCACHE /go-build
+
+COPY go.mod go.sum ./
+RUN --mount=type=cache,target=/go/pkg/mod/cache \
+    go mod download
+
 COPY . .
 
-RUN go build -o server .
+RUN --mount=type=cache,target=/go/pkg/mod/cache \
+    --mount=type=cache,target=/go-build \
+    go build -o bin/backend main.go
+
+CMD ["/code/bin/backend"]
+
+FROM builder AS dev-envs
+
+RUN <<EOF
+apk update
+apk add git
+EOF
+
+RUN <<EOF
+addgroup -S docker
+adduser -S --shell /bin/bash --ingroup docker vscode
+EOF
+
+# install Docker tools (cli, buildx, compose)
+COPY --from=gloursdocker/docker / /
+
+CMD ["go", "run", "main.go"]
 
-FROM alpine:3.12
-EXPOSE 8000
-COPY --from=build /go/src/github.com/org/repo/server /server
-CMD ["/server"]
+FROM scratch
+COPY --from=builder /code/bin/backend /usr/local/bin/backend
+CMD ["/usr/local/bin/backend"]

+ 7 - 6
nginx-golang-mysql/backend/go.mod

@@ -1,10 +1,11 @@
-module github.com/org/repo
+module github.com/docker/awesome-compose/nginx-golang-mysql/backend
 
-go 1.13
+go 1.18
 
 require (
-	github.com/go-sql-driver/mysql v1.3.0
-	github.com/gorilla/context v1.1.1
-	github.com/gorilla/handlers v1.3.0
-	github.com/gorilla/mux v1.6.2
+	github.com/go-sql-driver/mysql v1.6.0
+	github.com/gorilla/handlers v1.5.1
+	github.com/gorilla/mux v1.8.0
 )
+
+require github.com/felixge/httpsnoop v1.0.1 // indirect

+ 8 - 0
nginx-golang-mysql/backend/go.sum

@@ -0,0 +1,8 @@
+github.com/felixge/httpsnoop v1.0.1 h1:lvB5Jl89CsZtGIWuTcDM1E/vkVs49/Ml7JJe07l8SPQ=
+github.com/felixge/httpsnoop v1.0.1/go.mod h1:m8KPJKqk1gH5J9DgRY2ASl2lWCfGKXixSwevea8zH2U=
+github.com/go-sql-driver/mysql v1.6.0 h1:BCTh4TKNUYmOmMUcQ3IipzF5prigylS7XXjEkfCHuOE=
+github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
+github.com/gorilla/handlers v1.5.1 h1:9lRY6j8DEeeBT10CvO9hGW0gmky0BprnvDI5vfhUHH4=
+github.com/gorilla/handlers v1.5.1/go.mod h1:t8XrUpc4KVXb7HGyJ4/cEnwQiaxrX/hz1Zv/4g96P1Q=
+github.com/gorilla/mux v1.8.0 h1:i40aqfkR1h2SlN9hojwV5ZA91wcXFOvkdNIeFDP5koI=
+github.com/gorilla/mux v1.8.0/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So=

+ 16 - 5
nginx-golang-mysql/compose.yaml

@@ -1,20 +1,23 @@
 services:
   backend:
-    build: backend
+    build:
+      context: backend
+      target: builder
     secrets:
       - db-password
     depends_on:
       db:
         condition: service_healthy
+
   db:
     # We use a mariadb image which supports both amd64 & arm64 architecture
-    image: mariadb:10.6.4-focal
+    image: mariadb:10-focal
     # If you really want to use MySQL, uncomment the following line
-    #image: mysql:8.0.27
+    #image: mysql:8
     command: '--default-authentication-plugin=mysql_native_password'
     restart: always
     healthcheck:
-      test: ["CMD", "mysqladmin", "ping", "-h", "127.0.0.1", "--silent"]
+      test: ['CMD-SHELL', 'mysqladmin ping -h 127.0.0.1 --password="$$(cat /run/secrets/db-password)" --silent']
       interval: 3s
       retries: 5
       start_period: 30s
@@ -27,14 +30,22 @@ services:
       - MYSQL_ROOT_PASSWORD_FILE=/run/secrets/db-password
     expose:
       - 3306
+
   proxy:
-    build: proxy
+    image: nginx
+    volumes:
+      - type: bind
+        source: ./proxy/nginx.conf
+        target: /etc/nginx/conf.d/default.conf
+        read_only: true
     ports:
       - 80:80
     depends_on: 
       - backend
+
 volumes:
   db-data:
+
 secrets:
   db-password:
     file: db/password.txt

+ 0 - 2
nginx-golang-mysql/proxy/Dockerfile

@@ -1,2 +0,0 @@
-FROM nginx:1.13-alpine
-COPY conf /etc/nginx/conf.d/default.conf

+ 2 - 2
nginx-golang-mysql/proxy/conf → nginx-golang-mysql/proxy/nginx.conf

@@ -2,7 +2,7 @@ server {
     listen       80;
     server_name  localhost;
     location / {
-        proxy_pass   http://backend:8000;
+        proxy_pass          http://backend:8000;
+        proxy_http_version  1.1;
     }
-
 }