前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Rancher2.1.4使用记录 原

Rancher2.1.4使用记录 原

作者头像
尚浩宇
发布2019-03-12 10:59:04
2.2K0
发布2019-03-12 10:59:04
举报
文章被收录于专栏:杂烩杂烩

一、前言

    说实话,Rancher的官方文档真的很全,围绕着UI的方方面面都面面俱到。但看多了却发现,很多东西都浅尝辄止,尤其某个东西实在不懂的时候,看文档只能让自己更没头绪。所以此文的目的是方便自己能够在需要的时候回忆出点点滴滴。

    Rancher1.6的傻瓜式操作给了我很大的帮助,也帮我赢得了大部分运维的支持,最终得以施展。但Rancher2.0无论是开发版还是beta版,都并不是那么友好,总是莫名其妙的出现各种各样的问题。后来因为工作的调动,没有继续研究新版。不过现在终于有时间了,当前最新版本2.1.4,所以此文的基础也就是2.1.4。

    另外,本文不会花篇幅去介绍如何安装或者解决安装中的问题,但涉及到的,我都会附上链接。本文主要的作用一个是备忘,还一个是手册。如果以后回头看这篇文章,发现忘了的看一遍就回忆起来了,照着做一遍的环境就搭好了那就完美了。

二、先决

    有必要在这里提前声明一下先决条件(并不是说实际上就是这个数据,而是我的环境是这个数据)。从Rancher1.6开始到现在的2.1.4,每一个版本都用过。不同的版本对先决条件敏感,如1.6是敏感度最迟钝的,只要保证OS内核3.1.10以上(含)即可。至于Docker版本,在查阅Rancher文档的时候,很多地方明确指出最高支持版本17.02,但实际使用过程中,只要是最新版本的都可以。以下是具体的环境说明:

    物理机OS:Ubuntu 18.04

    Docker:18.09

    harbor:1.7.1

    Gitlab:10.4.4

三、准备

    从零开始,现有三台物理机,两台服务器,一台笔记本,服务器上只跑一个虚拟机实例,笔记本跑两个虚拟机实例。但需要注意的是:如果需要拷贝虚拟机,必须是同物理机上的拷贝,而不能夸物理机拷贝,哪怕用了什么ovf虚拟机格式,也都不行,因为在实际使用的时候会出现一些莫名的错误,也可能不出,全靠运气。以下是主要步骤(可直接点击穿越到教程,教程来源于网络):

1、更新源(apt-get update && apt-get upgrade)

    2、修改vi命令(默认vi命令不友好)

    3、设置root用户以及启用root远程登录

    4、设置limit

    5、安装docker

    6、配置加速器(加速器可用daoclould也可用阿里的,这里贴出的是daoclould的)

    7、设置机器域名host指向(如果是直接使用IP访问的话,跳过这个)

    8.1、安装rancher

代码语言:javascript
复制
sudo docker run -d --restart=unless-stopped -p 80:80 -p 443:443 rancher/rancher

    8.2、安装harbor

    9、登录Rancher创建集群导入机器

    10、所有机器harbor登录授权(如果不需要自己手动pull私服上的镜像,此步跳过)

    额外需要注意的是:

        1、最新版本的docker默认采用https方式拉取镜像(确切的说是自1.3.2版本开始),如果使用http,那就需要在机器上添加过滤,详情点击

        2、自授权的https证书,需要在机器上信任,信任方式点此

        3、Rancher内部是k8s,k8s集群中,不会读取宿主机的证书。故在宿主机配置了证书信任,不会渗透到k8s集群。也就是说在宿主机信任证书,对于k8s来说,没有任何影响。这个产生一个很大问题,就是在Rancher里配置了镜像库后,Rancher无法登陆到镜像库,原因就是CA证书不被信任。这直接导致私有镜像私服被废了,除非公司花钱买证书,或者使用如阿里云镜像私服这样第三方服务。

四、概念说明

    这一部分是说明1.6和2.0两部分,Rancher的概念,目的是着重理解Rancher。

    前段时间看了本书叫《码农翻身:用故事给技术加点料》,这个思路很清奇,久久不能忘。遂本章也用说故事的方式来阐明概念。

