如何执行一个已经运行Docker容器内的脚本?

采菊篱下 回复了问题 • 3 人关注 • 4 个回复 • 475 次浏览 • 2017-03-09 20:17 • 来自相关话题

OVM-V1.5 版正式发布,新增对ESXI节点的支持

maoliang 发表了文章 • 0 个评论 • 515 次浏览 • 2017-02-21 17:13 • 来自相关话题

OVM-V1.5版本正式发布,此版本新增对Esxi节点的支持,目前OVM混合虚拟化平台已经能够统一管理KVM、ESXI、Docker三种类型的底层虚拟化技术。同时也提升了OVM的易用性,管理平台和计算节点 iso镜像合并到一个镜像里,安装方面同时新增u盘安装,提高工作效率。


OVM是国内首款、完全免费、企业级——混合虚拟化管理平台,是从中小企业目前的困境得到启发,完全基于国内企业特点开发,更多的关注国内中小企业用户的产品需求。


OVM-V1.5虚拟化管理平台功能变动清单:

 

Ø  新增对VMwareEsxi节点的支持


Ø  合并管理平台和计算节点镜像为一个iso


Ø  支持通过USB安装OVM


Ø  修复其他若干bug

 

详细信息


1、新增对VMwareEsxi节点的支持

 

OVM-V 1.5版本新增对Esxi节点的支持,支持将现有的VMwareEsxi计算节点直接添加到OVM虚拟化管理平台进行管理,并支持将原有Esxi虚拟机导入到平台进行统一管理。目前OVM混合虚拟化平台已经能够统一管理KVM、ESXI、Docker三种类型的底层虚拟化技术。

 

2.   管理平台和计算节点 iso镜像合并


OVM-V 1.5版本将管理平台和计算节点原来的两个iso镜像合并到一个iso镜像里面,在安装过程中提供选项来安装不同的服务,此次的合并不仅方便了大家的下载,也提升了OVM的易用性。



3.   支持通过USB方式安装,提高工作效率

OVM1.5版本镜像支持通过USB方式进行安装,极大提高了一线运维人员的工作效率。

 

获得帮助

下载请访问OVM社区官网:51ovm.com

使用过程中遇到什么问题及获得下载密码,加入OVM社区qq官方交流群:22265939

  查看全部
OVM-V1.5版本正式发布,此版本新增对Esxi节点的支持,目前OVM混合虚拟化平台已经能够统一管理KVM、ESXI、Docker三种类型的底层虚拟化技术。同时也提升了OVM的易用性,管理平台和计算节点 iso镜像合并到一个镜像里,安装方面同时新增u盘安装,提高工作效率。


OVM是国内首款、完全免费、企业级——混合虚拟化管理平台,是从中小企业目前的困境得到启发,完全基于国内企业特点开发,更多的关注国内中小企业用户的产品需求。


OVM-V1.5虚拟化管理平台功能变动清单:

 

Ø  新增对VMwareEsxi节点的支持


Ø  合并管理平台和计算节点镜像为一个iso


Ø  支持通过USB安装OVM


Ø  修复其他若干bug

 

详细信息


1、新增对VMwareEsxi节点的支持

 

OVM-V 1.5版本新增对Esxi节点的支持,支持将现有的VMwareEsxi计算节点直接添加到OVM虚拟化管理平台进行管理,并支持将原有Esxi虚拟机导入到平台进行统一管理。目前OVM混合虚拟化平台已经能够统一管理KVM、ESXI、Docker三种类型的底层虚拟化技术。

 

2.   管理平台和计算节点 iso镜像合并


OVM-V 1.5版本将管理平台和计算节点原来的两个iso镜像合并到一个iso镜像里面,在安装过程中提供选项来安装不同的服务,此次的合并不仅方便了大家的下载,也提升了OVM的易用性。



3.   支持通过USB方式安装,提高工作效率

OVM1.5版本镜像支持通过USB方式进行安装,极大提高了一线运维人员的工作效率。

 

获得帮助

下载请访问OVM社区官网:51ovm.com

使用过程中遇到什么问题及获得下载密码,加入OVM社区qq官方交流群:22265939

 

Java程序处理中文乱码

回复

chris 发起了问题 • 1 人关注 • 0 个回复 • 446 次浏览 • 2017-02-16 23:40 • 来自相关话题

Docker挂载主机目录出现Permission denied状况分析

采菊篱下 发表了文章 • 0 个评论 • 799 次浏览 • 2017-02-16 23:10 • 来自相关话题

今天用脚本部署一个Docker私有化环境,挂载宿主机目录出现Permission denied的情况,导致服务启动失败,具体情况如下:








问题原因及解决办法:
原因是CentOS7中的安全模块selinux把权限禁掉了,至少有以下三种方式解决挂载的目录没有权限的问题:
1、在运行容器的时候,给容器加特权,及加上 --privileged=true 参数docker run -i -t -v /data/mysql/data:/data/var-3306 --privileged=true b0387b8279d4 /bin/bash -c "/opt/start_db.sh"2、临时关闭selinuxsetenforce 03、添加selinux规则,改变要挂载的目录的安全性文本:# 更改安全性文本的格式如下
chcon [-R] [-t type] [-u user] [-r role] 文件或者目录

选顷不参数:
-R :连同该目录下癿次目录也同时修改;
-t :后面接安全性本文的类型字段!例如 httpd_sys_content_t ;
-u :后面接身份识别,例如 system_u;
-r :后面街觇色,例如 system_r

[root@localhost Desktop]# chcon --help
Usage: chcon [OPTION]... CONTEXT FILE...
or: chcon [OPTION]... [-u USER] [-r ROLE] [-l RANGE] [-t TYPE] FILE...
or: chcon [OPTION]... --reference=RFILE FILE...
Change the SELinux security context of each FILE to CONTEXT.
With --reference, change the security context of each FILE to that of RFILE.

Mandatory arguments to long options are mandatory for short options too.
--dereference affect the referent of each symbolic link (this is
the default), rather than the symbolic link itself
-h, --no-dereference affect symbolic links instead of any referenced file
-u, --user=USER set user USER in the target security context
-r, --role=ROLE set role ROLE in the target security context
-t, --type=TYPE set type TYPE in the target security context
-l, --range=RANGE set range RANGE in the target security context
--no-preserve-root do not treat '/' specially (the default)
--preserve-root fail to operate recursively on '/'
--reference=RFILE use RFILE's security context rather than specifying
a CONTEXT value
-R, --recursive operate on files and directories recursively
-v, --verbose output a diagnostic for every file processed

The following options modify how a hierarchy is traversed when the -R
option is also specified. If more than one is specified, only the final
one takes effect.

-H if a command line argument is a symbolic link
to a directory, traverse it
-L traverse every symbolic link to a directory
encountered
-P do not traverse any symbolic links (default)

--help display this help and exit
--version output version information and exit

GNU coreutils online help: <http://www.gnu.org/software/coreutils/>
For complete documentation, run: info coreutils 'chcon invocation'在主机中修改/data/mysql/data目录的安全性文档[root@localhost Desktop]# chcon -Rt svirt_sandbox_file_t /data/mysql/data在docker中就可以正常访问该目录下的相关资源了。
卷权限参考:https://yq.aliyun.com/articles/53990  查看全部
Docker.jpeg

今天用脚本部署一个Docker私有化环境,挂载宿主机目录出现Permission denied的情况,导致服务启动失败,具体情况如下:
errorqx.png

cerror.png

问题原因及解决办法:
原因是CentOS7中的安全模块selinux把权限禁掉了,至少有以下三种方式解决挂载的目录没有权限的问题:
1、在运行容器的时候,给容器加特权,及加上 --privileged=true 参数
docker run -i -t -v /data/mysql/data:/data/var-3306 --privileged=true b0387b8279d4 /bin/bash -c "/opt/start_db.sh"
2、临时关闭selinux
setenforce 0
3、添加selinux规则,改变要挂载的目录的安全性文本:
# 更改安全性文本的格式如下
chcon [-R] [-t type] [-u user] [-r role] 文件或者目录

选顷不参数:
-R :连同该目录下癿次目录也同时修改;
-t :后面接安全性本文的类型字段!例如 httpd_sys_content_t ;
-u :后面接身份识别,例如 system_u;
-r :后面街觇色,例如 system_r

[root@localhost Desktop]# chcon --help
Usage: chcon [OPTION]... CONTEXT FILE...
or: chcon [OPTION]... [-u USER] [-r ROLE] [-l RANGE] [-t TYPE] FILE...
or: chcon [OPTION]... --reference=RFILE FILE...
Change the SELinux security context of each FILE to CONTEXT.
With --reference, change the security context of each FILE to that of RFILE.

Mandatory arguments to long options are mandatory for short options too.
--dereference affect the referent of each symbolic link (this is
the default), rather than the symbolic link itself
-h, --no-dereference affect symbolic links instead of any referenced file
-u, --user=USER set user USER in the target security context
-r, --role=ROLE set role ROLE in the target security context
-t, --type=TYPE set type TYPE in the target security context
-l, --range=RANGE set range RANGE in the target security context
--no-preserve-root do not treat '/' specially (the default)
--preserve-root fail to operate recursively on '/'
--reference=RFILE use RFILE's security context rather than specifying
a CONTEXT value
-R, --recursive operate on files and directories recursively
-v, --verbose output a diagnostic for every file processed

The following options modify how a hierarchy is traversed when the -R
option is also specified. If more than one is specified, only the final
one takes effect.

-H if a command line argument is a symbolic link
to a directory, traverse it
-L traverse every symbolic link to a directory
encountered
-P do not traverse any symbolic links (default)

