我正在设置一个 Debian 服务器来为 Java Web 应用程序提供服务。几个星期以来,我已经做了大量研究。Tomcat 的网站说,如果您没有集群,最好使用独立的 Tomcat 来提高速度。但是,我看到很多人建议使用 Apache + Tomcat 可以为您提供更好的安全性和防御攻击的能力。
请假设该进程将以非特权用户身份在端口 80 上运行。我认为如果您在服务器前面运行防火墙,Tomcat 应该没问题。但是,如果您只想使用 Linux 防火墙运行暴露的 Web 服务器,最佳选择是什么?
或者也许有人可以推荐另一个开源 Web 服务器。我试图让解决方案尽可能轻量,因为这些 Web 应用程序将在容器中运行。
欢迎并重视所有意见。
答案1
从我的经验来看,在 Tomcat 前面放置一些东西来屏蔽外界的影响是明智之举。如果您使用 Tomcat-native 扩展运行 tomcat,IO 会非常快,Tomcat 的表现也会非常好。
另外,Tomcat 还可以通过使用 jsvc 在端口 80 上运行,而无需以 root 身份运行,如果您的发行版未提供 jsvc,则构建和使用起来非常简单。
但是,保留一个简单的 Web 前端以防万一也是有用的:因为这个前端可以为您提供使用 Tomcat 时永远无法获得的一点灵活性(动态 gzip、重写规则、使用简单的虚拟主机和代理映射在同一个 IP:端口上处理多个 tomcat,...)
Apache2 可以使用以下方式作为前端mod_proxy + AJP。AJP 处理标头和源 IP 转发到 Tomcat,当您必须在域上添加 RewriteRules 时,您会感到非常高兴,因为 Apache 以非常简单的方式提供了该功能。
但是,AJP 接收 webapp 状态更改的速度非常慢,并且当您的 webapp 重新启动时必须等待 30 秒才能再次在互联网上看到它,这非常令人沮丧。最新的 AJP + Tomcat 组合中也存在一些不太好的问题,导致页面空白和内容类型损坏(虽然可以修复,但要放弃 tomcat 原生增强功能……)。
简单HTTP 代理模式也可以使用,但由于它不是真正的代理(Apache 更改了主机:标头,源 IP 变成了代理地址,...),所以我不太喜欢。
其他不错的选择包括:
HAProxy:非常智能和简单的代理,非常擅长处理负载,配置非常简单,非常可靠,是一个真正的 HTTP 代理,可以通过常见的 X-Forwarded-For 标头转发源 IP。我在生产中使用它,对此非常满意。它可以扩展到数千个实时连接,同时限制到后端的活动连接数,并且内置了许多不错的功能。但是,它可能不适合制作比 HTTP 路由更聪明的东西(例如 RewriteRules)。
Nginx:我听说这个服务器确实支持 AJP。它比 Apache 更轻量,功能比 HAProxy 更全面,如果有机会,我今天可能会尝试一下。
结论
- 如果你有时间进行测试,请尝试 Nginx,
- 如果你喜欢简单而可靠的前端,可以选择 HAProxy,
- 如果你喜欢“传统”路线,可以选择 Apache2+AJP,
- 如果您认为 Tomcat 足够强大,并且能够提供您所需的所有功能,请使用 jsvc 并将 Tomcat 放在端口 80 上
答案2
我在 UNIX 上使用 Tomcat 和 Glassfish 时遇到的问题是(因为它们是 Java 应用程序,我想)它们无法绑定到端口 80,然后放弃 root 权限。以 root 身份运行这些类型的东西并不是最佳做法,因此剩下两个选择:
(1)以绑定到高端口(例如 8080)的普通用户身份运行应用程序服务器,并使用类似 iptables 规则将端口 80 流量重定向到端口 8080。我已经在 Linux 上使用一些 Glassfish 服务器完成此操作,效果非常好。
(2) 以普通用户身份在 Apache 后面运行应用服务器。Apache 可以绑定到端口 80,放弃特权,然后将请求代理到高端口上的应用服务器。
我更喜欢后者,但主要是因为我使用 Apache 已有很长时间,并且发现它的配置和管理很方便。因此,如果您非常了解 Apache,那么使用它,当您需要动态重写某些 URL 或调整过期标头时,您会很高兴您这样做了。另一方面,如果您没有 Apache 经验(或者在这种情况下,因为您需要尽可能轻量级),那么坚持使用 Tomcat 并使用 iptables 可能会更容易。
答案3
根据 @deutsch 的回答,Tomcat 不必在 UNIX 上以 root 身份运行。如果您从软件包(例如 Fedora / CentOS / Red Hat 的 tomcat6 RPM)安装它,它将以具有一组受限权限的用户 tomcat 身份运行。
话虽如此,我同意@Deutsch的最后一段;除非部署期限非常紧迫,否则请使用Apache作为Tomcat的前端。即使您还不太熟悉它,也可以很容易地在Tomcat前面使用mod_proxy进行基本部署,并且您几乎肯定会从增加的灵活性和安全性中受益。