kubeedge keadm join命令逻辑详解,keadm-join-v1.10.0

puml格式,装plant uml查看

@startuml keadm-join-v1.10.0
' Author: xiaoyang.chen
' mail: xiaoyang.chen@???.com

start
: keadm join args (基于v1.10.0);
note left
args: 
kubeedge-version, kubeedge的版本
cgroupdriver, cgroup驱动器, 默认"cgroupfs"
certPath, 证书文件路径, 默认"/etc/kubeedge/certs"
cloudcore-ipport, KubeEdge CloudCore的ip:port, 必填
runtimetype, 容器运行时类型, 默认"docker" 
edgenode-name, 边缘节点的唯一字符串标识, 如果没有设置, 
    系统将产生一个唯一的字符串给边缘节点(取系统hostname), 如果产生失败, 将使用默认"default-edge-node"
remote-runtime-endpoint, 边缘节点的容器运行时节点的端点, 
    默认unix:///var/run/dockershim.sock
token, 用于申请证书, 默认""
certport, 用于申请证书的端口, 默认10002
tarballpath, kubeedge二进制安装包tar包的路径,
    tar包的目录层次参照github的kubeedge仓库, 默认KubeEdgePath = "/etc/kubeedge/"
labels, 用于设置节点的定制化标签, 格式 key1=value1,key2=value2, 默认为空
with-mqtt, 使用这个设置是否默认安装和开启 MQTT Broker, **该字段尚未启用**

example: 
keadm join 
--cloudcore-ipport=101.33.227.236:10000 
--token=xxx 
--kubeedge-version 1.10.0
end note

: 解析keadm join args的args, AddToolsVals;
partition "添加部署工具信息\n (func Add2ToolsList(\n toolList map[string]types.ToolsInstaller, \n flagData map[string]types.FlagData, \n joinOptions *types.JoinOptions \n) error)" {

    :var kubeVer string;
    if (参数"kubeedge-version"存在) then (yes)
        :kubeVar = val of args kubeedge-version;
    endif
    if (kubeVer == "") then (yes)
        :var latestVersion string;
        while (i := 0; i < util.RetryTimes(默认 5); i++)
            :通过 https://kubeedge.io/latestversion 
            获取最新的版本信息;
            if (获取最新版本的err, err != nil) then (yes)
                :打印错误信息;
            else (no)
                if (获取到的版本号字符串长度大于0) then (yes)
                    :版本号剪除前缀"v", v1.10.0=>1.10.0 
                    并赋值给 kubeVar;
                    :latestVersion = 版本号(未剪除"v");
                    break
                endif
            endif
        endwhile
        if (len(latestVersion) == 0) then (yes)
            :kubeVer = types.DefaultKubeEdgeVersion (1.10.0);
            :打印错误信息;
        endif
    endif
    :common := util.Common{...} (携带kubeedge版本号(解析 kubeVar));
    :toolList["KubeEdge"] = &util.KubeEdgeInstTool{common, ...} \n (携带其他多个信息(args: cgroupdriver, certPath, cloudcore-ipport, \n runtimetype, edgenode-name, remote-runtime-endpoint, \n token, certport, tarballpath, labels));
    :toolList["MQTT"] = &util.MQTTInstTool{};
    :return nil;
}
if (err from Add2ToolsList, err != nil) then (yes)
    :return err;
    end
endif

partition "根据部署工具信息安装\n (func Execute(toolList map[string]types.ToolsInstaller) error)" {

    while (name, tool := range toolList)
        if (name != "KubeEdge") then (yes)
            :安装对应的模块(err := tool.InstallTools());
            if (err != nil) then (yes)
                :return err;
                end
            endif
        endif
    endwhile
    :return toolList["KubeEdge"].InstallTools();
}
end

