![Nginx 不斷拋出 nginx: [emerg] bind() to 0.0.0.0:80 failed (98: 地址已在使用中)](https://rvso.com/image/718755/Nginx%20%E4%B8%8D%E6%96%B7%E6%8B%8B%E5%87%BA%20nginx%3A%20%5Bemerg%5D%20bind()%20to%200.0.0.0%3A80%20failed%20(98%3A%20%E5%9C%B0%E5%9D%80%E5%B7%B2%E5%9C%A8%E4%BD%BF%E7%94%A8%E4%B8%AD).png)
我已經檢查了很多網站,以及 ServerFault 中關於此問題的許多問題/答案。但是,我似乎沒有深入了解配置錯誤的根源。
我的 nginx 伺服器中有 4 個網域:
example.com
www.example.com
api.example.com
blog.example.com
它們都已啟動並在連接埠nginx.conf
80和443 中運行server_name
。還有一些其他變化,但原則上不會產生影響。喜歡不同的。root
error_log
access_log
fastcgi_param
example.com
這是和的模板www.example.com
:
server {
listen 80;
server_name example.com www.example.com;
root /var/www/example.com/public_html/web;
if ($http_host = example.com) {
return 301 https://www.example.com$request_uri;
}
location / {
# try to serve file directly, fallback to front controller
try_files $uri /index.php$is_args$args;
}
location ~ ^/index\.php(/|$) {
fastcgi_pass unix:/var/run/php/php7.0-fpm.sock;
fastcgi_split_path_info ^(.+\.php)(/.*)$;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param HTTPS off;
fastcgi_param DATABASE_NAME some_database;
fastcgi_param DATABASE_USER some_user;
fastcgi_param DATABASE_PASSWORD some_pwd;
}
#return 404 for all php files as we do have a front controller
location ~ \.php$ {
return 404;
}
error_log /var/log/nginx/www.example.com_error.log;
access_log /var/log/nginx/www.example.com_access.log;
# Redirect non-https traffic to https
if ($scheme != "https") {
return 301 https://$host$request_uri;
} # managed by Certbot
listen 443 ssl; # managed by Certbot
ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem; # managed by Certbot
ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem; # managed by Certbot
include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot
}
這就是我重新啟動伺服器時收到的確切錯誤:
root@vps_server:/etc/nginx# journalctl -xe
Mar 09 09:17:16 vps_server systemd[1]: Starting A high performance web server and a reverse proxy server...
-- Subject: Unit nginx.service has begun start-up
-- Defined-By: systemd
-- Support: http://www.ubuntu.com/support
--
-- Unit nginx.service has begun starting up.
Mar 09 09:17:16 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)
Mar 09 09:17:16 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:443 failed (98: Address already in use)
Mar 09 09:17:16 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)
Mar 09 09:17:16 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:443 failed (98: Address already in use)
Mar 09 09:17:17 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)
Mar 09 09:17:17 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:443 failed (98: Address already in use)
Mar 09 09:17:17 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)
Mar 09 09:17:17 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:443 failed (98: Address already in use)
Mar 09 09:17:18 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)
Mar 09 09:17:18 vps_server nginx[30764]: nginx: [emerg] bind() to 0.0.0.0:443 failed (98: Address already in use)
Mar 09 09:17:18 vps_server nginx[30764]: nginx: [emerg] still could not bind()
Mar 09 09:17:18 vps_server systemd[1]: nginx.service: Control process exited, code=exited status=1
Mar 09 09:17:18 vps_server systemd[1]: Failed to start A high performance web server and a reverse proxy server.
-- Subject: Unit nginx.service has failed
-- Defined-By: systemd
-- Support: http://www.ubuntu.com/support
--
-- Unit nginx.service has failed.
--
-- The result is failed.
Mar 09 09:17:18 vps_server systemd[1]: nginx.service: Unit entered failed state.
Mar 09 09:17:18 vps_server systemd[1]: nginx.service: Failed with result 'exit-code'.
當我嘗試使用更新憑證時,sudo certbot renew --dry-run
我收到類似的錯誤,儘管不完全相同。
如果我殺死 nginx 線程,那麼我就可以重新啟動伺服器。但下次我嘗試重新啟動它時,它會拋出相同的錯誤。最糟糕的是我無法更新我的 SSL 憑證(儘管這可能是由於不同的原因,我不想在這裡列出,因為這可能是原因)。
編輯
我已經使用 Vagrant 設定了一台具有完全相同配置的本地計算機,只是我註釋了 SSL 憑證資料。我可以毫無問題地重新啟動伺服器。所以也許它確實與 Certbot/SSL 配置有關。
為了幫助調試此問題,以下是輸出netstat -tulpn
(僅 nginx 使用連接埠 80 和 443,這是我理解的預期輸出):
/var/log/nginx# netstat -tulpn
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp 0 0 127.0.0.1:3306 0.0.0.0:* LISTEN 16700/mysqld
tcp 0 0 0.0.0.0:5355 0.0.0.0:* LISTEN 1578/systemd-resolv
tcp 0 0 0.0.0.0:80 0.0.0.0:* LISTEN 30608/nginx: master
tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN 1675/sshd
tcp 0 0 0.0.0.0:25 0.0.0.0:* LISTEN 10001/master
tcp 0 0 0.0.0.0:443 0.0.0.0:* LISTEN 30608/nginx: master
tcp6 0 0 :::5355 :::* LISTEN 1578/systemd-resolv
tcp6 0 0 :::22 :::* LISTEN 1675/sshd
tcp6 0 0 :::25 :::* LISTEN 10001/master
udp 0 0 127.0.0.53:53 0.0.0.0:* 1578/systemd-resolv
udp 0 0 0.0.0.0:68 0.0.0.0:* 1343/dhclient
udp 0 0 0.0.0.0:5355 0.0.0.0:* 1578/systemd-resolv
udp6 0 0 :::5355 :::* 1578/systemd-resolv
答案1
你是什麼nginx.conf
樣子的?我假設您沒有更改配置,可能只是添加了 gzip 和一個新的包含資料夾,以便為網站提供單獨的位置。對於每個域/子域都有一個單獨的設定檔。喜歡:
example.com
&www.example.com
api.example.com
blog.example.com
這是因為我假設這些是同一網域下的單獨網站。如果它們位於同一個網站上並且它們只是所謂的子頁面,那麼您最好只建立帶有位置選項的子頁面。
為了重新組織您的nginx
配置,我將建立一個com.example.conf
包含 3 個獨立伺服器部分的檔案。首先是將非 www 使用者重新導向到 www 網站:
server {
listen 80;
server_name example.com;
return 301 https://www.example.com$request_uri;
}
server {
listen 443 ssl;
server_name example.com;
return 301 https://www.example.com$request_uri;
}
第三部分將包含主要站點:
server {
listen 443 ssl;
server_name example.com www.example.com;
root /var/www/example.com/public_html/web;
index index.php;
error_log /var/log/nginx/www.example.com_error.log;
access_log /var/log/nginx/www.example.com_access.log;
location / {
# try to serve file directly, fallback to front controller
try_files $uri /index.php$is_args$args;
}
location ~ ^/index\.php(/|$) {
fastcgi_pass unix:/var/run/php/php7.0-fpm.sock;
fastcgi_split_path_info ^(.+\.php)(/.*)$;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param HTTPS off;
fastcgi_param DATABASE_NAME some;
fastcgi_param DATABASE_USER some_user;
fastcgi_param DATABASE_PASSWORD some_pwd;
}
location ~ \.php$ {
return 404;
}
}
(我必須說,你的 index.php 位置中的 fastcgi 部分對我來說看起來很奇怪,但我會把它留給你)
然後創建單獨的設定檔作為com.example.api.conf
和com.example.blog.conf
。像以前一樣新增先前配置中的前兩個部分,然後您可以為每個子網域新增不同的位置配置。
例如,我的 Laravel 網站有這個:
rewrite ^/index\.php?(.*)$ /$1 permanent;
location / {
try_files $uri @rewrite;
}
location @rewrite {
rewrite ^(.*)$ /index.php/$1 last;
}
location ~ ^/index.php(/|$) {
fastcgi_pass 127.0.0.1:9000;
fastcgi_split_path_info ^(.+\.php)(/.*)$;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param HTTPS on;
fastcgi_buffers 16 16k;
fastcgi_buffer_size 32k;
fastcgi_read_timeout 299;
}
希望這對您有幫助,如果沒有,請評論您的問題。
答案2
將bind()修復為0.0.0.0:80或443失敗(98:地址已在使用中)
運行以下命令:
sudo pkill -f nginx & wait $!
sudo systemctl start nginx
答案3
我終於解決了這個問題。伺服器似乎啟用了 IPV6,並且要求 nginx 配置略有不同。
而不是使用這個:
listen 80;
listen 443 ssl;
我必須使用以下內容:
listen [::]:80;
listen [::]:443 ssl;
在這個網站上我得到了更準確、更詳細的解釋:https://chrisjean.com/fix-nginx-emerg-bind-to-80-failed-98-address-already-in-use/
奇怪的是我的錯誤是:
nginx: [emerg] bind() to 0.0.0.0:443 failed (98: Address already in use)
而不是所描述的(在我提供的 URL 中):
nginx: [emerg] bind() to [::]:80 failed (98: Address already in use)
不過,這解決了問題,我能夠毫無問題地重新啟動 nginx 伺服器。
我設定的 vagrant 伺服器沒有啟用 IPV6,因此這可能與它的行為方式不同有關。