4.1白手起家的农场主(1.x)

    小明的志向是当一个农场主。虽然他从来没干过,但是他现在准备干了。

    于是他买了一块地,首先他用栅栏围了起来,防止牛羊越狱,同时也防止可恶的豺狼豹子偷猎牛羊。然后小明对圈内的地进行的划分,A区域B区域……,这样可以方便管理。每个区域他又建了很多棚舍,不过棚舍之间是互通的,这样牛羊就不会寂寞,可以串串门。

    万事俱备只差牛羊,小明考虑直接去牛羊中心,路途遥远,倒不如去最近的代理商,代理商就像超市,把牛羊从厂家运送过来,这样省时又省力。为了保险起见,小明只买了几百只牛羊,然后赶到自己规划好的农场。

    其实小明的工作很简单,定时检查一下牛羊的状态,是不是饿了渴了或者生病了又或者死亡了,不过如果牛羊死亡了,小明就必须再买一头回来。有时候小明还会给牛羊做个造型美化一下,小明说这叫升级,当然如果美化失败了,小明还会恢复原样,小明又叫这个回滚。

    小明很满意自己的农场,但觉得一个人有点无聊,于是他又建立了一个站台,站在站台上可以看到某个区域的每个棚舍,就像动物园一样。然后开放给大家,不仅能赚点外快,还不会觉得无聊。

    从此,小明过上了幸福的农场主生活,实现了人生理想。

    故事到此结束,现在解释一下文中的概念:

        1、小明:rancher的master节点 

        2、栅栏:rancher集群

        3、区域:集群

        4、棚舍:项目

        5、牛羊:容器

        6、牛羊中心:docker hub镜像中心

        7、代理商:国内镜像如阿里云

        8、升级:镜像升级

        9、回滚:镜像回滚

        10、站台:负载均衡(HA)

        11、小明的工作:cattle编排引擎

4.2高速发展的农场(2.x)

    小明的幸福没过多久,就出现问题了。第一,小明每天不仅要进行繁琐的工作,还要接待到访的游客,忙得团团转。第二、牧场太小了,访客太多了,每次都有人抱怨等待的时间太久了。小明痛定思痛决定要改善这两个问题,好在经营了一段时间,手里攒了不少积蓄。

    首先,他扩大了牧场,区域划分保持不变,以前一个大棚舍,现在建好几个大棚舍,但棚舍里做好规划,不同棚舍养不同的牛羊,同时棚舍之间是独立的,防止牛羊乱窜,但一样的同一个棚舍还是不禁止的。另外,大棚舍里的小棚舍,也得改造,每次游客来都反应脏乱差。所以,给每一头牛羊建立单独的房间,再装饰的非常精美,除此之外,每个房间还会配备专人管理,最后起个洋气的名字,叫pod。

    然后,雇佣一大批的人,把小明以前的工作都细化分工下去,比如待在pod里,负责牛羊的管理,比如升级和回滚。然后每个大棚舍自治,牛羊的采购、参观等等独立化,这样管理起来更方便,同时如果一个大棚舍出现问题,也不会影响到别的大棚舍。

    接着站台也要优化一下,以前是固定的几个站台,大家都按序排队。现在不用那么麻烦了,因为大棚舍自治了,每个大棚舍单独售票,所以只需要安排几个迎宾,游客来了,问一下去哪个大棚舍,然后直接带过去就行了,大大减少了访客的等待时间。

    最后,由于规模相比之前不可同日而语,各个流程小明无法手动管理,于是小明又规划了一个叫流程的东西,想要干什么东西话,只需要按照流程走就对了。

    至此,所有问题都解决了,并且小明也解放了,每天只需要巡视工作就成了,小日子过得不要不要得。

    故事到此结束,现在解释一下文中的概念:

        1、小明:rancher的master节点 

        2、栅栏:rancher集群

        3、区域:集群

        4、大棚舍:命名空间

        5、小棚舍:项目

        6、pod:pod,k8s对容器的包装,负责容器的生命周期

        7、牛羊中心:docker hub镜像中心

        8、代理商:国内镜像如阿里云

        9、升级:镜像升级

        10、回滚:镜像回滚

        11、站台:负载均衡(nginx),以前会在固定的IP上,现在只要在集群的任何一台机器上即可,因为会有专门的“迎宾”处理

        12、为小明工作的人:k8s编排引擎

        13、流程:流水线(CI/CD)