--help display this help and exit
--version output version information and exit

GNU coreutils online help: <http://www.gnu.org/software/coreutils/>
For complete documentation, run: info coreutils 'chcon invocation'
在主机中修改/data/mysql/data目录的安全性文档
[root@localhost Desktop]# chcon -Rt svirt_sandbox_file_t /data/mysql/data
在docker中就可以正常访问该目录下的相关资源了。
卷权限参考:https://yq.aliyun.com/articles/53990 

Kafka Consumer客户端启动报错

采菊篱下 回复了问题 • 2 人关注 • 1 个回复 • 501 次浏览 • 2017-02-11 18:50 • 来自相关话题

使用Kubeadm安装Kubernetes1.5版本

Not see︶ 发表了文章 • 2 个评论 • 2566 次浏览 • 2017-01-11 18:52 • 来自相关话题

1、下载说需要的包都得在墙外,需要翻墙。 但服务器上总不能提供这种便利。 比较麻烦。 两种办法,一种是绑定hosts  由于Kubernetes 编译的各种发行版安装包来源于 Github 上的另一个叫 release 的项目,把这个项目 clone 下来,  

可以参考漠然的文章: https://mritd.me/2016/10/29/set-up-kubernetes-cluster-by-kubeadm/
 
2、我是用的方法 是通过hosts绑定, 然后通过打包到源码,下次直接使用
使用Kubeadm安装Kubernetes1.5版本

1、系统版本:ubuntu16.04

root@master:~# docker version

Client:

Version: 1.12.1

API version: 1.24

Go version: go1.6.2

Git commit: 23cf638

Built: Tue, 27 Sep 2016 12:25:38 +1300

OS/Arch: linux/amd64



Server:

Version: 1.12.1

API version: 1.24

Go version: go1.6.2

Git commit: 23cf638

Built: Tue, 27 Sep 2016 12:25:38 +1300

OS/Arch: linux/amd64





1、部署前提条件

每台主机上面至少1G内存。

所有主机之间网络可达。



2、部署:

在主机上安装kubelet和kubeadm

curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | apt-key add -

主机master上操作如下:

cat <<EOF >/etc/apt/sources.list.d/kubernetes.list

deb http://apt.kubernetes.io/ kubernetes-xenial main

EOF

apt-get update

apt-get install -y docker.io

apt-get install -y kubelet kubeadm kubectl kubernetes-cni

下载后的kube组件并未自动运行起来。在 /lib/systemd/system下面我们能看到kubelet.service

root@master:~# ls /lib/systemd/system |grep kube

kubelet.service

kubelet的版本:

root@master:~# kubelet --version

Kubernetes v1.5.1

k8s的核心组件都有了,接下来我们就要boostrap kubernetes cluster了。

3、初始化集群

理论上通过kubeadm使用init和join命令即可建立一个集群,这init就是在master节点对集群进行初始化。和k8s 1.4之前的部署方式不同的是,

kubeadm安装的k8s核心组件都是以容器的形式运行于master node上的。因此在kubeadm init之前,最好给master node上的docker engine挂上加速器代理,

因为kubeadm要从gcr.io/google_containers repository中pull许多核心组件的images


在Kubeadm的文档中,Pod Network的安装是作为一个单独的步骤的。kubeadm init并没有为你选择一个默认的Pod network进行安装。

我们将首选Flannel 作为我们的Pod network,这不仅是因为我们的上一个集群用的就是flannel,而且表现稳定。

更是由于Flannel就是coreos为k8s打造的专属overlay network add-ons。甚至于flannel repository的readme.md都这样写着:“flannel is a network fabric for containers, designed for Kubernetes”。

如果我们要使用Flannel,那么在执行init时,按照kubeadm文档要求,我们必须给init命令带上option:–pod-network-cidr=10.244.0.0/16。


4、执行kubeadm init

执行kubeadm init命令:

root@master:~# kubeadm init --pod-network-cidr=10.244.0.0/16

[kubeadm] WARNING: kubeadm is in alpha, please do not use it for production clusters.

[preflight] Running pre-flight checks

[preflight] Starting the kubelet service

[init] Using Kubernetes version: v1.5.1

[tokens] Generated token: "2909ca.c0b0772a8817f9e3"

[certificates] Generated Certificate Authority key and certificate.

[certificates] Generated API Server key and certificate

[certificates] Generated Service Account signing keys

[certificates] Created keys and certificates in "/etc/kubernetes/pki"

[kubeconfig] Wrote KubeConfig file to disk: "/etc/kubernetes/kubelet.conf"

[kubeconfig] Wrote KubeConfig file to disk: "/etc/kubernetes/admin.conf"

[apiclient] Created API client, waiting for the control plane to become ready

[apiclient] All control plane components are healthy after 14.761716 seconds

[apiclient] Waiting for at least one node to register and become ready

[apiclient] First node is ready after 1.003312 seconds

[apiclient] Creating a test deployment

[apiclient] Test deployment succeeded

[token-discovery] Created the kube-discovery deployment, waiting for it to become ready

[token-discovery] kube-discovery is ready after 1.002402 seconds

[addons] Created essential addon: kube-proxy

[addons] Created essential addon: kube-dns



Your Kubernetes master has initialized successfully!



You should now deploy a pod network to the cluster.

Run "kubectl apply -f [podnetwork].yaml" with one of the options listed at:

http://kubernetes.io/docs/admin/addons/



You can now join any number of machines by running the following on each node:



kubeadm join --token=2909ca.c0b0772a8817f9e3 xxx.xxx.xxx.xxx (ip记下)



init成功后的master node有啥变化?k8s的核心组件均正常启动:

root@master:~# ps -ef |grep kube

root 23817 1 2 14:07 ? 00:00:35 /usr/bin/kubelet --kubeconfig=/etc/kubernetes/kubelet.conf --require-kubeconfig=true --pod-manifest-path=/etc/kubernetes/manifests --allow-privileged=true --network-plugin=cni --cni-conf-dir=/etc/cni/net.d --cni-bin-dir=/opt/cni/bin --cluster-dns=10.96.0.10 --cluster-domain=cluster.local

root 23921 23900 0 14:07 ? 00:00:01 kube-scheduler --address=127.0.0.1 --leader-elect --master=127.0.0.1:8080

root 24055 24036 0 14:07 ? 00:00:10 kube-apiserver --insecure-bind-address=127.0.0.1 --admission-control=NamespaceLifecycle,LimitRanger,ServiceAccount,PersistentVolumeLabel,DefaultStorageClass,ResourceQuota --service-cluster-ip-range=10.96.0.0/12 --service-account-key-file=/etc/kubernetes/pki/apiserver-key.pem --client-ca-file=/etc/kubernetes/pki/ca.pem --tls-cert-file=/etc/kubernetes/pki/apiserver.pem --tls-private-key-file=/etc/kubernetes/pki/apiserver-key.pem --token-auth-file=/etc/kubernetes/pki/tokens.csv --secure-port=6443 --allow-privileged --advertise-address=master的ip --kubelet-preferred-address-types=InternalIP,ExternalIP,Hostname --anonymous-auth=false --etcd-servers=http://127.0.0.1:2379

root 24084 24070 0 14:07 ? 00:00:11 kube-controller-manager --address=127.0.0.1 --leader-elect --master=127.0.0.1:8080 --cluster-name=kubernetes --root-ca-file=/etc/kubernetes/pki/ca.pem --service-account-private-key-file=/etc/kubernetes/pki/apiserver-key.pem --cluster-signing-cert-file=/etc/kubernetes/pki/ca.pem --cluster-signing-key-file=/etc/kubernetes/pki/ca-key.pem --insecure-experimental-approve-all-kubelet-csrs-for-group=system:kubelet-bootstrap --allocate-node-cidrs=true --cluster-cidr=10.244.0.0/16

root 24242 24227 0 14:07 ? 00:00:00 /usr/local/bin/kube-discovery

root 24308 24293 1 14:07 ? 00:00:15 kube-proxy --kubeconfig=/run/kubeconfig

root 29457 29441 0 14:09 ? 00:00:00 /opt/bin/flanneld --ip-masq --kube-subnet-mgr

root 29498 29481 0 14:09 ? 00:00:00 /bin/sh -c set -e -x; cp -f /etc/kube-flannel/cni-conf.json /etc/cni/net.d/10-flannel.conf; while true; do sleep 3600; done

root 30372 30357 0 14:10 ? 00:00:01 /exechealthz --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1 >/dev/null --url=/healthz-dnsmasq --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1:10053 >/dev/null --url=/healthz-kubedns --port=8080 --quiet

root 30682 30667 0 14:10 ? 00:00:01 /kube-dns --domain=cluster.local --dns-port=10053 --config-map=kube-dns --v=2

root 48755 1796 0 14:31 pts/0 00:00:00 grep --color=auto kube



而且以多cotainer的形式启动

root@master:~# docker ps

CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES

c4209b1077d2 gcr.io/google_containers/kubedns-amd64:1.9 "/kube-dns --domain=c" 22 minutes ago Up 22 minutes k8s_kube-dns.61e5a20f_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_fc02f762

0908d6398b0b gcr.io/google_containers/exechealthz-amd64:1.2 "/exechealthz '--cmd=" 22 minutes ago Up 22 minutes k8s_healthz.9d343f54_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_0ee806f6

0e35e96ca4ac gcr.io/google_containers/dnsmasq-metrics-amd64:1.0 "/dnsmasq-metrics --v" 22 minutes ago Up 22 minutes k8s_dnsmasq-metrics.2bb05ef7_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_436b9370

