文章配图-Photo by Clément H on Unsplash

今天在本地开发环境联调前后端时,发现前端 web 页面怎么也连不上后端接口,发送不了请求。

搜索了一圈,发现原因是浏览器禁止某些端口的访问,测试用的 6000 端口刚好属于其中之一。

环境说明

前端基于 ant 框架实现, npm start 后监听 localhost:8000

后端由 Flask 开发,debug 模式启动,监听 localhost:6000

前端页面请求后端时,直接发送请求到 http://localhost:6000 接口。

用火狐打开 http://localhost:8000,发现前端连不上后端,浏览器开发工具中的 Network 一直没有出现 localhost:6000 的请求。

尝试解决

初次实验

  1. 把前端配置中随机改个端口号,比如 6001,发现在 Network 中有了 localhost:6001 请求数据,说明换端口后可以正常创建连接

  2. 把后端启动地址改成 localhost:5000,前端代码中把请求端口改成 5000,发现这时可以正常发送接口也有数据。

通过以上两个测试,初步判断错误是由于 6000 端口造成的,换用其他端口就能访问。

可是到这也没有弄清楚究竟是什么原因导致 6000 端口不能访问。

浏览器提供新线索

之后把端口换回 6000,尝试换用 Chrome 访问页面,这时在控制台出现一条报错信息: net::ERR_UNSAFE_PORT

Chrome ERR_UNSAFE_PORT 报错

根据报错信息,找到这条回答,原来浏览器默认把一些端口认为是 「不安全端口」,因为这些端口号已经被其他服务使用,可能出现跨协议脚本攻击(Cross-Protocol Scripting)。

Chrome 禁止的端口列表,参考源码链接

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
1,       // tcpmux
7,       // echo
9,       // discard
11,      // systat
13,      // daytime
15,      // netstat
17,      // qotd
19,      // chargen
20,      // ftp data
21,      // ftp access
22,      // ssh
23,      // telnet
25,      // smtp
37,      // time
42,      // name
43,      // nicname
53,      // domain
77,      // priv-rjs
79,      // finger
87,      // ttylink
95,      // supdup
101,     // hostriame
102,     // iso-tsap
103,     // gppitnp
104,     // acr-nema
109,     // pop2
110,     // pop3
111,     // sunrpc
113,     // auth
115,     // sftp
117,     // uucp-path
119,     // nntp
123,     // NTP
135,     // loc-srv /epmap
139,     // netbios
143,     // imap2
179,     // BGP
389,     // ldap
427,     // SLP (Also used by Apple Filing Protocol)
465,     // smtp+ssl
512,     // print / exec
513,     // login
514,     // shell
515,     // printer
526,     // tempo
530,     // courier
531,     // chat
532,     // netnews
540,     // uucp
548,     // AFP (Apple Filing Protocol)
556,     // remotefs
563,     // nntp+ssl
587,     // stmp?
601,     // ??
636,     // ldap+ssl
993,     // ldap+ssl
995,     // pop3+ssl
2049,    // nfs
3659,    // apple-sasl / PasswordServer
4045,    // lockd
6000,    // X11
6665,    // Alternate IRC [Apple addition]
6666,    // Alternate IRC [Apple addition]
6667,    // Standard IRC [Apple addition]
6668,    // Alternate IRC [Apple addition]
6669,    // Alternate IRC [Apple addition]
6697,    // IRC + TLS

火狐中禁止使用的端口,详细信息参考链接

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
1 	tcpmux
7 	echo
9 	discard
11 	systat
13 	daytime
15 	netstat
17 	qotd
19 	chargen
20 	ftp data
21 	ftp control
22 	ssh
23 	telnet
25 	smtp
37 	time
42 	name
43 	nicname
53 	domain
77 	priv-rjs
79 	finger
87 	ttylink
95 	supdup
101 	hostriame
102 	iso-tsap
103 	gppitnp
104 	acr-nema
109 	POP2
110 	POP3
111 	sunrpc
113 	auth
115 	sftp
117 	uucp-path
119 	NNTP
123 	NTP
135 	loc-srv / epmap
139 	netbios
143 	IMAP2
179 	BGP
389 	LDAP
465 	SMTP+SSL
512 	print / exec
513 	login
514 	shell
515 	printer
526 	tempo
530 	courier
531 	chat
532 	netnews
540 	uucp
556 	remotefs
563 	NNTP+SSL
587 	submission
601 	syslog
636 	LDAP+SSL
993 	IMAP+SSL
995 	POP3+SSL
2049 	nfs
4045 	lockd
6000 	X11

解决方案

开发环境中把后端接口换为没有被禁止访问的接口就行。

生产环境中不会直接访问后端应用,通过 nginx 反代,一般用的也是 80、443 端口。

总结

很不走运,随便挑的 6000 端口在被禁止的端口之列,这才导致从浏览器没法连接后端。

刚开始用火狐时也一直没找到原因,后来换 Chrome 才发现有用的报错信息,前端出问题换一换不同的浏览器,往往有惊喜。

最后,开发测试环境选择端口的时候,还是选择大家约定俗成的端口比较好,比如 8000,8080,8888 等。