五、场景实例

    有一个以JAVA编写的微服务,现在要部署上线。

5.1规划

    首先,环境分为本地环境(dev)、测试环境(test)、预发布环境(uat)、线上环境(live)。

    然后,根据业务划分命名空间,比如后台统一为service,手机客户端统一为app

    然后,根据业务划分项目,如用户管理的后台服务项目,则命名为user-manager

    然后,根据代码项目划分服务,比如认证服务是user-auth,登录是user-login

    然后,根据实际代码,配置负责均衡暴露服务,为外界提供接口

    同时,配备日志采集,可以统一查看各个项目的日志

5.2流水线(CI/CD)

    简单说下原理,Rancher按以下步骤运行:

        1、Rancher启动一个jenkins镜像,此镜像可以通过配置一个负载均衡来暴露出去访问后台界面,用户名是admin,密码是容器里的环境变量ADMIN_PASSWORD,默认是cgfh9ljx7dtx7s2vmqf7r9xcf6zj45s5lxcwg95zmtqz9n58mg84pc,如果启动流水线报错,登录jenkins,进去系统设置->全局安全设置,找到“防止跨站点请求伪造”,确定勾选,然后点击保存(如果已勾选,那么勾选掉,保存,再编辑,勾选,保存),再重新启动流水线即可。

        2、将流水线任务生成groovy脚本,然后在jenkins上创建任务并执行。

        3、流水线的每一个阶段对应一个镜像,Rancher会启动对应的容器,执行流水线配置的流程。

    一个典型的jenkins流水线脚本,类似如下:

