我将使用非常具体的方式来解释问题,但我认为这比抽象问题更具体...
比如说,在kubernetes集群之外但在网络中有一个mongo db副本集。副本集的所有成员的IP地址由应用服务器和数据库服务器中的/ etc / hosts解析。
在实验/过渡阶段,我需要从kubernetes pod访问那些mongo db服务器。 但是,kubernetes似乎不允许在pods /容器中向/ etc / hosts添加自定义条目。
mongo db副本集已经在处理大型数据集,因此无法在群集中创建新的副本集。
Becaseu我使用GKE,我想应该避免更改kube-dns命名空间中的任何资源。配置或替换kube-dns以适合我的需要是最后一件事。
是否可以解析kubernetes集群中自定义主机名的IP地址?
这只是一个想法,但如果kube2sky可以读取一些configmap的条目并将它们用作dns记录,那么它就会很棒。
例如repl1.mongo.local: 192.168.10.100
。
答案 0 :(得分:10)
访问kubernetes之外的主机或ips需要一种外部名称。
以下对我有用。
{
"kind": "Service",
"apiVersion": "v1",
"metadata": {
"name": "tiny-server-5",
"namespace": "default"
},
"spec": {
"type": "ExternalName",
"externalName": "192.168.1.15",
"ports": [{ "port": 80 }]
}
}
答案 1 :(得分:4)
对于记录,是那些未检查引用的github issue的人的替代解决方案。
您可以定义"外部"通过不指定任何选择器或ClusterIP在Kubernetes中提供服务。您还必须定义指向外部IP的相应端点。
{ "kind": "Service", "apiVersion": "v1", "metadata": { "name": "my-service" }, "spec": { "ports": [ { "protocol": "TCP", "port": 80, "targetPort": 9376 } ] } } { "kind": "Endpoints", "apiVersion": "v1", "metadata": { "name": "my-service" }, "subsets": [ { "addresses": [ { "ip": "1.2.3.4" } ], "ports": [ { "port": 9376 } ] } ] }
有了这个,您可以将容器中的应用指向my-service:9376
,并将流量转发到1.2.3.4:9376
限制:
something.like.this
)。这意味着您可能需要将应用修改为仅指向your-service
,而不是yourservice.domain.tld
。ExternalName
类型服务定义一种DNS别名。答案 2 :(得分:3)
更新时间:2017-07-03 Kunbernetes 1.7现在支持caniuse.com。
解决方案不是关于kube-dns,而是关于/ etc / hosts。 无论如何,以下诀窍似乎到目前为止......
编辑:更改/ etc / hosts可能与kubernetes系统有竞争条件。让它重试。
1)创建一个configMap
apiVersion: v1
kind: ConfigMap
metadata:
name: db-hosts
data:
hosts: |
10.0.0.1 db1
10.0.0.2 db2
2)添加名为ensure_hosts.sh
的脚本。
#!/bin/sh
while true
do
grep db1 /etc/hosts > /dev/null || cat /mnt/hosts.append/hosts >> /etc/hosts
sleep 5
done
别忘了chmod a+x ensure_hosts.sh
。
3)添加包装脚本start.sh
您的图片
#!/bin/sh
$(dirname "$(realpath "$0")")/ensure_hosts.sh &
exec your-app args...
别忘了chmod a+x start.sh
4)将configmap用作卷并运行start.sh
apiVersion: extensions/v1beta1
kind: Deployment
...
spec:
template:
...
spec:
volumes:
- name: hosts-volume
configMap:
name: db-hosts
...
containers:
command:
- ./start.sh
...
volumeMounts:
- name: hosts-volume
mountPath: /mnt/hosts.append
...
答案 3 :(得分:1)
使用configMap似乎是更好的设置DNS的方法,但是在添加一些记录时(在我看来)它有点重。所以我通过docker /etc/hosts
执行的shell脚本将记录添加到CMD
。
例如:
Dockerfile
...(ignore)
COPY run.sh /tmp/run.sh
CMD bash /tmp/run.sh
run.sh
#!/bin/bash
echo repl1.mongo.local 192.168.10.100 >> /etc/hosts
# some else command...
请注意,如果您在一个容器中运行多于一个容器,则必须在每个容器中添加脚本,因为kubernetes随机启动容器,/etc/hosts
可能会被另一个容器覆盖(从以后开始。)
答案 4 :(得分:1)
现在可以使用/etc/hosts
将条目添加到Pod的.spec.hostAliases
例如:要将foo.local
,bar.local
解析为127.0.0.1
和foo.remote
,
bar.remote
至10.1.2.3
,您可以在以下位置为Pod配置HostAliases
.spec.hostAliases
:
apiVersion: v1
kind: Pod
metadata:
name: hostaliases-pod
spec:
restartPolicy: Never
hostAliases:
- ip: "127.0.0.1"
hostnames:
- "foo.local"
- "bar.local"
- ip: "10.1.2.3"
hostnames:
- "foo.remote"
- "bar.remote"
containers:
- name: cat-hosts
image: busybox
command:
- cat
args:
- "/etc/hosts"