在 Ruby on Rails 的上下文中引用时,啥是中间件?

Posted

技术标签:

【中文标题】在 Ruby on Rails 的上下文中引用时,啥是中间件?【英文标题】:What is middleware when referenced in the context of Ruby on Rails?在 Ruby on Rails 的上下文中引用时,什么是中间件? 【发布时间】:2011-03-14 02:59:17 【问题描述】:

我经常在 Ruby on Rails 的上下文中听到“中间件”这个词。它到底是什么?你能提供具体的例子吗?

【问题讨论】:

【参考方案1】:

中间件与 Rack 相关,Rack 是用于 Web 应用程序的标准 Ruby API。由于 Rails 应用程序现在是 Rack 应用程序,它们适用于两者。

机架中间件是应用服务器(Webrick、Thin、Unicorn、Passenger 等)和实际应用程序(例如 Rails 应用程序)之间的一切。它是 Web 应用程序服务器和应用程序本身之间的pipeline

Rack 应用程序的输入是一个“环境”,其中包含所有 HTTP 请求详细信息(以及更多信息)。输出是一个 HTTP 响应。 中间件层就像过滤器,可以修改输入、输出或两者。 Rails 使用中间件来implement some of its features(查询缓存、cookie 存储、http 方法扩展),但你可以添加自己的。

Rack 中间件是一种在使用 Rack 的 Web 应用程序中重用简单的 Web 相关行为的有效方法,而不管底层框架如何。如果您的应用程序的一部分添加了功能,但不负责 HTTP 响应,则它有资格作为 Rack 中间件。

您可以将其实现为Rack middleware 的一些示例包括:

HTTP 缓存(服务器端和客户端) 日志记录 身份验证 监控 HTTP 标头过滤

另见this SO question。

【讨论】:

【参考方案2】:

假设您想创建一个缓存服务。此缓存服务与应用程序无关,因此您可以将其与许多应用程序一起使用。您也想支持许多不同的 Web 服务器。

注意到它是如何位于服务器和框架之间的吗?这是一个中间件的例子。它不是应用程序逻辑,也不是真正的低级网络东西,而是提供介于两者之间的服务。一些示例包括 QoS(服务质量)、安全性、缓存......

如果您的服务支持所有流行的(以及一些不那么流行的)服务器(瘦、webrick),那就太好了。如果你支持他们,更多的人可以使用你的精彩软件。您可以看到实现这一点确实很麻烦,您需要使用特定于服务器的特殊代码来支持每个服务器。

现在这只是问题的一半,因为还有许多 Web 框架。 Rails 是 500 磅的大猩猩,但还有其他框架,例如 Merb 和 Sinatra。在您的缓存服务中支持这些是另一个需要支持的m 项。现在您支持 n x m 不同的路径。好麻烦。

输入Rack。 Rack 位于框架和服务器之间,并为您提供了一个接口来编码您的缓存服务器。如果服务器和框架支持机架,并且大多数都支持,那么您的服务只需要支持机架接口,您就可以获得对所有框架和服务机架支持的支持。 (有点像latex编译成dvi,然后把dvi转成ps、pdf、....)。您不需要从 Merb 到 WEBrick 的转换器以及从 Sinata 到 Thin 的转换器。如果您的缓存服务支持机架,您就可以避免这些差异。

有了这个“窄腰”,m-frameworks 在应用程序和服务器之间扩展到 n-servers 之前聚集在一起,您还可以看到它如何提供一个添加功能的好地方,例如路由、日志记录、静态服务这绕过了您的解释框架等的缓慢性。

【讨论】:

Rack 不完全是中间件,它是一个简单的接口,便于服务器和 Web 应用程序之间的通信。 Rack 允许使用中间件,但它本身不是一个。 解决了您的 cmets。谢谢。【参考方案3】:

给 4 岁孩子的解释:

你还记得你小时候玩过的游戏:"Chinese whispers"吗? (没有种族主义的意图——这实际上是我那个时代的游戏名称)。您想告诉坐在电话另一端的朋友一个特别的信息。但你不能直接告诉他或她:你必须在一个人之间传递你的信息,直到它最终到达他或她。

但更多情况下,您会发现消息在通过链时发生变化,直到到达终点。例如:

    发起人:“你会永远记住这一天,你差点抓到杰克斯派洛船长。” 第 1 个人 - 继续说:“您将永远记得差点抓到 Jack Sparrow 船长的那一天。” 第二个人 - 继续说:“你将永远记得你差点抓住杰克斯派洛船长的那一天。” 第三人称:“你会记得抓到杰克斯派洛船长的那一天。” Person 4 - 继续说:“你会记得 Jack Sparrow 船长。” 收到的最后一条消息:“记住”

中间件基本上是介于您之间的人、消息的发起者和最终收到的消息:注意他们如何更改或过滤消息?简而言之,这就是中间件的全部内容。当然,anology 是紧张的,但希望这将为您提供理解上述更多技术答案的基础。

【讨论】:

【参考方案4】:

Rails 中间件允许您在请求或响应到达 Rails 之前捕获并修改它。 (您位于 Rack 和 Rails 之间的中间)。例如,您可以获取每个返回“image/png”mime 类型的响应,并在将其移至 Rack 以供服务之前为其添加水印。或者,您可以过滤掉出于某种原因(未经授权,没有标头)不喜欢的请求,并且永远不要让它们触碰到障碍。或者,您可以在将传入请求传递到 Rails 之前为其添加标头。或者您可以从 rails 获取响应,如果它是“text/html”,您可以在传递到输出之前压缩 html(删除空格等)。 (我在http://github.com/maxim/html_press 中试验过)

这些小应用程序很多,并且作为“中间件”插入。

【讨论】:

【参考方案5】:

查看CodeRack 有助于了解其中的一些可能性。现在当你问你经常在 Ruby on Rails 的上下文中听到它时,你更普遍地问中间件是什么?

【讨论】:

以上是关于在 Ruby on Rails 的上下文中引用时,啥是中间件?的主要内容,如果未能解决你的问题,请参考以下文章

Ruby on Rails 中的 Runner

了解 Ruby on Rails 6 中的路由 + 模块/类名称 [以及在此上下文中模块是啥]

推送到Heroku时Ruby on Rails错误

Ruby on rails - 两次引用同一个模型?

Ruby on rails:仅从两列范围内获取数据

在 Ruby on Rails 中清除或实现表