代码语言:javascript
复制
import org.jenkinsci.plugins.pipeline.modeldefinition.Utils
def label = "buildpod.${env.JOB_NAME}.${env.BUILD_NUMBER}".replace('-', '_').replace('/', '_')
podTemplate(label: label, namespace: 'p-8j2pf-pipeline', instanceCap: 1, serviceAccount: 'jenkins',volumes: [emptyDirVolume(mountPath: '/var/lib/docker', memory: false), secretVolume(mountPath: '/etc/docker/certs.d/docker-registry.p-8j2pf-pipeline', secretName: 'registry-crt')], containers: [
containerTemplate(name: 'step-0-0', image: 'rancher/pipeline-tools:v0.1.0', ttyEnabled: true, command: 'cat' , envVars: [
    envVar(key: 'CICD_GIT_REF', value: 'refs/heads/master'),envVar(key: 'CICD_GIT_BRANCH', value: 'master'),envVar(key: 'CICD_PIPELINE_ID', value: 'p-dd58c'),envVar(key: 'CICD_CLUSTER_ID', value: 'c-gb2hf'),envVar(key: 'CICD_LOCAL_REGISTRY', value: '127.0.0.1:34350'),envVar(key: 'CICD_GIT_COMMIT', value: '6795394'),envVar(key: 'CICD_GIT_URL', value: 'http://git.lumiai.top/york/hyperloop-baseapi.git'),envVar(key: 'CICD_TRIGGER_TYPE', value: 'user'),envVar(key: 'CICD_EVENT', value: ''),envVar(key: 'CICD_EXECUTION_ID', value: 'p-dd58c-27'),envVar(key: 'CICD_EXECUTION_SEQUENCE', value: '27'),envVar(key: 'CICD_PROJECT_ID', value: 'p-8j2pf'),envVar(key: 'CICD_GIT_REPO_NAME', value: 'hyperloop-baseapi'),
]),containerTemplate(name: 'step-1-0', image: 'maven:3.6.0-jdk-8-alpine', ttyEnabled: true, command: 'cat' , envVars: [
    envVar(key: 'CICD_GIT_COMMIT', value: '6795394'),envVar(key: 'CICD_GIT_REPO_NAME', value: 'hyperloop-baseapi'),envVar(key: 'CICD_GIT_REF', value: 'refs/heads/master'),envVar(key: 'CICD_GIT_URL', value: 'http://git.lumiai.top/york/hyperloop-baseapi.git'),envVar(key: 'CICD_PIPELINE_ID', value: 'p-dd58c'),envVar(key: 'CICD_EVENT', value: ''),envVar(key: 'CICD_CLUSTER_ID', value: 'c-gb2hf'),envVar(key: 'CICD_GIT_BRANCH', value: 'master'),envVar(key: 'CICD_TRIGGER_TYPE', value: 'user'),envVar(key: 'CICD_EXECUTION_ID', value: 'p-dd58c-27'),envVar(key: 'CICD_EXECUTION_SEQUENCE', value: '27'),envVar(key: 'CICD_PROJECT_ID', value: 'p-8j2pf'),envVar(key: 'CICD_LOCAL_REGISTRY', value: '127.0.0.1:34350'),
]),containerTemplate(name: 'step-2-0', image: 'rancher/jenkins-plugins-docker:17.12', ttyEnabled: true, command: 'cat' , privileged: true, envVars: [
    envVar(key: 'CICD_GIT_REF', value: 'refs/heads/master'),envVar(key: 'CICD_PIPELINE_ID', value: 'p-dd58c'),envVar(key: 'CICD_EXECUTION_ID', value: 'p-dd58c-27'),envVar(key: 'CICD_EXECUTION_SEQUENCE', value: '27'),envVar(key: 'CICD_PROJECT_ID', value: 'p-8j2pf'),envVar(key: 'CICD_CLUSTER_ID', value: 'c-gb2hf'),envVar(key: 'CICD_LOCAL_REGISTRY', value: '127.0.0.1:34350'),envVar(key: 'CICD_GIT_COMMIT', value: '6795394'),envVar(key: 'CICD_GIT_REPO_NAME', value: 'hyperloop-baseapi'),envVar(key: 'CICD_GIT_BRANCH', value: 'master'),envVar(key: 'CICD_GIT_URL', value: 'http://git.lumiai.top/york/hyperloop-baseapi.git'),envVar(key: 'CICD_TRIGGER_TYPE', value: 'user'),envVar(key: 'CICD_EVENT', value: ''),envVar(key: 'PLUGIN_DOCKERFILE', value: './Dockerfile'),envVar(key: 'PLUGIN_CONTEXT', value: '.'),envVar(key: 'DOCKER_REGISTRY', value: '127.0.0.1:34350'),envVar(key: 'PLUGIN_REPO', value: '127.0.0.1:34350/scc/hyperloop/baseapi'),envVar(key: 'PLUGIN_TAG', value: 'dev'),secretEnvVar(key: 'DOCKER_USERNAME', secretName: 'p-8j2pf-12700134350', secretKey: 'username'),secretEnvVar(key: 'DOCKER_PASSWORD', secretName: 'p-8j2pf-12700134350', secretKey: 'password'),
]),
containerTemplate(name: 'jnlp', image: 'rancher/jenkins-jnlp-slave:3.10-1-alpine', envVars: [
envVar(key: 'JENKINS_URL', value: 'http://jenkins:8080')], args: '${computer.jnlpmac} ${computer.name}', ttyEnabled: false)], yaml: """
apiVersion: v1
kind: Pod
metadata:
  labels:
    app: jenkins
    execution: p-dd58c-27
spec:
  affinity:
    podAntiAffinity:
      preferredDuringSchedulingIgnoredDuringExecution:
      - weight: 100
        podAffinityTerm:
          labelSelector:
            matchExpressions:
            - key: app
              operator: In
              values:
              - jenkins
          topologyKey: kubernetes.io/hostname
"""
) {
node(label) {
timestamps {
timeout(60) {
stage('Clone'){

parallel 'step-0-0': {
  stage('step-0-0'){
    container(name: 'step-0-0') {
      checkout([$class: 'GitSCM', branches: [[name: 'local/temp']], userRemoteConfigs: [[url: 'http://git.lumiai.top/york/hyperloop-baseapi.git', refspec: '+refs/heads/master:refs/remotes/local/temp', credentialsId: 'p-dd58c-27']]])
    }
  }
}
}

stage('打包'){

parallel 'step-1-0': {
  stage('step-1-0'){
    container(name: 'step-1-0') {
      sh ''' 
echo "haha">baseapi.jar '''
    }
  }
}
}

stage('发布ƒ'){

parallel 'step-2-0': {
  stage('step-2-0'){
    container(name: 'step-2-0') {
      sh '''/usr/local/bin/dockerd-entrypoint.sh /bin/drone-docker'''
    }
  }
}
}


}
}
}
}

    好了,说完原理,下面实操。

    进入到Rancher管理平台,依次进入dev(集群)->service(命名空间),然后点击流水线。   

