各位大大好
目前我嘗試用docker做前後端分離的練習
架構是這樣的
總共三個container (frontend(Vue), backend(Laravel), database)
重點擺在frontend和backend的溝通
由於我要跟外部的網站做oauth 需要填入redirect url
所以我用ngrok把frontend的port expose
我嘗試用nginx(跟frontend在同一個container上)做reserve透過docker設定的network去打到backend的api url 可是在ngrok會傳回503
我猜是ngrok在碰到nginx轉換的時候沒辦法認得
想請問解決方法或有沒有其他方式能達成我要的需求?
P.S:如果單純更改vue.config.js
中的url是可以達成的
以下檔案供參考
/frontend/Dockerfile
FROM node:16 AS build
WORKDIR /app
COPY package*.json ./
RUN npm install -g @vue/cli-service \
&& npm install -g @vue/cli \
&& npm install
RUN apt-get update \
&& apt-get install nginx -y
CMD ["npm", "run", "dev"]
/backend/Dockerfile
FROM php:7.2-fpm
WORKDIR /var/www/html/dns
COPY . /var/www/html/dns
RUN apt-get update \
&& apt-get install -y \
&& apt-get install libpng-dev -y \
&& apt-get install supervisor -y \
&& php -r "copy('https://getcomposer.org/installer', 'composer-setup.php');" \
&& php -r "if (hash_file('sha384', 'composer-setup.php') === '55ce33d7678c5a611085589f1f3ddf8b3c52d662cd01d4ba75c0ee0459970c2200a51f492d557530c71c15d8dba01eae') { echo 'Installer verified'; } else { echo 'Installer corrupt'; unlink('composer-setup.php'); } echo PHP_EOL;" \
&& php composer-setup.php \
&& php -r "unlink('composer-setup.php');" \
&& mv composer.phar /usr/local/bin/composer \
&& docker-php-ext-install sockets \
&& docker-php-ext-install zip \
&& docker-php-ext-install gd \
&& composer install
CMD ["php", "artisan", "serve", "--host", "0.0.0.0"] \
&& ["php", "artisan", "queue:work", "--daemon", "--quiet", "--queue=default", "--delay=3", "--sleep=3", "--tries=3"]
/docker-compose.yml
version: "3"
networks:
connect:
services:
frontend:
build: ./frontend
volumes:
- ./frontend:/app
- ./frontend/config/default.conf:/etc/nginx/conf.d/default.conf
ports:
- 8080:9528
networks:
- connect
tty: true
backend:
build: ./backend/
ports:
- 8000:8000
expose:
- 8000
networks:
- connect
volumes:
- ./backend/:/var/www/html/dns # 將專案掛載進容器裡面
restart: always
/config/default.conf
server {
listen 8000;
server_name localhost;
location /api {
proxy_pass http://backend:8000/api;
}
}
其餘小問題
docker有時候我更改DockerFile都還是沒變,我都要砍掉image重啟才有用,請問原因(cache?)
根據測試環境或是正式環境,會有不同的容器配置
測試環境的情況下,是使用 npm run dev
來跑前端
正式環境的情況下,會將前端打包後,放到 nginx
底下直接作為靜態檔案來服務
這段看你自己使用什麼 web server 應該都大同小異
兩種,我都建議使用 nginx
來統一你對外服務的 port
詳細大概是這樣配置
nginx
可以透過 docker
內部的 network
進行反向代理
這樣整個服務就會只有 nginx
是對外,而不需要開啟過多的服務
先將這個流程部署完之後,應該可以解決你大部分的問題!
每次有更動 Dockerfile
都要重新 docker compose build
並且再次啟動 docker compose up -d
才會確實生效哦!
或是你也可以直接輸入 docker compose up -d --build
這個就會在啟動之前幫你去打包相對應的 image
參考:https://docs.docker.com/engine/reference/commandline/compose_up/#options
感謝大大回答 很詳細
我也是看到網路上很多方法都是用nginx當作對外
但這樣在開發時 不就用不到hot reload的方便嗎
畢竟前端打包完就放著,如果有一點小改就要下指令再重打包
這也是我用node image然後再把nginx裝進去的原因
一樣可以哦 只要在 nginx 加入 websocket 的條件就可以了
不過我不清楚 vue 的機制 他也是用 webpack 的 hot reload 嗎
一樣的話可以參考以下設定
location /ws{
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $remote_addr;
proxy_set_header Host $host;
proxy_pass http://frontend:3000;
proxy_redirect off;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
}
好的大大 我來試試