• K8s源码风格及规范



    一、工程概述

    • 本项目主要基于Kubernetes集群开展,针对开源项目进行功能扩展。要求基于已有的Kubernetes集群和Prometheus 监控系统进行扩展开发。
    • K8s是由Google开发,并使用go语言进行开发的。

    二、源码准备

    1.系统环境:
    • 操作系统:我们使用Linux作为k8s源码分析和调试环境,fedora、centos、ubuntu都行,我这里使用fedora;
    • golang相关:
    GOROOT=/usr/local/lib/golang
    GOPATH=/root/go
    go version go1.10.3 linux/amd64
    
    2.源码下载
    mkdir -p /root/go/src/k8s.io
    cd /root/go/src/k8s.io/
    git clone https://github.com/kubernetes/kubernetes.git
    
    • 目录展示:

    • 主要目录:

    目录名 功能
    cmd 每个组件代码入口(main函数)
    pkg 各个组件的具体功能实现
    staging 已经分库的项目
    vendor 依赖
    3.IDE
    • 通过学校邮箱申请JetBrains的教育账号,通过Goland看代码:

    三、go语言特点及命名规范

    1.go语言特点

    GO语言的关键特性主要包括以下几方面:

    • 并发与协程
    • 基于消息传递的通信方式
    • 丰富实用的内置数据类型
    • 函数多返回值
    • defer机制
    • 反射(reflect)
    • 高性能HTTP Server
    • 工程管理
    • 编程规范
    2.相关规范
    • package名字
      保持package的名字和目录保持一致,尽量采取有意义的包名,简短,有意义,尽量和标准库不要冲突。

    • import 规范
      import在多行的情况下,自动工具会自动帮你格式化,但是我们这里还是规范一下import的一些规范,如果你在一个文件里面引入了一个package,还是建议采用如下格式:

    import (
        "fmt"
    )
    

    如果你的包引入了三种类型的包,标准库包,程序内部包,第三方包,建议采用如下方式进行组织你的包:

    import (
        "strings"
    
        "myproject/models"
        "myproject/controller"
    
        "github.com/mysql"
    )   
    

    有顺序的引入包,不同的类型采用空格分离,第一种实标准库,第二是项目包,第三是第三方包。在项目中不要使用相对路径引入包:

    // 这是不好的导入
    import “../pkg”
    
    // 这是正确的做法
    import “github.com/tx23/pkg”
    
    • 变量申明
      变量名采用驼峰标准,不要使用_来命名变量名,多个变量申明放在一起
      在函数外部申明必须使用var,不要采用:=,容易踩到变量的作用域的问题。
    var (
        Found bool
        count int
    )
    
    • 自定义类型的string循环问题
      如果自定义的类型定义了String方法,那么在打印的时候会产生隐藏的一些bug。
    type MyInt int
    func (m MyInt) String() string { 
        return fmt.Sprint(m)   //BUG:死循环
    }
    
    func(m MyInt) String() string { 
        return fmt.Sprint(int(m))   //这是安全的,因为我们内部进行了类型转换
    }
    
    • 避免返回命名的参数
      如果你的函数很短小,少于10行代码,那么可以使用,不然请直接使用类型,因为如果使用命名变量很容易引起隐藏的bug。
    func Foo(a int, b int) (string, ok){
    
    }
    

    当然如果是有多个相同类型的参数返回,那么命名参数可能更清晰。

    func (f *Foo) Location() (float64, float64, error)

    • 错误处理
      错误处理的原则就是不能丢弃任何有返回err的调用,不要采用_丢弃,必须全部处理。接收到错误,要么返回err,要么实在不行就panic,或者使用log记录下来,error的信息不要采用大写字母,尽量保持你的错误简短,但是要足够表达你的错误的意思。

    • 注意闭包的调用
      在循环中调用函数或者goroutine方法,一定要采用显示的变量调用,不要再闭包函数里面调用循环的参数

    fori:=0;i<limit;i++{
        go func(){ DoSomething(i) }() //错误的做法
        go func(i int){ DoSomething(i) }(i)//正确的做法
    }
    
    • 在逻辑处理中禁用panic
      在main包中只有当实在不可运行的情况采用panic,例如文件无法打开,数据库无法连接导致程序无法正常运行,但是对于其他的package对外的接口不能有panic,只能在包内采用。强烈建议在main包中使用log.Fatal来记录错误,这样就可以由log来结束程序。

    • struct规范
      struct申明和初始化格式采用多行:
      定义如下:

    type User struct{
        Username  string
        Email     string
    }
    

    初始化如下:

    u := User{
        Username: "astaxie",
        Email:    "astaxie@gmail.com",
    }
    
    • recieved是值类型还是指针类型
      到底是采用值类型还是指针类型主要参考如下原则:
    func(w Win) Tally(playerPlayer)int    //w不会有任何改变 
    func(w *Win) Tally(playerPlayer)int    //w会改变数据
    

    更多的请参考:
    https://code.google.com/p/go-wiki/wiki/CodeReviewComments#Receiver_Type

    • 带mutex的struct必须是指针receivers
      如果你定义的struct中带有mutex,那么你的receivers必须是指针

    参考资料:
    https://code.google.com/p/go-wiki/wiki/CodeReviewComments
    http://golang.org/doc/effective_go.html

  • 相关阅读:
    Vue数组循环
    vue使用swiper6分页器踩坑
    Vue基础语法(四)
    Vue安装jquery
    Vue基础语法(三)
    Too Rich(贪心加搜索)
    ZOJ Anagrams by Stack(堆栈中的搜索)
    最长子序列和(分治法实现)
    幸运数字(数位dp)
    蜥蜴和地下室(深搜)
  • 原文地址:https://www.cnblogs.com/tangxin2019/p/11615739.html
Copyright © 2020-2023  润新知