3921b4e59aca gcr.io/google_containers/kube-dnsmasq-amd64:1.4 "/usr/sbin/dnsmasq --" 22 minutes ago Up 22 minutes k8s_dnsmasq.f7e18a01_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_06c5efa7

18513413ba60 gcr.io/google_containers/pause-amd64:3.0 "/pause" 22 minutes ago Up 22 minutes k8s_POD.d8dbe16c_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_9de0a18d

45132c8d6d3d quay.io/coreos/flannel-git:v0.6.1-28-g5dde68d-amd64 "/bin/sh -c 'set -e -" 23 minutes ago Up 23 minutes k8s_install-cni.fc218cef_kube-flannel-ds-0fnxc_kube-system_22034e49-d632-11e6-9d86-0050569c3e9b_88dffd75

4c2a2e46c808 quay.io/coreos/flannel-git:v0.6.1-28-g5dde68d-amd64 "/opt/bin/flanneld --" 23 minutes ago Up 23 minutes k8s_kube-flannel.5fdd90ba_kube-flannel-ds-0fnxc_kube-system_22034e49-d632-11e6-9d86-0050569c3e9b_2706c3cb

ad08c8dd177c gcr.io/google_containers/pause-amd64:3.0 "/pause" 23 minutes ago Up 23 minutes k8s_POD.d8dbe16c_kube-flannel-ds-0fnxc_kube-system_22034e49-d632-11e6-9d86-0050569c3e9b_279d8436

847f00759977 gcr.io/google_containers/kube-proxy-amd64:v1.5.1 "kube-proxy --kubecon" 24 minutes ago Up 24 minutes k8s_kube-proxy.2f62b4e5_kube-proxy-9c0bf_kube-system_f5326252-d631-11e6-9d86-0050569c3e9b_c1f31904

f8da0f38f3e1 gcr.io/google_containers/pause-amd64:3.0 "/pause" 24 minutes ago Up 24 minutes k8s_POD.d8dbe16c_kube-proxy-9c0bf_kube-system_f5326252-d631-11e6-9d86-0050569c3e9b_c340d947

c1efa29640d1 gcr.io/google_containers/kube-discovery-amd64:1.0 "/usr/local/bin/kube-" 24 minutes ago Up 24 minutes k8s_kube-discovery.6907cb07_kube-discovery-1769846148-4rsq9_kube-system_f49933be-d631-11e6-9d86-0050569c3e9b_c4827da2

4c6a646d0b2e gcr.io/google_containers/pause-amd64:3.0 "/pause" 24 minutes ago Up 24 minutes k8s_POD.d8dbe16c_kube-discovery-1769846148-4rsq9_kube-system_f49933be-d631-11e6-9d86-0050569c3e9b_8823b66a

ece79181f177 gcr.io/google_containers/pause-amd64:3.0 "/pause" 24 minutes ago Up 24 minutes k8s_dummy.702d1bd5_dummy-2088944543-r2mw3_kube-system_f38f3ede-d631-11e6-9d86-0050569c3e9b_ade728ba

9c3364c623df gcr.io/google_containers/pause-amd64:3.0 "/pause" 24 minutes ago Up 24 minutes k8s_POD.d8dbe16c_dummy-2088944543-r2mw3_kube-system_f38f3ede-d631-11e6-9d86-0050569c3e9b_838c58b5

a64a3363a82b gcr.io/google_containers/kube-controller-manager-amd64:v1.5.1 "kube-controller-mana" 25 minutes ago Up 25 minutes k8s_kube-controller-manager.84edb2e5_kube-controller-manager-master_kube-system_7b7c15f8228e3413d3b0d0bad799b1ea_697ef6ee

27625502c298 gcr.io/google_containers/kube-apiserver-amd64:v1.5.1 "kube-apiserver --ins" 25 minutes ago Up 25 minutes k8s_kube-apiserver.5942f3e3_kube-apiserver-master_kube-system_aeb59dd32f3217b366540250d2c35d8c_38a83844

5b2cc5cb9ac1 gcr.io/google_containers/pause-amd64:3.0 "/pause" 25 minutes ago Up 25 minutes k8s_POD.d8dbe16c_kube-controller-manager-master_kube-system_7b7c15f8228e3413d3b0d0bad799b1ea_2f88a796

e12ef7b3c1f0 gcr.io/google_containers/etcd-amd64:3.0.14-kubeadm "etcd --listen-client" 25 minutes ago Up 25 minutes k8s_etcd.c323986f_etcd-master_kube-system_3a26566bb004c61cd05382212e3f978f_ef6eb513

84a731cbce18 gcr.io/google_containers/pause-amd64:3.0 "/pause" 25 minutes ago Up 25 minutes k8s_POD.d8dbe16c_kube-apiserver-master_kube-system_aeb59dd32f3217b366540250d2c35d8c_a3a2ea4e

612b021457a1 gcr.io/google_containers/kube-scheduler-amd64:v1.5.1 "kube-scheduler --add" 25 minutes ago Up 25 minutes k8s_kube-scheduler.bb7d750_kube-scheduler-master_kube-system_0545c2e223307b5ab8c74b0ffed56ac7_a49fab86

ac0d8698f79f gcr.io/google_containers/pause-amd64:3.0 "/pause" 25 minutes ago Up 25 minutes k8s_POD.d8dbe16c_etcd-master_kube-system_3a26566bb004c61cd05382212e3f978f_9a6b7925

2a16a2217bf3 gcr.io/google_containers/pause-amd64:3.0 "/pause" 25 minutes ago Up 25 minutes k8s_POD.d8dbe16c_kube-scheduler-master_kube-system_0545c2e223307b5ab8c74b0ffed56ac7_d2b51317





kube-apiserver的IP是host ip,从而推断容器使用的是host网络,这从其对应的pause容器的network属性就可以看出:



root@master:~# docker ps |grep apiserver

27625502c298 gcr.io/google_containers/kube-apiserver-amd64:v1.5.1 "kube-apiserver --ins" 26 minutes ago Up 26 minutes k8s_kube-apiserver.5942f3e3_kubeapiserver-master_kube-system_aeb59dd32f3217b366540250d2c35d8c_38a83844

84a731cbce18 gcr.io/google_containers/pause-amd64:3.0 "/pause" 26 minutes ago Up 26 minutes k8s_POD.d8dbe16c_kube-apiserver-master_kube-system_aeb59dd32f3217b366540250d2c35d8c_a3a2ea4e



问题一、

如果kubeadm init执行过程中途出现了什么问题,比如前期忘记挂加速器导致init hang住,你可能会ctrl+c退出init执行。重新配置后,再执行kubeadm init,这时你可能会遇到下面kubeadm的输出:

# kubeadm init --pod-network-cidr=10.244.0.0/16

[kubeadm] WARNING: kubeadm is in alpha, please do not use it for production clusters.

[preflight] Running pre-flight checks

[preflight] Some fatal errors occurred:

Port 10250 is in use

/etc/kubernetes/manifests is not empty

/etc/kubernetes/pki is not empty

/var/lib/kubelet is not empty

/etc/kubernetes/admin.conf already exists

/etc/kubernetes/kubelet.conf already exists

[preflight] If you know what you are doing, you can skip pre-flight checks with `--skip-preflight-checks`



kubeadm会自动检查当前环境是否有上次命令执行的“残留”。如果有,必须清理后再行执行init。我们可以通过”kubeadm reset”来清理环境,以备重来。



# kubeadm reset

[preflight] Running pre-flight checks

[reset] Draining node: "iz25beglnhtz"

[reset] Removing node: "iz25beglnhtz"

[reset] Stopping the kubelet service

[reset] Unmounting mounted directories in "/var/lib/kubelet"

[reset] Removing kubernetes-managed containers

[reset] Deleting contents of stateful directories: [/var/lib/kubelet /etc/cni/net.d /var/lib/etcd]

[reset] Deleting contents of config directories: [/etc/kubernetes/manifests /etc/kubernetes/pki]

[reset] Deleting files: [/etc/kubernetes/admin.conf /etc/kubernetes/kubelet.conf]





5、要使用Flannel网络,因此我们需要执行如下安装命令:

#kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml

configmap "kube-flannel-cfg" created

daemonset "kube-flannel-ds" created



需要稍等几秒钟,我们再来看master node上的cluster信息:

root@master:~# ps -ef |grep kube |grep flannel

root 29457 29441 0 14:09 ? 00:00:00 /opt/bin/flanneld --ip-masq --kube-subnet-mgr

root 29498 29481 0 14:09 ? 00:00:00 /bin/sh -c set -e -x; cp -f /etc/kube-flannel/cni-conf.json /etc/cni/net.d/10-flannel.conf; while true; do sleep 3600; done



root@master:~# kubectl get pods --all-namespaces

NAMESPACE NAME READY STATUS RESTARTS AGE

kube-system dummy-2088944543-r2mw3 1/1 Running 0 30m

kube-system etcd-master 1/1 Running 0 31m

kube-system kube-apiserver-master 1/1 Running 0 31m

kube-system kube-controller-manager-master 1/1 Running 0 31m

kube-system kube-discovery-1769846148-4rsq9 1/1 Running 0 30m

kube-system kube-dns-2924299975-txh1v 4/4 Running 0 30m

kube-system kube-flannel-ds-0fnxc 2/2 Running 0 29m

kube-system kube-flannel-ds-lpgpv 2/2 Running 0 23m

kube-system kube-flannel-ds-s05nr 2/2 Running 0 18m

kube-system kube-proxy-9c0bf 1/1 Running 0 30m