5.2.1源码管理

    源码管理使用本地Gitlab,代码语言是Java,使用maven构建,提供REST风格的API接口。

    目前Rancher只支持接入单个代码库,不支持多代码库同时接入。打开Gitlab,点击个人设置->应用,然后配置应用信息,拿到应用ID和应用密钥,最后回到Rancher输入gitlab地址、应用ID和应用密钥即可接入。

5.2.3源码打包

    启用任意代码项目后,流水线首页就会出现对应的数据,点击编辑。

    编辑页面,可操作的东西不多,但很简明易懂。

    第一步克隆代码,这一步是默认的也是必须和无法编辑的。

    点击添加阶段,输入阶段名,如“打包”,点击完成

    点击添加步骤,步骤类型分三类,一类是运行脚本,一类是构建并发布镜像,最后一类是部署YAML,每一个阶段可以添加很多步骤。这里点击运行脚本,然后在下面镜像那里输入maven:3.6.0-jdk-8-alpine,输入完成后会出现提示框maven:3.6.0-jdk-8-alpine (Custom),鼠标点击即可,最后在脚本那里输入mvn clean package。

5.2.4镜像发布

    打包完成后,再创建一个阶段,叫“镜像发布”,再点击添加步骤。

    步骤类型是“构建并发布镜像”,下面Dockerfile路径指的是代码中基于项目根路径的Dockerfile路径,镜像名称注意不用写镜像私服地址,但要带有仓库中对应项目名,比如harbor中我有一个项目叫shy,那么这里应该输入shy/xxx:xxx,再勾选下面的“推送镜像到远端镜像仓库”,选择对应的镜像库即可。

     特别需要注意的是,这一步会启动一个叫rancher/jenkins-plugins-docker:17.12的镜像,这个镜像会使用默认的https推送镜像,如果使用了Harbor,但是自签证书,那么这一步永远过不去,必须是合法的CA证书。或者使用阿里云的镜像私服,那个CA证书肯定得合法的。

5.2.5上线部署

    镜像发布后,在创建一个阶段,叫“上线部署”,再点击添加步骤。

    步骤类型是“部署YAML”,下面YAML路径同样指的是代码中基于项目根路径的YAML路径。然后点击添加, 在流水线配置的右下角有个“显示高级选项”,打开他,配置触发规则。也可不配置,每次手动执行。

    最后点击完成,即创建完一个完整的流水线。

5.3日志采集

    一个服务不可能只有1个实例,多实例就导致日志的排查比较困难,因为不知道访问落到了哪个实例上,所以一个集中式的日志中心是很有必要的。rancher针对每一个命名空间都提供了一个专门的日志采集接口,只需要配置日志输出即可。

    打开所有的应用商店,搜索efk,然后点击安装。

    接着,命名空间视图下,点击资源->日志,选择Elasticsearch,输入刚刚创建的es的地址,确定索引前缀,保存即可。指的注意的是,这里的日志粒度还是有点粗的,只到项目这一层级,实际使用的时候,可以多建项目,每个项目一类服务的方式,规避粒度粗的问题。