:toolList["MQTT"].InstallTools();
partition "func (m *MQTTInstTool) InstallTools() error" {

    :根据包管理工具类型设置部署工具的系统接口参数 
    m.SetOSInterface(GetOSInterface());
    switch (包管理工具类型)
    case ("apt")
      :设置为DebOS;
    case ("yum") 
      :设置为RpmOS;
    case ("pacman")
      :设置为PacmanOS;
    case (default)
      :打印错误信息;
      :panic("...package manager...");
      end
    endswitch
    :根据不同的包管理工具安装mosquitto(
        DebOS用apt-get func (d *DebOS) InstallMQTT() error, 
        RpmOS用yum安装用systemctl启动 func (r *RpmOS) InstallMQTT() error, 
        PacmanOS用pacman安装 func (o *PacmanOS) InstallMQTT() error);
    :return nil;
}
end

:toolList["KubeEdge"].InstallTools();
partition "func (ku *KubeEdgeInstTool) InstallTools() error" {

    :根据包管理工具类型设置部署工具的系统接口参数 
    ku.SetOSInterface(GetOSInterface());
    switch (包管理工具类型)
    case ("apt")
      :设置为DebOS;
    case ("yum") 
      :设置为RpmOS;
    case ("pacman")
      :设置为PacmanOS;
    case (default)
      :打印错误信息;
      :panic("...package manager...");
      end
    endswitch
    :根据二进制文件名称"edgecore"判断edgeCore是否在运行, (edgeCoreRunning, err);
    if (err != nil) then (yes)
        :return err;
        end
    endif
    if (edgeCoreRunning) then (yes)
        :return fmt.Errorf(\n "EdgeCore is already running on this node, \n please run reset to clean up first" \n);
        end
    endif
    :设置kubeedge安装工具的kubeedge版本;
    :设置安装工具的安装选项
    TarballPath(args tarballpath)
    ComponentType(types.EdgeCore, 默认"edgecore");
    partition "根据安装选项使用kubeedge安装工具安装edgecore, \n func installKubeEdge(options types.InstallOptions, arch string, version semver.Version) error" {
        :二进制安装包tar.gz的文件名为
        fmt.Sprintf("kubeedge-v%s-linux-%s.tar.gz", version, arch), 具体见kubeedge仓库的tar.gz文件的命名;
        :二进制安装包tar.gz的文件的CheckSum文件名为
        fmt.Sprintf("checksum_kubeedge-v%s-linux-%s.tar.gz.txt", version, arch);
        :判断二进制安装包tar.gz是否存在,
        不存在则从github kubeedge仓库的release tag
        中下载对应的tar.gz包和对应的checksum文件用于SHA512验证,
        默认的下载尝试次数为3;
        partition 下载service文件 {
            if (HasSystemd()) then (yes)
                :var ServiceFileName string;
                switch (安装的组件类型)
                case ("cloudcore")
                    :ServiceFileName="cloudcore.service";
                case ("edgecore")
                    :ServiceFileName="edgecore.service";
                case (default)
                    :return fmt.Errorf("component type %s not support", componentType);
                    end
                endswitch
                :service文件存放路径为"/etc/kubeedge/"+"/"+ServiceFileName;
                :如果没有找到service文件, 
                则从github kubeedge仓库的release tag中下载对应的service文件,
                默认的下载尝试次数为5;
            endif
        }
        if (options.ComponentType == types.CloudCore) then (yes)
            :解压tar.gz并将解压后放在cloud/cloudcore下的"cloudcore"文件复制到/usr/local/bin;
        elseif (options.ComponentType == types.EdgeCore) then (yes)
            :解压tar.gz并将解压后放在edge下的"edgecore"文件复制到/usr/local/bin;
        endif
    }
    :检查配置文件目录"/etc/kubeedge/config/"是否存在, 不存在则创建并设置511权限;
    #Red:生成edgecore的默认配置,
    **edgeCoreConfig := v1alpha1.NewDefaultEdgeCoreConfig()**;
    :edgeCoreConfig.Modules.EdgeHub.WebSocket.Server = ku.CloudCoreIP 
    (args cloudcore-ipport);
    if (ku.EdgeNodeName != "", args edgenode-name) then (yes)
        :edgeCoreConfig.Modules.Edged.HostnameOverride = ku.EdgeNodeName;
    endif
    if (ku.RuntimeType != "", args runtimetype) then (yes)
        :edgeCoreConfig.Modules.Edged.RuntimeType = ku.RuntimeType;
    endif
    if (ku.CGroupDriver != "", args cgroupdriver) then (yes)
        switch (ku.CGroupDriver)
        case (v1alpha1.CGroupDriverSystemd, "systemd")
            :edgeCoreConfig.Modules.Edged.CGroupDriver = 
                v1alpha1.CGroupDriverSystemd;
        case (v1alpha1.CGroupDriverCGroupFS, "cgroupfs")
            :edgeCoreConfig.Modules.Edged.CGroupDriver = 
                v1alpha1.CGroupDriverCGroupFS;
        case (default)
            :return fmt.Errorf(
                "unsupported CGroupDriver: %s", ku.CGroupDriver);
            end
        endswitch
    endif 
    if (ku.RemoteRuntimeEndpoint != "", args remote-runtime-endpoint) then (yes)
        :edgeCoreConfig.Modules.Edged.RemoteRuntimeEndpoint = ku.RemoteRuntimeEndpoint
		edgeCoreConfig.Modules.Edged.RemoteImageEndpoint = ku.RemoteRuntimeEndpoint;
    endif
    if (ku.Token != "", args token) then (yes)
        :edgeCoreConfig.Modules.EdgeHub.Token = ku.Token;
    endif
    :获取args cloudcore-ipport 中的ip并赋值给cloudCoreIp;
    if (ku.CertPort != "", args certport) then (yes)
        :edgeCoreConfig.Modules.EdgeHub.HTTPServer = 
        "https://" + cloudCoreIP + ":" + ku.CertPort;
    else (no)
        :edgeCoreConfig.Modules.EdgeHub.HTTPServer = 
        "https://" + cloudCoreIP + ":10002";
    endif
    :edgeCoreConfig.Modules.EdgeStream.TunnelServer = 
    net.JoinHostPort(cloudCoreIP, strconv.Itoa(constants.DefaultTunnelPort)), 
    constants.DefaultTunnelPort 10004;
    if (len(ku.Labels) >= 1, args labels) then (yes)
        :labelsMap := make(map[string]string);
        while (_, label := range ku.Labels)
            :label是key=value的格式, 
            解析并获取lable中的key和value;
            :labelsMap[key] = value;
        endwhile
        :edgeCoreConfig.Modules.Edged.Labels = labelsMap;
    endif
    :对edgecore配置进行验证, 
    errs := validation.ValidateEdgeCoreConfiguration(edgeCoreConfig);
    if (len(errs) > 0) then (yes)
        :return errors.New(
            util.SpliceErrors(errs.ToAggregate().Errors()));
        end
    endif
    :将edgeCoreConfig的内容写入"/etc/kubeedge/config/edgecore.yaml";
    partition 启动edgecore进程 {
        :检查日志目录"/var/log/kubeedge/"是否存在, 不存在则创建并设置511权限;
        :systemdExist := HasSystemd();
        if (systemdExist) then (yes)
            :执行命令"sudo ln /etc/kubeedge/%s.service /etc/systemd/system/%s.service && 
            sudo systemctl daemon-reload && sudo systemctl enable %s && \n sudo systemctl start %s", %s为"edgecore";
            :fmt.Printf("KubeEdge edgecore is running, 
            For logs visit: journalctl -u %s.service -xe\n", "edgecore");
        else (no)
            :执行命令"/usr/local/bin/edgecore > /etc/kubeedge/kubeedge/edge/edgecore.log 2>&1 &";
            :fmt.Println(""KubeEdge edgecore is running, For logs visit:"", 
            /var/log/kubeedge/edgecore.log);
        endif
    }
    :return nil;
}
end

@enduml

版权声明:本文为sky527759原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。