kube-system kube-proxy-t8hxr 1/1 Running 0 18m

kube-system kube-proxy-zd0v2 1/1 Running 0 23m

kube-system kube-scheduler-master 1/1 Running 0 31m



至少集群的核心组件已经全部run起来了。看起来似乎是成功了。





接下来开始node下的操作



6、minion node:join the cluster



这里我们用到了kubeadm的第二个命令:kubeadm join。



在minion node上执行(注意:这里要保证master node的9898端口在防火墙是打开的):

前提node下需要有上面安装的kube组建

7、安装kubelet和kubeadm

curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | apt-key add -

我是用的是

http://119.29.98.145:8070/zhi/apt-key.gpg



主机master上操作如下:



curl -s http://119.29.98.145:8070/zhi/apt-key.gpg | apt-key add -



cat <<EOF >/etc/apt/sources.list.d/kubernetes.list



deb http://apt.kubernetes.io/ kubernetes-xenial main



EOF



apt-get update



apt-get install -y docker.io

apt-get install -y kubelet kubeadm kubectl kubernetes-cni

记住master的token

root@node01:~# kubeadm join --token=2909ca.c0b0772a8817f9e3 xxx.xxx.xxx.xxx(ip)

8、在master node上查看当前cluster状态:

root@master:~# kubectl get node

NAME STATUS AGE

master Ready,master 59m

node01 Ready 51m

node02 Ready 46m 查看全部
1、下载说需要的包都得在墙外,需要翻墙。 但服务器上总不能提供这种便利。 比较麻烦。 两种办法,一种是绑定hosts  由于Kubernetes 编译的各种发行版安装包来源于 Github 上的另一个叫 release 的项目,把这个项目 clone 下来,  

可以参考漠然的文章: https://mritd.me/2016/10/29/set-up-kubernetes-cluster-by-kubeadm/
 
2、我是用的方法 是通过hosts绑定, 然后通过打包到源码,下次直接使用
使用Kubeadm安装Kubernetes1.5版本

1、系统版本:ubuntu16.04

root@master:~# docker version

Client:

Version: 1.12.1

API version: 1.24

Go version: go1.6.2

Git commit: 23cf638

Built: Tue, 27 Sep 2016 12:25:38 +1300

OS/Arch: linux/amd64



Server:

Version: 1.12.1

API version: 1.24

Go version: go1.6.2

Git commit: 23cf638

Built: Tue, 27 Sep 2016 12:25:38 +1300

OS/Arch: linux/amd64





1、部署前提条件

每台主机上面至少1G内存。

所有主机之间网络可达。



2、部署:

在主机上安装kubelet和kubeadm

curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | apt-key add -

主机master上操作如下:

cat <<EOF >/etc/apt/sources.list.d/kubernetes.list

deb http://apt.kubernetes.io/ kubernetes-xenial main

EOF

apt-get update

apt-get install -y docker.io

apt-get install -y kubelet kubeadm kubectl kubernetes-cni

下载后的kube组件并未自动运行起来。在 /lib/systemd/system下面我们能看到kubelet.service

root@master:~# ls /lib/systemd/system |grep kube

kubelet.service

kubelet的版本:

root@master:~# kubelet --version

Kubernetes v1.5.1

k8s的核心组件都有了,接下来我们就要boostrap kubernetes cluster了。

3、初始化集群

理论上通过kubeadm使用init和join命令即可建立一个集群,这init就是在master节点对集群进行初始化。和k8s 1.4之前的部署方式不同的是,

kubeadm安装的k8s核心组件都是以容器的形式运行于master node上的。因此在kubeadm init之前,最好给master node上的docker engine挂上加速器代理,

因为kubeadm要从gcr.io/google_containers repository中pull许多核心组件的images


在Kubeadm的文档中,Pod Network的安装是作为一个单独的步骤的。kubeadm init并没有为你选择一个默认的Pod network进行安装。

我们将首选Flannel 作为我们的Pod network,这不仅是因为我们的上一个集群用的就是flannel,而且表现稳定。

更是由于Flannel就是coreos为k8s打造的专属overlay network add-ons。甚至于flannel repository的readme.md都这样写着:“flannel is a network fabric for containers, designed for Kubernetes”。

如果我们要使用Flannel,那么在执行init时,按照kubeadm文档要求,我们必须给init命令带上option:–pod-network-cidr=10.244.0.0/16。


4、执行kubeadm init

执行kubeadm init命令:

root@master:~# kubeadm init --pod-network-cidr=10.244.0.0/16

[kubeadm] WARNING: kubeadm is in alpha, please do not use it for production clusters.

[preflight] Running pre-flight checks

[preflight] Starting the kubelet service

[init] Using Kubernetes version: v1.5.1

[tokens] Generated token: "2909ca.c0b0772a8817f9e3"

[certificates] Generated Certificate Authority key and certificate.

[certificates] Generated API Server key and certificate

[certificates] Generated Service Account signing keys

[certificates] Created keys and certificates in "/etc/kubernetes/pki"

[kubeconfig] Wrote KubeConfig file to disk: "/etc/kubernetes/kubelet.conf"

[kubeconfig] Wrote KubeConfig file to disk: "/etc/kubernetes/admin.conf"

[apiclient] Created API client, waiting for the control plane to become ready

[apiclient] All control plane components are healthy after 14.761716 seconds

[apiclient] Waiting for at least one node to register and become ready

[apiclient] First node is ready after 1.003312 seconds

[apiclient] Creating a test deployment

[apiclient] Test deployment succeeded

[token-discovery] Created the kube-discovery deployment, waiting for it to become ready

[token-discovery] kube-discovery is ready after 1.002402 seconds

[addons] Created essential addon: kube-proxy

[addons] Created essential addon: kube-dns



Your Kubernetes master has initialized successfully!



You should now deploy a pod network to the cluster.

Run "kubectl apply -f [podnetwork].yaml" with one of the options listed at:

http://kubernetes.io/docs/admin/addons/



You can now join any number of machines by running the following on each node:



kubeadm join --token=2909ca.c0b0772a8817f9e3 xxx.xxx.xxx.xxx (ip记下)



init成功后的master node有啥变化?k8s的核心组件均正常启动:

root@master:~# ps -ef |grep kube

root 23817 1 2 14:07 ? 00:00:35 /usr/bin/kubelet --kubeconfig=/etc/kubernetes/kubelet.conf --require-kubeconfig=true --pod-manifest-path=/etc/kubernetes/manifests --allow-privileged=true --network-plugin=cni --cni-conf-dir=/etc/cni/net.d --cni-bin-dir=/opt/cni/bin --cluster-dns=10.96.0.10 --cluster-domain=cluster.local

root 23921 23900 0 14:07 ? 00:00:01 kube-scheduler --address=127.0.0.1 --leader-elect --master=127.0.0.1:8080

root 24055 24036 0 14:07 ? 00:00:10 kube-apiserver --insecure-bind-address=127.0.0.1 --admission-control=NamespaceLifecycle,LimitRanger,ServiceAccount,PersistentVolumeLabel,DefaultStorageClass,ResourceQuota --service-cluster-ip-range=10.96.0.0/12 --service-account-key-file=/etc/kubernetes/pki/apiserver-key.pem --client-ca-file=/etc/kubernetes/pki/ca.pem --tls-cert-file=/etc/kubernetes/pki/apiserver.pem --tls-private-key-file=/etc/kubernetes/pki/apiserver-key.pem --token-auth-file=/etc/kubernetes/pki/tokens.csv --secure-port=6443 --allow-privileged --advertise-address=master的ip --kubelet-preferred-address-types=InternalIP,ExternalIP,Hostname --anonymous-auth=false --etcd-servers=http://127.0.0.1:2379

root 24084 24070 0 14:07 ? 00:00:11 kube-controller-manager --address=127.0.0.1 --leader-elect --master=127.0.0.1:8080 --cluster-name=kubernetes --root-ca-file=/etc/kubernetes/pki/ca.pem --service-account-private-key-file=/etc/kubernetes/pki/apiserver-key.pem --cluster-signing-cert-file=/etc/kubernetes/pki/ca.pem --cluster-signing-key-file=/etc/kubernetes/pki/ca-key.pem --insecure-experimental-approve-all-kubelet-csrs-for-group=system:kubelet-bootstrap --allocate-node-cidrs=true --cluster-cidr=10.244.0.0/16

root 24242 24227 0 14:07 ? 00:00:00 /usr/local/bin/kube-discovery

root 24308 24293 1 14:07 ? 00:00:15 kube-proxy --kubeconfig=/run/kubeconfig

root 29457 29441 0 14:09 ? 00:00:00 /opt/bin/flanneld --ip-masq --kube-subnet-mgr

root 29498 29481 0 14:09 ? 00:00:00 /bin/sh -c set -e -x; cp -f /etc/kube-flannel/cni-conf.json /etc/cni/net.d/10-flannel.conf; while true; do sleep 3600; done

root 30372 30357 0 14:10 ? 00:00:01 /exechealthz --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1 >/dev/null --url=/healthz-dnsmasq --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1:10053 >/dev/null --url=/healthz-kubedns --port=8080 --quiet

root 30682 30667 0 14:10 ? 00:00:01 /kube-dns --domain=cluster.local --dns-port=10053 --config-map=kube-dns --v=2

root 48755 1796 0 14:31 pts/0 00:00:00 grep --color=auto kube



而且以多cotainer的形式启动

root@master:~# docker ps

CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES

c4209b1077d2 gcr.io/google_containers/kubedns-amd64:1.9 "/kube-dns --domain=c" 22 minutes ago Up 22 minutes k8s_kube-dns.61e5a20f_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_fc02f762

