名称 最后更新
conf 正在载入提交数据...
controllers 正在载入提交数据...
internal/repository 正在载入提交数据...
models 正在载入提交数据...
protocol 正在载入提交数据...
routers 正在载入提交数据...
services 正在载入提交数据...
static/js 正在载入提交数据...
tests 正在载入提交数据...
views 正在载入提交数据...
.gitignore 正在载入提交数据...
Dockerfile 正在载入提交数据...
README.md 正在载入提交数据...
docker-compose.yaml 正在载入提交数据...
go.mod 正在载入提交数据...
go.sum 正在载入提交数据...
main.go 正在载入提交数据...
rollback.sh 正在载入提交数据...
run.sh 正在载入提交数据...
start.sh 正在载入提交数据...
stop.sh 正在载入提交数据...

目录

代码声明

命名规范

1.包名

*
package名和目录保持一致,需避免和标准库冲突
小写
*
package comm

2.命名

package pkg

*1.错误*
/*
定义在包的首部,所有错误都定义在一起,
并且以Err开头
*/
var ErrFooBar = fmt.Errorf("pkg: ...")

*2.变量*
/*
采用驼峰命名
*/
var fooBar int

*3.常量*
/*
大写+下划线
*/
var(
    FOO = 1
    BAR = 2
    FOO_BAR = 3
)

*4.结构*
/*
采用驼峰命名法
*/
type FooBar struct{
    foo int
    Bar string
}


*5.方法接口*
/*
采用驼峰命名法
非对外方法,首字母需为小写
*/
func foo(){}
func Foo(){}

3.目录结构

* conf          //配置
  * dev.conf
  * prod.conf
* controller    //控制器
  * v1
    * auth.go
* internal
  * repository  //存储层
    * user.go
    * *_mock.go
* model         //模型
* protocol      //协议层
* routers       //路由
* service       //逻辑层
  * auth
* static        //静态数据
* views         //视图

* main.go   
* Dockerfile
* README.md
* *.sh         //脚本

项目约定

  1. 入参跟返回值都要定义一个协议结构 protocol.XxxRequest *protocol.XxxResponse,方便扩展
  2. 函数方法的变量都定义在函数的头几行 var( ... )
  3. 服务调用尽量封装成接口,方便测试扩展 比如:ISmsServe{ Send() error }
  4. 公用的基础代码库,需要做一下封装放在 gocomm ,方便在其他项目中调用
  5. 可以使用代码生成固定格式, 项目地址 脚本:.\gencode.exe new -c Auth -m Login
package  pkg
//Login
func(this *AuthController)Login(){
    var msg *mybeego.Message
    defer func(){
        this.Resp(msg)
    }()
    var request *protocol.LoginRequest
    if err:=json.Unmarshal(this.ByteBody,&request);err!=nil{
        log.Error(err)
        msg = mybeego.NewMessage(1)
        return
    }
    if b,m :=this.Valid(request);!b{
        msg = m
        return
    }
    msg = this.GenMessage(auth.Login(request))
}

/*Login */
type LoginRequest struct {
    Xxx string`json:"xxx" valid:"Required"`
}
type LoginResponse struct {
}

func Login(request *protocol.LoginRequest)(rsp *protocol.LoginResponse,err error){
    var (

    )
    rsp =&protocol.LoginResponse{}
    return
}

注意事项

  1. 启动一个groutine(eg:go func(){}()),需要在函数内进行recover,不然groutine里面panic,会导致外部程序一起崩溃掉;
  2. 当接受者是map, chan, func, 不要使用指针传递,因为它们本身就是引用类型
  3. 当接受者类型是一个结构体并且很庞大,或者是一个大数组,建议使用指针传递来提高性能,其他场景使用值传递即可
  4. 当接受者是一个结构体,并且包含了sync.Mutex或者类似的用于同步的成员。必须使用指针传递,避免成员拷贝
  5. 当函数内部需要修改接受者,必须使用指针传递
  6. 声明空的slice应该使用下面的格式: var t []string 不要使用 t := []string{} ,前者声明了一个nil slice而后者是一个长度为0的非nil的slice。