openstack集群访问外部服务出现访问失败
场景描述:
openstack私有云中的容器服务A(部署在openshift上)需要通过http访问阿里云中的B服务,中间需要经过openstack的nat网关,以及阿里云的lb。但在访问时发现访问失败,A服务无法获取B服务的http响应。

问题分析:
容器中的服务A请求阿里云的服务B时失败,但在容器所在的node节点直接curl该url是成功的,说明底层网络连接是通的。在A服务和B服务所在的node节点抓包发现,A服务发送http请求时,tcp链路是通的,但由于没有接收到B服务的http response,A服务判断业务超时,发送tcp断链

但在B服务端可以看到,它其实已经正确回复了A服务的http request。因此猜测报文可能被A服务的node或网关丢弃了。

为排除问题,将A服务部署在非openstack环境中,环境部署如下,发现A服务可以正常访问B服务,可以排除阿里云的问题。

回到出问题的环境,出现网络丢包的原因一般出现在如下场景:
- 防火墙,包括一些权限策略类的设置,如selinux,apparmor,iptables等
- 网络传输或接收设备繁忙,可能如cpu过载,内存不足,缓存队列满等
- 网络参数配置,如tcp超时参数设置,最大连接数,接口mtu等
本环境中网络负载很小,且数据是可以在两端传输的,可以排除1,2两点。由于使用curl可以正常访问服务B,可以判断A服务所在的node节点上的某些配置可能会导致丢包。仔细观察A服务主动发出的报文和使用curl发出的报文,可以发现两者在MSS上有所不同,A服务发出的MSS为1460,而使用curl则是1260

使用如下目录将A服务所在的node节点从eth0发送的TCP的MSS设置为1260,此时发现A服务可以正常访问B服务
iptables -t nat -I POSTROUTING -o eth0 -p tcp -m tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu
iptables -t nat -I POSTROUTING -o eth0 -p tcp -m tcp --tcp-flags SYN,RST SYN -j TCPMSS --set-mss
由此得出,该问题是因为A服务发出的MTU不正确导致的。使用ip link命令查看A服务所在节点的eth0的MTU,值为1300。而A服务所在容器的eth0为1500,这样就导致了A服务发出的tcp报文的MSS大于它所在节点的MSS,B服务(MSS为1460)发送的报文大于A服务所在集群可接收大小之后会被网关或node节点丢弃
修复方法:
在docker daemon中添加如下参数,重启docker(必要时重启node)即可将容器的mss修改为1260
# cat /etc/docker/daemon.json
{
"mtu":
}
PS:
- openshift容器会自适应host的mtu,参见Optimizing the MTU for Your Network。一般情况下,SDN会占用50字节,因此openshift中的MTU=HostMtu-50
openstack集群访问外部服务出现访问失败的更多相关文章
- S1_搭建分布式OpenStack集群_07 nova服务配置 (计算节点)
一.服务安装(计算节点)安装软件:# yum install openstack-nova-compute -y 编辑/etc/nova/nova.conf文件并设置如下内容:# vim /etc/n ...
- S1_搭建分布式OpenStack集群_08 网络服务(neutron)安装部署
一.数据库配置(控制节点)创建数据库以及用户:# mysql -uroot -p12345678MariaDB [(none)]> CREATE DATABASE neutron;MariaDB ...
- S1_搭建分布式OpenStack集群_06 nova服务配置 (控制节点)
一.创建数据库(控制节点)创建数据库以及用户:# mysql -uroot -p12345678MariaDB [(none)]> CREATE DATABASE nova_api;MariaD ...
- istio: 无法提供内部访问外部服务
现象 能够内部无法访问外部服务. 在部署测试服务 kubectl apply -f samples/sleep/sleep.yaml 设置环境变量 export SOURCE_POD=$(kubect ...
- 集群重启后启动ambari-server访问Web页面无法启动集群解决
集群重启后启动ambari-server访问Web页面无法启动集群解决 使用ambari部署的集群重新启动后,必须手动重启ambari-server和所有集群主机上的ambari-agent. amb ...
- 【精】搭建redis cluster集群,JedisCluster带密码访问【解决当中各种坑】!
转: [精]搭建redis cluster集群,JedisCluster带密码访问[解决当中各种坑]! 2017年05月09日 00:13:18 冉椿林博客 阅读数:18208 版权声明:本文为博主 ...
- 模拟安装redis5.0集群并通过Java代码访问redis集群
在虚拟机上模拟redis5.0的集群,由于redis的投票机制,一个集群至少需要3个redis节点,如果每个节点设置一主一备,一共需要六台虚拟机来搭建集群,此处,在一台虚拟机上使用6个redis实例来 ...
- openstack高可用集群21-生产环境高可用openstack集群部署记录
第一篇 集群概述 keepalived + haproxy +Rabbitmq集群+MariaDB Galera高可用集群 部署openstack时使用单个控制节点是非常危险的,这样就意味着单个节 ...
- 理解 OpenStack + Ceph (1):Ceph + OpenStack 集群部署和配置
本系列文章会深入研究 Ceph 以及 Ceph 和 OpenStack 的集成: (1)安装和部署 (2)Ceph RBD 接口和工具 (3)Ceph 物理和逻辑结构 (4)Ceph 的基础数据结构 ...
随机推荐
- Xamarin.Forms一些常见问题
安装 1.查看Xaramin.Forms的版本 在vs项目中查看引用的包(Xamarin.Forms)的版本,或者直接进文件夹看 C:\Microsoft\Xamarin\NuGet\xamarin. ...
- 8.学习springmvc的拦截器
一.springmvc拦截器介绍和环境搭建 1.介绍: 过滤器:servlet中的一部分,可以拦截所有想要访问的资源. 拦截器:SpringMVC框架中的,只能在SpringMVC中使用并且只能过滤控 ...
- 7.学习springmvc的异常处理
一.页面的异常处理流程 二.建立项目springmvc04_exception 1.编写index.jsp页面: <%@ page contentType="text/html;cha ...
- P4141 消失之物
目录 链接 思路 代码 链接 P4141 消失之物 思路 f[N];//表示删掉物品后能出现容积为i的方案数 a[N];//单纯0-1背包的方案数asd 那么就先求出a[i]来,然后转移就是 if(j ...
- ImportError: No module named 'typing'
k@ubuntu:~/Desktop/virtualenv$ python3 Python ( , ::) [GCC ] on linux Type "help", "c ...
- [POI2008]PER-Permutation
[POI2008]PER-Permutation 带重复的康托展开! 根本不需要中国剩余定理就可以A掉! 看完题面你会惊人地发现这好像一个康托展开!(显然是不同的啦) 首先我们来看康托展开这个东西在数 ...
- GIT-本地仓库
用户配置 git config --global user.name "name" git config --global user.email "123@qq.com& ...
- 大龄IT程序员的救赎之道
不知道从什么时候开始,中年危机持续刷屏,遍布整个职场,横跨各个行业,对各个细分工种的中年男女或者即将步入中年的青年男女几乎形成了垂直打击,而且中年这个年龄分界线从40岁滑落到35岁,甚至到30岁.笔者 ...
- redis渐进式rehash机制
在Redis中,键值对(Key-Value Pair)存储方式是由字典(Dict)保存的,而字典底层是通过哈希表来实现的.通过哈希表中的节点保存字典中的键值对.我们知道当HashMap中由于Hash冲 ...
- js中for..of..的使用和迭代器
for..of是ES6中引入的新特性,它主要的作用是:循环一个可迭代的对象. 它可以循环遍历,数组.字符串.Set对象等等,先来看两个简单的例子: 遍历字符串 let str = 'Hello' fo ...