0908d6398b0b gcr.io/google_containers/exechealthz-amd64:1.2 "/exechealthz '--cmd=" 22 minutes ago Up 22 minutes k8s_healthz.9d343f54_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_0ee806f6

0e35e96ca4ac gcr.io/google_containers/dnsmasq-metrics-amd64:1.0 "/dnsmasq-metrics --v" 22 minutes ago Up 22 minutes k8s_dnsmasq-metrics.2bb05ef7_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_436b9370

3921b4e59aca gcr.io/google_containers/kube-dnsmasq-amd64:1.4 "/usr/sbin/dnsmasq --" 22 minutes ago Up 22 minutes k8s_dnsmasq.f7e18a01_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_06c5efa7

18513413ba60 gcr.io/google_containers/pause-amd64:3.0 "/pause" 22 minutes ago Up 22 minutes k8s_POD.d8dbe16c_kube-dns-2924299975-txh1v_kube-system_f5364cd5-d631-11e6-9d86-0050569c3e9b_9de0a18d

45132c8d6d3d quay.io/coreos/flannel-git:v0.6.1-28-g5dde68d-amd64 "/bin/sh -c 'set -e -" 23 minutes ago Up 23 minutes k8s_install-cni.fc218cef_kube-flannel-ds-0fnxc_kube-system_22034e49-d632-11e6-9d86-0050569c3e9b_88dffd75

4c2a2e46c808 quay.io/coreos/flannel-git:v0.6.1-28-g5dde68d-amd64 "/opt/bin/flanneld --" 23 minutes ago Up 23 minutes k8s_kube-flannel.5fdd90ba_kube-flannel-ds-0fnxc_kube-system_22034e49-d632-11e6-9d86-0050569c3e9b_2706c3cb

ad08c8dd177c gcr.io/google_containers/pause-amd64:3.0 "/pause" 23 minutes ago Up 23 minutes k8s_POD.d8dbe16c_kube-flannel-ds-0fnxc_kube-system_22034e49-d632-11e6-9d86-0050569c3e9b_279d8436

847f00759977 gcr.io/google_containers/kube-proxy-amd64:v1.5.1 "kube-proxy --kubecon" 24 minutes ago Up 24 minutes k8s_kube-proxy.2f62b4e5_kube-proxy-9c0bf_kube-system_f5326252-d631-11e6-9d86-0050569c3e9b_c1f31904

f8da0f38f3e1 gcr.io/google_containers/pause-amd64:3.0 "/pause" 24 minutes ago Up 24 minutes k8s_POD.d8dbe16c_kube-proxy-9c0bf_kube-system_f5326252-d631-11e6-9d86-0050569c3e9b_c340d947

c1efa29640d1 gcr.io/google_containers/kube-discovery-amd64:1.0 "/usr/local/bin/kube-" 24 minutes ago Up 24 minutes k8s_kube-discovery.6907cb07_kube-discovery-1769846148-4rsq9_kube-system_f49933be-d631-11e6-9d86-0050569c3e9b_c4827da2

4c6a646d0b2e gcr.io/google_containers/pause-amd64:3.0 "/pause" 24 minutes ago Up 24 minutes k8s_POD.d8dbe16c_kube-discovery-1769846148-4rsq9_kube-system_f49933be-d631-11e6-9d86-0050569c3e9b_8823b66a

ece79181f177 gcr.io/google_containers/pause-amd64:3.0 "/pause" 24 minutes ago Up 24 minutes k8s_dummy.702d1bd5_dummy-2088944543-r2mw3_kube-system_f38f3ede-d631-11e6-9d86-0050569c3e9b_ade728ba

9c3364c623df gcr.io/google_containers/pause-amd64:3.0 "/pause" 24 minutes ago Up 24 minutes k8s_POD.d8dbe16c_dummy-2088944543-r2mw3_kube-system_f38f3ede-d631-11e6-9d86-0050569c3e9b_838c58b5

a64a3363a82b gcr.io/google_containers/kube-controller-manager-amd64:v1.5.1 "kube-controller-mana" 25 minutes ago Up 25 minutes k8s_kube-controller-manager.84edb2e5_kube-controller-manager-master_kube-system_7b7c15f8228e3413d3b0d0bad799b1ea_697ef6ee

27625502c298 gcr.io/google_containers/kube-apiserver-amd64:v1.5.1 "kube-apiserver --ins" 25 minutes ago Up 25 minutes k8s_kube-apiserver.5942f3e3_kube-apiserver-master_kube-system_aeb59dd32f3217b366540250d2c35d8c_38a83844

5b2cc5cb9ac1 gcr.io/google_containers/pause-amd64:3.0 "/pause" 25 minutes ago Up 25 minutes k8s_POD.d8dbe16c_kube-controller-manager-master_kube-system_7b7c15f8228e3413d3b0d0bad799b1ea_2f88a796

e12ef7b3c1f0 gcr.io/google_containers/etcd-amd64:3.0.14-kubeadm "etcd --listen-client" 25 minutes ago Up 25 minutes k8s_etcd.c323986f_etcd-master_kube-system_3a26566bb004c61cd05382212e3f978f_ef6eb513

84a731cbce18 gcr.io/google_containers/pause-amd64:3.0 "/pause" 25 minutes ago Up 25 minutes k8s_POD.d8dbe16c_kube-apiserver-master_kube-system_aeb59dd32f3217b366540250d2c35d8c_a3a2ea4e

612b021457a1 gcr.io/google_containers/kube-scheduler-amd64:v1.5.1 "kube-scheduler --add" 25 minutes ago Up 25 minutes k8s_kube-scheduler.bb7d750_kube-scheduler-master_kube-system_0545c2e223307b5ab8c74b0ffed56ac7_a49fab86

ac0d8698f79f gcr.io/google_containers/pause-amd64:3.0 "/pause" 25 minutes ago Up 25 minutes k8s_POD.d8dbe16c_etcd-master_kube-system_3a26566bb004c61cd05382212e3f978f_9a6b7925

2a16a2217bf3 gcr.io/google_containers/pause-amd64:3.0 "/pause" 25 minutes ago Up 25 minutes k8s_POD.d8dbe16c_kube-scheduler-master_kube-system_0545c2e223307b5ab8c74b0ffed56ac7_d2b51317





kube-apiserver的IP是host ip,从而推断容器使用的是host网络,这从其对应的pause容器的network属性就可以看出:



root@master:~# docker ps |grep apiserver

27625502c298 gcr.io/google_containers/kube-apiserver-amd64:v1.5.1 "kube-apiserver --ins" 26 minutes ago Up 26 minutes k8s_kube-apiserver.5942f3e3_kubeapiserver-master_kube-system_aeb59dd32f3217b366540250d2c35d8c_38a83844

84a731cbce18 gcr.io/google_containers/pause-amd64:3.0 "/pause" 26 minutes ago Up 26 minutes k8s_POD.d8dbe16c_kube-apiserver-master_kube-system_aeb59dd32f3217b366540250d2c35d8c_a3a2ea4e



问题一、

如果kubeadm init执行过程中途出现了什么问题,比如前期忘记挂加速器导致init hang住,你可能会ctrl+c退出init执行。重新配置后,再执行kubeadm init,这时你可能会遇到下面kubeadm的输出:

# kubeadm init --pod-network-cidr=10.244.0.0/16

[kubeadm] WARNING: kubeadm is in alpha, please do not use it for production clusters.

[preflight] Running pre-flight checks

[preflight] Some fatal errors occurred:

Port 10250 is in use

/etc/kubernetes/manifests is not empty

/etc/kubernetes/pki is not empty

/var/lib/kubelet is not empty

/etc/kubernetes/admin.conf already exists

/etc/kubernetes/kubelet.conf already exists

[preflight] If you know what you are doing, you can skip pre-flight checks with `--skip-preflight-checks`



kubeadm会自动检查当前环境是否有上次命令执行的“残留”。如果有,必须清理后再行执行init。我们可以通过”kubeadm reset”来清理环境,以备重来。



# kubeadm reset

[preflight] Running pre-flight checks

[reset] Draining node: "iz25beglnhtz"

[reset] Removing node: "iz25beglnhtz"

[reset] Stopping the kubelet service

[reset] Unmounting mounted directories in "/var/lib/kubelet"

[reset] Removing kubernetes-managed containers

[reset] Deleting contents of stateful directories: [/var/lib/kubelet /etc/cni/net.d /var/lib/etcd]

[reset] Deleting contents of config directories: [/etc/kubernetes/manifests /etc/kubernetes/pki]

[reset] Deleting files: [/etc/kubernetes/admin.conf /etc/kubernetes/kubelet.conf]





5、要使用Flannel网络,因此我们需要执行如下安装命令:

#kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml

configmap "kube-flannel-cfg" created

daemonset "kube-flannel-ds" created



需要稍等几秒钟,我们再来看master node上的cluster信息:

root@master:~# ps -ef |grep kube |grep flannel

root 29457 29441 0 14:09 ? 00:00:00 /opt/bin/flanneld --ip-masq --kube-subnet-mgr

root 29498 29481 0 14:09 ? 00:00:00 /bin/sh -c set -e -x; cp -f /etc/kube-flannel/cni-conf.json /etc/cni/net.d/10-flannel.conf; while true; do sleep 3600; done



root@master:~# kubectl get pods --all-namespaces

NAMESPACE NAME READY STATUS RESTARTS AGE

kube-system dummy-2088944543-r2mw3 1/1 Running 0 30m

kube-system etcd-master 1/1 Running 0 31m

