【问题标题】:Sticky and NON-Sticky sessions粘性和非粘性会话
【发布时间】:2012-05-16 16:33:26
【问题描述】:

我想知道粘性会话和非粘性会话之间的区别。我从网上阅读后的理解:

粘性:只有一个会话对象会在那里。

非粘性会话:每个服务器节点的会话对象

【问题讨论】:

    标签: session sticky-session


    【解决方案1】:

    当您的网站仅由一个 Web 服务器提供服务时,对于每个客户端-服务器对,会创建一个会话对象并保留在 Web 服务器的内存中。来自客户端的所有请求都转到此 Web 服务器并更新此会话对象。如果在交互期间需要将一些数据存储在会话对象中,则将其存储在此会话对象中,并在会话存在时一直保留。

    但是,如果您的网站由位于负载均衡器后面的多个 Web 服务器提供服务,则负载均衡器会决定每个请求应该发送到哪个实际(物理)Web 服务器。例如,如果负载均衡器后面有 3 个 Web 服务器 A、B 和 C,则可能www.mywebsite.com 来自服务器 A,www.mywebsite.com 来自服务器 B,www.mywebsite.com/ 可能来自服务器 C .

    现在,如果请求是从(物理上)3 个不同的服务器提供的,每个服务器都会为您创建一个会话对象,并且因为这些会话对象位于三个独立的盒子上,所以没有直接的方法可以知道其中有什么另一个的会话对象。为了在这些服务器会话之间进行同步,您可能必须将会话数据写入/读取到所有人通用的层中 - 例如数据库。现在,为此用例向数据库写入数据和从数据库读取数据可能不是一个好主意。现在,sticky-session的角色来了。

    如果指示负载平衡器使用粘性会话,那么您的所有交互都将在同一物理服务器上进行,即使存在其他服务器也是如此。因此,在您与本网站的整个交互过程中,您的会话对象将是相同的。

    总而言之,在粘性会话的情况下,您的所有请求都将被定向到同一个物理 Web 服务器,而在非粘性负载均衡器的情况下,可以选择任何网络服务器来处理您的请求。

    例如,您可以在此处阅读有关 Amazon 的 Elastic Load Balancer 和粘性会话的信息:http://aws.typepad.com/aws/2010/04/new-elastic-load-balancing-feature-sticky-sessions.html

    【讨论】:

    • @TJ- 如果一个节点不可用会怎样?
    • 在大多数情况下,会话将丢失。在AWS ESB的情况下如果一个实例发生故障或变得不健康,负载均衡器将停止将请求路由到该实例,而是根据现有的负载均衡算法选择一个新的健康实例。负载均衡器将会话视为现在“卡”在新的健康实例上,并继续将请求路由到该实例,即使失败的实例返回。
    • LoadBalancer 根据哪些信息使 HTTP 会话保持粘性?特别是在 HTTPS 连接上,这个问题变得很有趣。您是否向 LB 提供了 Web 服务器的私钥,以便它能够断开 SSL 连接并获取 HTTP 会话?或者LB只是使用客户端IP地址?在这种情况下,多个客户端使用相同 IP 地址的代理服务器呢?或者更糟糕的是,IP 地址经常变化的移动客户端?或者有更好的技术吗?谢谢
    • 是的,你完全正确。为了在这种情况下使用“x-forwarded-for”标头或粘性cookie,需要使用SSL Termination,因此需要在LB 处解密请求。
    • @g000ze 在处理不直接提供给 Internet 的应用程序时,我相信只在最外层的代理服务器上启用 TLS 是很常见的。 (负载均衡器可能过于简单地被视为一种特殊类型的代理服务器,可以将请求传递到多个服务器中的任何一个。)负载均衡器和其他服务器之间的流量将发生在本地安全网络上,因此通常不需要对其进行加密,或者如果需要对其进行加密,则自签名证书就足够了(因为可以将代理配置为信任它)。
    【解决方案2】:

    我在这里做了一些更详细的回答: https://stackoverflow.com/a/11045462/592477

    或者你可以在那里阅读 ==>

    当您使用负载平衡时,这意味着您有多个 tomcat 实例,您需要分配负载。

    • 如果您使用没有粘性会话的会话复制:假设您只有一个用户在使用您的网络应用,而您有 3 个 tomcat 实例。该用户向您的应用发送多个请求,然后 负载均衡器会将其中一些请求发送到第一个 tomcat 实例,并将其他一些请求发送到第二个 实例,其他到第三个。
    • 如果您使用无复制的粘性会话: 假设您只有一个用户在使用您的网络应用程序,而您有 3 个 tomcat 实例。该用户向您的应用发送多个请求,然后 负载均衡器会将第一个用户请求发送到三个中的一个 tomcat 实例,以及由此发送的所有其他请求 会话期间的用户将被发送到同一个 tomcat 实例。 在这些请求期间,如果您关闭或重新启动此 Tomcat 实例(使用的tomcat实例)负载均衡器发送 对另一个仍然存在的 tomcat 实例的剩余请求 正在运行,但由于您不使用会话复制,因此实例 接收剩余请求的tomcat没有 用户会话然后对于这个tomcat,用户开始一个会话: 用户失去了他的会话并与网络应用程序断开连接,尽管 网络应用仍在运行。
    • 如果您使用带有会话复制的粘性会话: 假设您只有一个用户在使用您的网络应用,而您有 3 个 tomcat 实例。该用户向您的应用发送多个请求,然后 负载均衡器会将第一个用户请求发送到三个中的一个 tomcat 实例,以及由此发送的所有其他请求 会话期间的用户将被发送到同一个 tomcat 实例。 在这些请求期间,如果您关闭或重新启动此 Tomcat 实例(使用的tomcat实例)负载均衡器发送 对另一个仍然存在的 tomcat 实例的剩余请求 当您使用会话复制时,正在运行的实例 tomcat 接收剩余的请求有一个用户会话的副本然后 用户继续他的会话:用户继续浏览您的网络 app没有被断开,tomcat实例的关闭 不会影响用户导航。

    【讨论】:

    • 嗯.. 读到这里我想知道:有第四个选项是否有意义:非粘性会话复制?或者换一种说法:如果一个人将会话复制到不同的实例,那么拥有一个粘性会话有什么好处?我的意思是,如果您要跨实例复制会话,您也可以将请求转发到任何服务器,对吗?我错过了什么?
    • @dingalapadum 你是对的,理论上你可以在没有粘性会话的情况下进行会话复制。但在大型集群的情况下,这对网络性能不利。然后有一些使用带有粘性会话的会话复制的策略,例如在 tomcat (tomcat.apache.org/tomcat-9.0-doc/cluster-howto.html) 中的这种策略是放置一个粘性会话并且只有一个副本(这里的一个节点称为备份管理器,它保留所有节点会话复制)。
    • 那么sticky session可以让你只有一个session副本,在大型集群中最好。
    • 啊,我明白了 - 如果我理解正确,您的意思是在整个集群中复制所有会话会在内部淹没集群 - 我明白了问题所在。哦,现在仔细看看你的答案,我刚刚看到,这实际上是你描述的第一个案例......'duh me'..
    • @dingalapadum 欢迎您提出问题,它允许改进答案
    猜你喜欢
    • 2019-09-24
    • 2016-07-25
    • 1970-01-01
    • 2011-09-16
    • 1970-01-01
    • 2012-03-30
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多