Quasar+Docker部署问题:localhost无法访问,容器IP可正常访问
我正在尝试用Docker部署一套包含Nginx + Quasar + Laravel + MySQL的技术栈。由于第三方插件要求使用已备案域名,希望始终通过localhost而非动态公网IP访问应用。
刚接触Docker,可能存在概念盲区,目前无法通过http://localhost:9000/访问Quasar应用,推测问题与端口转发有关。
所有服务启动后,进入Quasar容器执行quasar dev,得到两个访问地址:
App URL................ http://localhost:9000/
http://172.xx.xx.4:9000/
容器IP对应的地址可正常访问,但http://localhost:9000/访问时提示:
This site can’t be reached
localhost refused to connect.
Try:
Checking the connection
Checking the proxy and the firewall
ERR_CONNECTION_REFUSED
以下是相关配置文件:
docker-compose.yml
version: '3.8' services: # Laravel App api: build: args: user: luciano uid: 1000 context: backend # path to the docker file dockerfile: Dockerfile # name of the dockerfile image: laravel # name to assign to the image container_name: viso-api # name to assign to the container restart: unless-stopped # always restart container except when stopped (manually or otherwise) working_dir: /var/www # working directory of the running container tty: true # once started keeps container running (attaching a terminal to it, like using -t docker directive) environment: # set environment variables SERVICE_NAME: app SERVICE_TAGS: dev depends_on: - db volumes: # map application directory in the /var/www/html directory of the container - './backend:/var/www' - './.docker/php/uploads.ini:/usr/local/etc/php/conf.d/uploads.ini' networks: # networks at which container is connected - viso-network # Quasar App quasar: build: context: frontend dockerfile: Dockerfile target: develop-stage image: quasar container_name: viso-frontend working_dir: /app volumes: - './frontend:/app' networks: - viso-network depends_on: - api # command: /bin/sh -c "yarn && quasar dev" # Nginx Service nginx: image: 'nginx:1.23.1-alpine' container_name: viso-nginx restart: unless-stopped tty: true ports: # exposed ports - '8888:80' volumes: - './backend:/var/www' - './.docker/nginx:/etc/nginx/conf.d' # nginx configuration networks: - viso-network depends_on: - db - api # MySQL Service db: image: 'mysql:8.0.30' container_name: viso-db restart: unless-stopped tty: true ports: - '33066:3306' environment: MYSQL_DATABASE: viso_manager MYSQL_ROOT_PASSWORD: secretroot MYSQL_ROOT_HOST: '%' MYSQL_USER: luciano MYSQL_PASSWORD: secretluciano volumes: - './.dbdata:/var/lib/mysql' - './.docker/mysql/my.cnf:/etc/mysql/conf.d/my.cnf' networks: - viso-network # Docker Networks networks: viso-network: driver: bridge # Volumes volumes: .dbdata:
Laravel Dockerfile
FROM php:8.1-fpm # Set working directory WORKDIR /var/www # Get argument defined in docker-compose file ARG user ARG uid # Install system dependencies RUN apt-get update && apt-get install -y \ git \ curl \ libonig-dev \ libxml2-dev \ libpng-dev \ libwebp-dev \ libjpeg-dev \ libfreetype6-dev \ zip \ unzip \ nano \ && docker-php-ext-install pdo_mysql \ && docker-php-ext-install mbstring \ && docker-php-ext-install exif \ && docker-php-ext-install pcntl \ && docker-php-ext-install bcmath \ && docker-php-ext-install gd \ && docker-php-ext-configure gd --with-jpeg --with-webp --with-freetype \ && docker-php-ext-install -j$(nproc) gd \ && docker-php-source delete # Clear cache RUN apt-get clean && rm -rf /var/lib/apt/lists/* # Install Composer RUN curl -sS https://getcomposer.org/installer | php -- --install-dir=/usr/local/bin --filename=composer # Create system user to run Composer and Artisan Commands RUN useradd -G www-data,root -u $uid -d /home/$user $user RUN mkdir -p /home/$user/.composer && \ chown -R $user:$user /home/$user EXPOSE 80 USER $user
Quasar Dockerfile
# develop stage FROM node:alpine as develop-stage WORKDIR /app COPY package*.json ./ RUN yarn global add @quasar/cli COPY . . RUN yarn install EXPOSE 9999 # build stage FROM develop-stage as build-stage RUN yarn RUN quasar build # production stage FROM nginx:alpine as production-stage COPY --from=build-stage /app/dist/spa /usr/share/nginx/html EXPOSE 80 CMD ["nginx", "-g", "daemon off;"]
nginx.conf
server { listen 80; index index.php index.html; error_log /var/log/nginx/error.log; access_log /var/log/nginx/access.log; root /var/www/public; client_max_body_size 32M; location ~ \.php$ { try_files $uri =404; fastcgi_split_path_info ^(.+\.php)(/.+)$; fastcgi_pass api:9000; fastcgi_index index.php; include fastcgi_params; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; fastcgi_param PATH_INFO $fastcgi_path_info; } location / { try_files $uri $uri/ /index.php?$query_string; gzip_static on; } location /storage { add_header "Access-Control-Allow-Origin" "*"; } }
核心问题
- Quasar开发服务绑定范围有限:
quasar dev默认仅绑定容器内部的localhost,宿主机无法通过端口转发访问该服务。 - 端口未映射到宿主机:docker-compose中Quasar服务未配置端口映射规则,宿主机9000端口无法关联到容器内的服务端口。
修复步骤
1. 修改docker-compose.yml的Quasar服务配置
添加端口映射并调整启动命令:
quasar: build: context: frontend dockerfile: Dockerfile target: develop-stage image: quasar container_name: viso-frontend working_dir: /app volumes: - './frontend:/app' networks: - viso-network depends_on: - api ports: - "9000:9000" # 新增:将宿主机9000端口映射到容器9000端口 command: /bin/sh -c "quasar dev -H 0.0.0.0" # 新增:绑定容器所有网卡地址,允许外部访问
2. 验证启动状态
修改后启动Quasar服务,应该看到类似输出:
App URL................ http://0.0.0.0:9000/
http://172.xx.xx.4:9000/
http://localhost:9000/
此时宿主机访问http://localhost:9000/即可正常打开Quasar应用。
3. 可选:通过Nginx统一访问入口(推荐)
如果希望通过Nginx的8888端口同时访问前端和后端,可以修改nginx.conf添加反向代理:
server { listen 80; index index.php index.html; error_log /var/log/nginx/error.log; access_log /var/log/nginx/access.log; # Laravel API 路由 location /api { root /var/www/public; try_files $uri $uri/ /index.php?$query_string; gzip_static on; } location ~ ^/api/.+\.php$ { try_files $uri =404; fastcgi_split_path_info ^(.+\.php)(/.+)$; fastcgi_pass api:9000; fastcgi_index index.php; include fastcgi_params; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; fastcgi_param PATH_INFO $fastcgi_path_info; } # Quasar 前端路由 location / { proxy_pass http://quasar:9000; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; } location /storage { add_header "Access-Control-Allow-Origin" "*"; } }
此时只需访问http://localhost:8888即可打开Quasar应用,http://localhost:8888/api访问Laravel接口,无需单独访问9000端口。
4. 重启服务
执行以下命令使配置生效:
docker-compose down docker-compose up -d
内容的提问来源于stack exchange,提问作者Luciano