kube-system kube-apiserver-master 1/1 Running 0 31m

kube-system kube-controller-manager-master 1/1 Running 0 31m

kube-system kube-discovery-1769846148-4rsq9 1/1 Running 0 30m

kube-system kube-dns-2924299975-txh1v 4/4 Running 0 30m

kube-system kube-flannel-ds-0fnxc 2/2 Running 0 29m

kube-system kube-flannel-ds-lpgpv 2/2 Running 0 23m

kube-system kube-flannel-ds-s05nr 2/2 Running 0 18m

kube-system kube-proxy-9c0bf 1/1 Running 0 30m

kube-system kube-proxy-t8hxr 1/1 Running 0 18m

kube-system kube-proxy-zd0v2 1/1 Running 0 23m

kube-system kube-scheduler-master 1/1 Running 0 31m



至少集群的核心组件已经全部run起来了。看起来似乎是成功了。





接下来开始node下的操作



6、minion node:join the cluster



这里我们用到了kubeadm的第二个命令:kubeadm join。



在minion node上执行(注意:这里要保证master node的9898端口在防火墙是打开的):

前提node下需要有上面安装的kube组建

7、安装kubelet和kubeadm

curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | apt-key add -

我是用的是

http://119.29.98.145:8070/zhi/apt-key.gpg



主机master上操作如下:



curl -s http://119.29.98.145:8070/zhi/apt-key.gpg | apt-key add -



cat <<EOF >/etc/apt/sources.list.d/kubernetes.list



deb http://apt.kubernetes.io/ kubernetes-xenial main



EOF



apt-get update



apt-get install -y docker.io

apt-get install -y kubelet kubeadm kubectl kubernetes-cni

记住master的token

root@node01:~# kubeadm join --token=2909ca.c0b0772a8817f9e3 xxx.xxx.xxx.xxx(ip)

8、在master node上查看当前cluster状态:

root@master:~# kubectl get node

NAME STATUS AGE

master Ready,master 59m

node01 Ready 51m

node02 Ready 46m

源码分析Elasticsearch Master选举过程

Geek小A 发表了文章 • 2 个评论 • 524 次浏览 • 2017-01-05 20:16 • 来自相关话题

ES 有Master节点和Data节点,Master节点什么意思呢? 就是主人节点,这个集群的主人,就是皇帝。ES同一时刻只有一个Master节点。小生一直看古装走火入魔,所谓心里有王朝,眼里就有王朝,看啥啥是王朝。就用王朝解释下集群,皇帝比喻下Master。我们先来看2个配置项。
 
node.master: true  就是皇子,意思是有资格成为Master,成为皇帝的人选,这是天生的,是无字天书,在elasticsearch.yml里写好的。

discovery.zen.minimum_master_nodes: 1 就是几个皇子在场的时候,才能选新皇帝,不然难以服众,容易脑裂(brain split)是吧。
 

Master的职责

只有皇帝才有资格发布圣旨ClusterState(集群状态)。他维护着这个王朝的状态,决定着这个王朝很多重要的大小事物。有一些事情必须皇帝才能执行,比如砍头(删除索引)。但是ES作为P2P集群,Master的职责,还是被弱化了一些。一张图看一下皇帝的工作内容。





 

什么时候选Master

只有在皇帝驾崩,和王朝诞生的时候,才选举Master皇帝,是吧,想让皇帝禅位,除非他死了,或者王朝被推翻了(所有节点重启)

 
节点启动,要加入一个集群的时候
 