5.4负载均衡

    1.x的Rancher,事先是不知道实际的IP地址的,每次都是先配置负载均衡,拿到IP再配置DNS解析。

    2.x的Rancher,不用事先知道具体的IP了,访问集群内的任何一台机器即可,并且再也不用担心80端口不够用的情况。但由于这个版本放弃了HA,采用的nginx,并且不支持自定义配置,导致目前只支持L7层的负载均衡。

5.5机器扩容

    Rancher的扩容非常容易,按照第三章的前7条执行,然后将此时的镜像打包成系统镜像,以后直接拿这个镜像安装系统。安装完成后,直接在Rancher界面上添加主机,即可实现扩容,另外2.x的版本新主机的管理不需要手动进行,k8s会主动进行管理。

六、最佳实践

    这里说的我们线上集群的情况,并进行了一定得推测。另外,docker最佳搭档就是所有无状态的服务,Rancher同理也最适合无状态的服务,对于有状态的,如mysql,最好不要丢到rancher或者说docker上运行,不稳定是其次,数据丢失可怕了。

6.1机器配置

    物理机很重要,他是载体,决定了容器的情况。

    CPU:最低单U8核,越多越好,看具体情况。

    内存:32G是最低了,再少跑不了多少容器,我们是64G。

    硬盘:机械盘RAID5跑不了(这玩意读取性能不高为啥用他?因为生产中硬盘坏了很常见啊,呵呵),当然最好的还是固态,但那玩意成本太高。

    网卡:千兆的应该是标配了吧

6.2节点数量

    1.x受限于cattle的编排能力,节点数最好保持在20台左右,容器总量500以下,多了cattle就处理不过来了。

    2.x对节点数量没限制,但是节点的类型需要注意下:

        worker:是工作节点,不限数量,我们是除rancher本身外,其它都是worker

        control:集群控制节点,负责每个pod的控制,我们是设置了总机器数量的数量

        etcd:k-v存储,数量必须是奇数,我们是设置了总机器数量的1/3

    也就是说每3台机器,有一台的类型是worker和control以及etcd,其它两台是worker和control。

6.3HA

    Rancher:主节点必须是高可用的,我们是3个主节点,使用mysql存储数据,中间用mycat代理。

    Mysql:跑在物理机上,1主2从。

6.4安全

    虽然Rancher是一个密闭的集群,但宿主机被黑,跑在这上面的容器也会遭殃。但如果物理机如果开启了防火墙,却又会导致一些莫名的错误,这时该怎么办呢?

    如果有自己的机房和机器,解决方案是:

        1、关闭所有主机的防火墙,同时断开一切与外网的连接,相当于一个密闭的局域网

        2、将F5架设在局域网的前端,外网可以访问F5,内网也可以访问F5,但外网访问不了内网。然后再将F5打造成一个堡垒机,最后所有请求通过F5转发的对应的服务上。

    如果是云服务器,购买机器,不买外网IP,通过云提供商的负载均衡访问所购买的机器,这种和上面是一模一样的。

    最后说下登录认证,企业一般使用ldap,或者直接数据库密码存储。但推荐ldap,企业里是非常方便的。

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 一、前言
  • 二、先决
  • 三、准备
  • 四、概念说明
    • 4.1白手起家的农场主(1.x)
      • 4.2高速发展的农场(2.x)
      • 五、场景实例
        • 5.1规划
          • 5.2流水线(CI/CD)
            • 5.2.1源码管理
            • 5.2.3源码打包
            • 5.2.4镜像发布
            • 5.2.5上线部署
          • 5.3日志采集
            • 5.4负载均衡
              • 5.5机器扩容
              • 六、最佳实践
                • 6.1机器配置
                  • 6.2节点数量
                    • 6.3HA
                      • 6.4安全
                      相关产品与服务
                      负载均衡
                      负载均衡(Cloud Load Balancer,CLB)提供安全快捷的流量分发服务,访问流量经由 CLB 可以自动分配到云中的多台后端服务器上,扩展系统的服务能力并消除单点故障。负载均衡支持亿级连接和千万级并发,可轻松应对大流量访问,满足业务需求。
                      领券
                      问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档