//ZenDiscovery
private void innterJoinCluster() {
boolean retry = true;
while (retry) {
if (lifecycle.stoppedOrClosed()) {
return;
}
retry = false;
DiscoveryNode masterNode = findMaster(); //找一个节点出来当皇帝
if (masterNode == null) {
logger.trace("no masterNode returned");
retry = true;
continue;
}
//....
或者节点关闭 Master Gone
private void handleMasterGone(final DiscoveryNode masterNode, final String reason) {
if (lifecycleState() != Lifecycle.State.STARTED) {
return;
}
if (master) {
return;
}
logger.info("master_left [{}], reason [{}]", masterNode, reason);
clusterService.submitStateUpdateTask("zen-disco-master_failed (" + masterNode + ")", Priority.HIGH, new ProcessedClusterStateUpdateTask() {
@Override
public ClusterState execute(ClusterState currentState) {
if (!masterNode.id().equals(currentState.nodes().masterNodeId())) {
return currentState;
}
DiscoveryNodes.Builder nodesBuilder = DiscoveryNodes.newNodesBuilder()
.putAll(currentState.nodes())
.remove(masterNode.id())
.masterNodeId(null);
if (!electMaster.hasEnoughMasterNodes(nodesBuilder.build())) {
return rejoin(ClusterState.builder().state(currentState).nodes(nodesBuilder).build(), "not enough master nodes after master left (reason = " + reason + ")");
}
final DiscoveryNode electedMaster = electMaster.electMaster(nodesBuilder.build()); // 选举Master
 

Master选举

首先必须是皇子(node.master: true),具体哪皇子成为皇帝呢? 看天意啊,最先启动的那个节点。老臣认为。当立嫡长子为太子,成为皇帝啊,这样江山社稷才能稳固啊,(一阵激动)省略上万句。。。好了,演完戏了,看代码。

 
ZenDiscovery模块启动的时候,要加入集群。findMaster 方法里,Ping一堆节点出来,Ping就是发现节点,这里的Ping不是Linux的命令Ping,是向ES的9300端口发送数据的意思。Linux的Ping是可以禁止的,不能因为命令Ping不通机器,就认为相互不能发现节点。Ping有组播MulticastZenPing和单播UnicastZenPing 两种。如果节点少,用单播也可以。组播在一些环境下可能无法相互发现节点,或者被安全软件识别为恶意程序。节点列表确定后。交给 ElectMasterService 去选举,快排后的第一个节点
//ElectMasterService
/**
* Elects a new master out of the possible nodes, returning it. Returns <tt>null</tt>
* if no master has been elected.
*/
public DiscoveryNode electMaster(Iterable<DiscoveryNode> nodes) {
List<DiscoveryNode> sortedNodes = sortedMasterNodes(nodes);
if (sortedNodes == null || sortedNodes.isEmpty()) {
return null;
}
return sortedNodes.get(0);
}

private List<DiscoveryNode> sortedMasterNodes(Iterable<DiscoveryNode> nodes) {
List<DiscoveryNode> possibleNodes = Lists.newArrayList(nodes);
if (possibleNodes.isEmpty()) {
return null;
}
// clean non master nodes
for (Iterator<DiscoveryNode> it = possibleNodes.iterator(); it.hasNext(); ) {
DiscoveryNode node = it.next();
if (!node.masterNode()) {
it.remove();
}
}
CollectionUtil.quickSort(possibleNodes, nodeComparator);
return possibleNodes;
}对了,皇帝上位以后,第一件事情是发布圣旨,昭告天下,以后寡人就是皇帝了。

怎么看,现在谁是皇帝呢?
 
curl http://localhost:9200/_cat/master?v
脑裂问题
 
关于brain split脑裂问题,可以看这个:
如何避免脑裂: http://blog.trifork.com/2013/10/24/how-to-avoid-the-split-brain-problem-in-elasticsearch/  
官方讨论:https://github.com/elasticsearch/elasticsearch/issues/2488 
 
最后,为了让大家对皇帝有个感性的认识,赠图一张,不谢!




原文分享:http://www.codeweblog.com/elasticsearch-%E6%BA%90%E4%BB%A3%E7%A0%81%E5%88%86%E6%9E%90%E4%B9%8Bmaster%E9%80%89%E4%B8%BE/  查看全部
ES 有Master节点和Data节点,Master节点什么意思呢? 就是主人节点,这个集群的主人,就是皇帝。ES同一时刻只有一个Master节点。小生一直看古装走火入魔,所谓心里有王朝,眼里就有王朝,看啥啥是王朝。就用王朝解释下集群,皇帝比喻下Master。我们先来看2个配置项。
 
node.master: true  就是皇子,意思是有资格成为Master,成为皇帝的人选,这是天生的,是无字天书,在elasticsearch.yml里写好的。

discovery.zen.minimum_master_nodes: 1 就是几个皇子在场的时候,才能选新皇帝,不然难以服众,容易脑裂(brain split)是吧。
 


Master的职责


只有皇帝才有资格发布圣旨ClusterState(集群状态)。他维护着这个王朝的状态,决定着这个王朝很多重要的大小事物。有一些事情必须皇帝才能执行,比如砍头(删除索引)。但是ES作为P2P集群,Master的职责,还是被弱化了一些。一张图看一下皇帝的工作内容。

Masterkpi.png

 


什么时候选Master


只有在皇帝驾崩,和王朝诞生的时候,才选举Master皇帝,是吧,想让皇帝禅位,除非他死了,或者王朝被推翻了(所有节点重启)

 
节点启动,要加入一个集群的时候
 
//ZenDiscovery
private void innterJoinCluster() {
boolean retry = true;
while (retry) {
if (lifecycle.stoppedOrClosed()) {
return;
}
retry = false;
DiscoveryNode masterNode = findMaster(); //找一个节点出来当皇帝
if (masterNode == null) {
logger.trace("no masterNode returned");
retry = true;
continue;
}
//....

或者节点关闭 Master Gone
private void handleMasterGone(final DiscoveryNode masterNode, final String reason) {
if (lifecycleState() != Lifecycle.State.STARTED) {
return;
}
if (master) {
return;
}
logger.info("master_left [{}], reason [{}]", masterNode, reason);
clusterService.submitStateUpdateTask("zen-disco-master_failed (" + masterNode + ")", Priority.HIGH, new ProcessedClusterStateUpdateTask() {
@Override
public ClusterState execute(ClusterState currentState) {
if (!masterNode.id().equals(currentState.nodes().masterNodeId())) {
return currentState;
}
DiscoveryNodes.Builder nodesBuilder = DiscoveryNodes.newNodesBuilder()
.putAll(currentState.nodes())
.remove(masterNode.id())
.masterNodeId(null);
if (!electMaster.hasEnoughMasterNodes(nodesBuilder.build())) {
return rejoin(ClusterState.builder().state(currentState).nodes(nodesBuilder).build(), "not enough master nodes after master left (reason = " + reason + ")");
}
final DiscoveryNode electedMaster = electMaster.electMaster(nodesBuilder.build()); // 选举Master

 


Master选举


首先必须是皇子(node.master: true),具体哪皇子成为皇帝呢? 看天意啊,最先启动的那个节点。老臣认为。当立嫡长子为太子,成为皇帝啊,这样江山社稷才能稳固啊,(一阵激动)省略上万句。。。好了,演完戏了,看代码。

 
ZenDiscovery模块启动的时候,要加入集群。findMaster 方法里,Ping一堆节点出来,Ping就是发现节点,这里的Ping不是Linux的命令Ping,是向ES的9300端口发送数据的意思。Linux的Ping是可以禁止的,不能因为命令Ping不通机器,就认为相互不能发现节点。Ping有组播MulticastZenPing和单播UnicastZenPing 两种。如果节点少,用单播也可以。组播在一些环境下可能无法相互发现节点,或者被安全软件识别为恶意程序。节点列表确定后。交给 ElectMasterService 去选举,快排后的第一个节点
//ElectMasterService
/**
* Elects a new master out of the possible nodes, returning it. Returns <tt>null</tt>
* if no master has been elected.
*/
public DiscoveryNode electMaster(Iterable<DiscoveryNode> nodes) {
List<DiscoveryNode> sortedNodes = sortedMasterNodes(nodes);
if (sortedNodes == null || sortedNodes.isEmpty()) {
return null;
}
return sortedNodes.get(0);
}

private List<DiscoveryNode> sortedMasterNodes(Iterable<DiscoveryNode> nodes) {
List<DiscoveryNode> possibleNodes = Lists.newArrayList(nodes);
if (possibleNodes.isEmpty()) {
return null;
}
// clean non master nodes
for (Iterator<DiscoveryNode> it = possibleNodes.iterator(); it.hasNext(); ) {
DiscoveryNode node = it.next();
if (!node.masterNode()) {
it.remove();
}
}
CollectionUtil.quickSort(possibleNodes, nodeComparator);
return possibleNodes;
}
对了,皇帝上位以后,第一件事情是发布圣旨,昭告天下,以后寡人就是皇帝了。

怎么看,现在谁是皇帝呢?
 
curl http://localhost:9200/_cat/master?v

脑裂问题
 
关于brain split脑裂问题,可以看这个:
如何避免脑裂: http://blog.trifork.com/2013/10/24/how-to-avoid-the-split-brain-problem-in-elasticsearch/  
官方讨论:https://github.com/elasticsearch/elasticsearch/issues/2488 
 
最后,为了让大家对皇帝有个感性的认识,赠图一张,不谢!
hd.png

原文分享:http://www.codeweblog.com/elasticsearch-%E6%BA%90%E4%BB%A3%E7%A0%81%E5%88%86%E6%9E%90%E4%B9%8Bmaster%E9%80%89%E4%B8%BE/ 

消费kafka数据出错Found a message larger than the maximum fetch size

采菊篱下 回复了问题 • 2 人关注 • 1 个回复 • 568 次浏览 • 2017-01-05 14:18 • 来自相关话题

如何为Kafka集群选择合适的主题和分区数量

Ansible 发表了文章 • 0 个评论 • 446 次浏览 • 2016-12-26 00:03 • 来自相关话题

这是许多Kafka用户提出的常见问题。 这篇文章的目的是解释几个重要的决定因素,并提供一些简单的公式。
 

更多的分区提供更高的吞吐量

首先要理解的是,主题分区是Kafka中并行性的单位。 在生产者和代理端,对不同分区的写入可以完全并行完成。 因此,昂贵的操作(例如压缩)可以利用更多的硬件资源。 在消费者方面,Kafka总是将一个分区的数据提供给一个消费者线程。 因此,消费者(在消费者组内)的并行度受所消耗的分区的数量的限制。 因此,一般来说,Kafka集群中的分区越多,吞吐量就越高。

用于选择分区数量的粗略公式基于吞吐量。 你衡量整个,你可以在生产单个分区(称之为P)和消费实现(称为C)。 比方说,你的目标吞吐量吨 。 然后,你需要至少有MAX(T / P,T / C)分区。 人们可以在生产者上实现的每分区吞吐量取决于诸如批处理大小,压缩编解码器,确认类型,复制因子等等的配置。然而,一般来说,可以在10秒的MB /如在此所示单个分区的基准 。 消费者吞吐量通常是与应用相关的,因为它对应于消费者逻辑可以如何快速地处理每个消息。 所以,你真的需要测量它。

虽然可以随着时间增加分区的数量,但是如果使用密钥生成消息,则必须小心。 当发布带密钥的消息时,Kafka基于密钥的散列将消息确定性地映射到分区。 这提供了保证具有相同密钥的消息总是路由到同一分区。 此保证对于某些应用可能是重要的,因为分区内的消息总是按顺序递送给消费者。 如果分区的数量改变,则这样的保证可能不再保持。 为了避免这种情况,一种常见的做法是过度分区。 基本上,您可以根据未来的目标吞吐量确定分区数,比如一两年后。 最初,您可以根据您的当前吞吐量只有一个小的Kafka集群。 随着时间的推移,您可以向集群添加更多代理,并按比例将现有分区的一部分移动到新代理(可以在线完成)。 这样,当使用密钥时,您可以跟上吞吐量增长,而不会破坏应用程序中的语义。

除了吞吐量,还有一些其他因素,在选择分区数时值得考虑。 正如你将看到的,在某些情况下,分区太多也可能产生负面影响。
 

更多分区需要打开更多的文件句柄

每个分区映射到broker中文件系统中的目录。 在该日志目录中,每个日志段将有两个文件(一个用于索引,另一个用于实际数据)。 目前,在Kafka中,每个broker打开每个日志段的索引和数据文件的文件句柄。 因此,分区越多,底层操作系统中需要配置打开文件句柄限制的分区越多。 这大多只是一个配置问题。 我们已经看到生产Kafka集群中,运行的每个broker打开的文件句柄数超过30000。
 

更多分区可能是不可用性增加

Kafka支持群集内复制 ,它提供更高的可用性和耐用性。 分区可以有多个副本,每个副本存储在不同的代理上。 其中一个副本被指定为领导者,其余的副本是追随者。 在内部,Kafka自动管理所有这些副本,并确保它们保持同步。 生产者和消费者对分区的请求都在领导副本上提供。 当代理失败时,该代理上具有leader的分区变得暂时不可用。 Kafka将自动将那些不可用分区的领导者移动到其他一些副本以继续服务客户端请求。 这个过程由指定为控制器的Kafka代理之一完成。 它涉及在ZooKeeper中为每个受影响的分区读取和写入一些元数据。 目前,ZooKeeper的操作是在控制器中串行完成的。

在通常情况下,当代理被干净地关闭时,控制器将主动地将领导者一次一个地关闭关闭代理。 单个领导者的移动只需要几毫秒。 因此,从客户的角度来看,在干净的代理关闭期间只有一小窗口的不可用性。

然而,当代理不干净地关闭(例如,kill -9)时,所观察到的不可用性可能与分区的数量成比例。 假设代理具有总共2000个分区,每个具有2个副本。 大致来说,这个代理将是大约1000个分区的领导者。 当这个代理不干净失败时,所有这1000个分区完全不能同时使用。 假设为单个分区选择新的领导需要5毫秒。 对于所有1000个分区,选择新的领导将需要5秒钟。 因此,对于一些分区,它们的观察到的不可用性可以是5秒加上检测故障所花费的时间。

如果一个是不幸的,失败的代理可能是控制器。 在这种情况下,选举新领导者的过程将不会开始,直到控制器故障转移到新的代理。 控制器故障转移自动发生,但需要新控制器在初始化期间从ZooKeeper读取每个分区的一些元数据。 例如,如果Kafka集群中有10,000个分区,并且从ZooKeeper初始化元数据每个分区需要2ms,则可以向不可用性窗口添加20多秒。

一般来说,不洁的故障是罕见的。 但是,如果在这种极少数情况下关心可用性,则可能最好将每个代理的分区数限制为两个到四千个,集群中的分区总数限制到几万个。
 

更多分区可能会增加端到端延迟

Kafka中的端到端延迟由从生产者发布消息到消费者读取消息的时间来定义。 Kafka仅在提交后向消费者公开消息,即,当消息被复制到所有同步副本时。 因此,提交消息的时间可以是端到端等待时间的显着部分。 默认情况下,对于在两个代理之间共享副本的所有分区,Kafka代理仅使用单个线程从另一个代理复制数据。 我们的实验表明,将1000个分区从一个代理复制到另一个代理可以添加大约20毫秒的延迟,这意味着端到端延迟至少为20毫秒。 这对于一些实时应用来说可能太高。

请注意,此问题在较大的群集上减轻。 例如,假设代理上有1000个分区引导,并且在同一个Kafka集群中有10个其他代理。 剩余的10个代理中的每个仅需要从第一代理平均获取100个分区。 因此,由于提交消息而增加的延迟将仅为几毫秒,而不是几十毫秒。

作为一个经验法则,如果你关心的延迟,它可能是一个好主意,每个经纪人的分区数量限制为100 * b * r,其中b是经纪人在kafka集群的数量和r是复制因子。
 

更多分区可能需要更多的内存在客户端

在最新的0.8.2版本,我们汇合到我们平台1.0,我们已经开发出一种更有效的Java生产商。 新生产者的一个好的功能是它允许用户设置用于缓冲传入消息的内存量的上限。 在内部,生产者缓冲每个分区的消息。 在累积了足够的数据或已经过去足够的时间之后,累积的消息从缓冲器中移除并发送到代理。

如果增加分区的数量,消息将在生产者中的更多分区中累积。 所使用的内存总量现在可能超过配置的内存限制。 当这种情况发生时,生产者必须阻止或丢弃任何新的消息,这两者都不是理想的。 为了防止这种情况发生,需要重新配置具有较大内存大小的生产者。

作为经验法则,为了实现良好的吞吐量,应该在生成器中分配至少几十KB的每个分区,并且如果分区的数量显着增加,则调整存储器的总量。

消费者也存在类似的问题。 消费者每个分区获取一批消息。 消费者消耗的分区越多,需要的内存就越多。 然而,这通常只是不是实时的消费者的问题。
 

总结

通常,Kafka集群中的更多分区导致更高的吞吐量。 然而,人们不得不意识到在总体上或每个代理中具有过多分区对可用性和等待时间的潜在影响。 在未来,我们计划改进一些限制,使Kafka在分区数方面更具可扩展性。
 

翻译原文:https://www.confluent.io/blog/how-to-choose-the-number-of-topicspartitions-in-a-kafka-cluster/  
作者:饶俊 查看全部
kafka.png

这是许多Kafka用户提出的常见问题。 这篇文章的目的是解释几个重要的决定因素,并提供一些简单的公式。
 


更多的分区提供更高的吞吐量


首先要理解的是,主题分区是Kafka中并行性的单位。 在生产者和代理端,对不同分区的写入可以完全并行完成。 因此,昂贵的操作(例如压缩)可以利用更多的硬件资源。 在消费者方面,Kafka总是将一个分区的数据提供给一个消费者线程。 因此,消费者(在消费者组内)的并行度受所消耗的分区的数量的限制。 因此,一般来说,Kafka集群中的分区越多,吞吐量就越高。

用于选择分区数量的粗略公式基于吞吐量。 你衡量整个,你可以在生产单个分区(称之为P)和消费实现(称为C)。 比方说,你的目标吞吐量吨 。 然后,你需要至少有MAX(T / P,T / C)分区。 人们可以在生产者上实现的每分区吞吐量取决于诸如批处理大小,压缩编解码器,确认类型,复制因子等等的配置。然而,一般来说,可以在10秒的MB /如在此所示单个分区的基准 。 消费者吞吐量通常是与应用相关的,因为它对应于消费者逻辑可以如何快速地处理每个消息。 所以,你真的需要测量它。

虽然可以随着时间增加分区的数量,但是如果使用密钥生成消息,则必须小心。 当发布带密钥的消息时,Kafka基于密钥的散列将消息确定性地映射到分区。 这提供了保证具有相同密钥的消息总是路由到同一分区。 此保证对于某些应用可能是重要的,因为分区内的消息总是按顺序递送给消费者。 如果分区的数量改变,则这样的保证可能不再保持。 为了避免这种情况,一种常见的做法是过度分区。 基本上,您可以根据未来的目标吞吐量确定分区数,比如一两年后。 最初,您可以根据您的当前吞吐量只有一个小的Kafka集群。 随着时间的推移,您可以向集群添加更多代理,并按比例将现有分区的一部分移动到新代理(可以在线完成)。 这样,当使用密钥时,您可以跟上吞吐量增长,而不会破坏应用程序中的语义。

除了吞吐量,还有一些其他因素,在选择分区数时值得考虑。 正如你将看到的,在某些情况下,分区太多也可能产生负面影响。
 


更多分区需要打开更多的文件句柄


每个分区映射到broker中文件系统中的目录。 在该日志目录中,每个日志段将有两个文件(一个用于索引,另一个用于实际数据)。 目前,在Kafka中,每个broker打开每个日志段的索引和数据文件的文件句柄。 因此,分区越多,底层操作系统中需要配置打开文件句柄限制的分区越多。 这大多只是一个配置问题。 我们已经看到生产Kafka集群中,运行的每个broker打开的文件句柄数超过30000。
 


更多分区可能是不可用性增加


Kafka支持群集内复制 ,它提供更高的可用性和耐用性。 分区可以有多个副本,每个副本存储在不同的代理上。 其中一个副本被指定为领导者,其余的副本是追随者。 在内部,Kafka自动管理所有这些副本,并确保它们保持同步。 生产者和消费者对分区的请求都在领导副本上提供。 当代理失败时,该代理上具有leader的分区变得暂时不可用。 Kafka将自动将那些不可用分区的领导者移动到其他一些副本以继续服务客户端请求。 这个过程由指定为控制器的Kafka代理之一完成。 它涉及在ZooKeeper中为每个受影响的分区读取和写入一些元数据。 目前,ZooKeeper的操作是在控制器中串行完成的。

在通常情况下,当代理被干净地关闭时,控制器将主动地将领导者一次一个地关闭关闭代理。 单个领导者的移动只需要几毫秒。 因此,从客户的角度来看,在干净的代理关闭期间只有一小窗口的不可用性。

然而,当代理不干净地关闭(例如,kill -9)时,所观察到的不可用性可能与分区的数量成比例。 假设代理具有总共2000个分区,每个具有2个副本。 大致来说,这个代理将是大约1000个分区的领导者。 当这个代理不干净失败时,所有这1000个分区完全不能同时使用。 假设为单个分区选择新的领导需要5毫秒。 对于所有1000个分区,选择新的领导将需要5秒钟。 因此,对于一些分区,它们的观察到的不可用性可以是5秒加上检测故障所花费的时间。

如果一个是不幸的,失败的代理可能是控制器。 在这种情况下,选举新领导者的过程将不会开始,直到控制器故障转移到新的代理。 控制器故障转移自动发生,但需要新控制器在初始化期间从ZooKeeper读取每个分区的一些元数据。 例如,如果Kafka集群中有10,000个分区,并且从ZooKeeper初始化元数据每个分区需要2ms,则可以向不可用性窗口添加20多秒。

一般来说,不洁的故障是罕见的。 但是,如果在这种极少数情况下关心可用性,则可能最好将每个代理的分区数限制为两个到四千个,集群中的分区总数限制到几万个。
 


更多分区可能会增加端到端延迟


Kafka中的端到端延迟由从生产者发布消息到消费者读取消息的时间来定义。 Kafka仅在提交后向消费者公开消息,即,当消息被复制到所有同步副本时。 因此,提交消息的时间可以是端到端等待时间的显着部分。 默认情况下,对于在两个代理之间共享副本的所有分区,Kafka代理仅使用单个线程从另一个代理复制数据。 我们的实验表明,将1000个分区从一个代理复制到另一个代理可以添加大约20毫秒的延迟,这意味着端到端延迟至少为20毫秒。 这对于一些实时应用来说可能太高。

请注意,此问题在较大的群集上减轻。 例如,假设代理上有1000个分区引导,并且在同一个Kafka集群中有10个其他代理。 剩余的10个代理中的每个仅需要从第一代理平均获取100个分区。 因此,由于提交消息而增加的延迟将仅为几毫秒,而不是几十毫秒。

作为一个经验法则,如果你关心的延迟,它可能是一个好主意,每个经纪人的分区数量限制为100 * b * r,其中b是经纪人在kafka集群的数量和r是复制因子。
 


更多分区可能需要更多的内存在客户端


在最新的0.8.2版本,我们汇合到我们平台1.0,我们已经开发出一种更有效的Java生产商。 新生产者的一个好的功能是它允许用户设置用于缓冲传入消息的内存量的上限。 在内部,生产者缓冲每个分区的消息。 在累积了足够的数据或已经过去足够的时间之后,累积的消息从缓冲器中移除并发送到代理。

如果增加分区的数量,消息将在生产者中的更多分区中累积。 所使用的内存总量现在可能超过配置的内存限制。 当这种情况发生时,生产者必须阻止或丢弃任何新的消息,这两者都不是理想的。 为了防止这种情况发生,需要重新配置具有较大内存大小的生产者。

作为经验法则,为了实现良好的吞吐量,应该在生成器中分配至少几十KB的每个分区,并且如果分区的数量显着增加,则调整存储器的总量。

消费者也存在类似的问题。 消费者每个分区获取一批消息。 消费者消耗的分区越多,需要的内存就越多。 然而,这通常只是不是实时的消费者的问题。
 


总结


通常,Kafka集群中的更多分区导致更高的吞吐量。 然而,人们不得不意识到在总体上或每个代理中具有过多分区对可用性和等待时间的潜在影响。 在未来,我们计划改进一些限制,使Kafka在分区数方面更具可扩展性。
 


翻译原文:https://www.confluent.io/blog/how-to-choose-the-number-of-topicspartitions-in-a-kafka-cluster/  
作者:饶俊


Druid每个任务内存调整

回复

采菊篱下 发起了问题 • 1 人关注 • 0 个回复 • 533 次浏览 • 2016-12-08 16:22 • 来自相关话题