跳至主要內容

Golang项目规范

zhengcog...大约 7 分钟golanggolang

一 说明

1.1 编程规范统一,可避免陷于语言陷阱,有利于团队协作

1.2 统一目录组织结构,避免目录及文件名随意

1.3 ide配置保存代码自动gofmt,goimports

1.4 使用go mod管理第三包

1.5 tag键设置为4个字符

二 项目源码组织结构

项目源码组织结构参考以下,建议都按以下结构开新项目

.
├── README.md
├── cmd # 定义启动命令
│   ├── admin #运营后台接口
│   │   └── admin.go
│   ├── api #app/h5接口
│   │   └── api.go
│   └── cmd.go
├── conf #配置文件存放目录
│   ├── in-dev.yaml #开发环境配置
│   └── in-prod.yaml #生产环境配置
├── data #临时文件存放目录
│   └── logs #日志文件存放目录
├── docs #接口文档存放目录
│   ├── admin #运营后台接口文档
│   │   ├── docs.go
│   │   ├── swagger.json
│   │   └── swagger.yaml
│   └── api #app/h5接口文档
│       ├── docs.go
│       ├── swagger.json
│       └── swagger.yaml
├── internal #内部包
│   ├── admin #运营后台接口
│   │   ├── controller #控制器存放目录
│   │   │   └── base.go
│   │   └── router #路由
│   │       └── router.go
│   ├── api #app/h5接口
│   │   ├── controller #控制器存放目录
│   │   │   └── base.go
│   │   └── router #路由
│   │       └── router.go
│   └── common #公共目录
│       ├── dao #dao层,操作数据库
│       │   └── dao.go
│       ├── dto #dto层,定义传输对象,用于表单验证等
│       │   └── dto.go
│       ├── middleware #中间件
│       │   └── middleware.go
│       ├── model #model层,定义struct与数据库的映射关系
│       │   └── model.go
│       └── service #服务层,业务逻辑主要都写在这一层
│           └── service.go
├── main.go #入口文件
├── pkg #外部包,一些不依赖内部包(internal)的代码都存放在此
│   ├── cache #缓存包
│   │   └── cache.go
│   ├── logger #日志包
│   │   └── logger.go
│   └── utils #公共工具类函数包
│       ├── strings.go
│       └── utils.go
└── scripts #脚本存放目录
    ├── init.sh
    └── init.sql

三 代码规范

3.1 包

  • 全部使用小写,不用驼峰命名方式,不使用下划线、中划线,与外层目录名相同,尽量和标准库包名不要冲突
  • 命名要有意义,一看包名就能知道这个包的用途

举例:

// 符合规范
package files
package logger
//不符合规范
package testAbc
package test_abc
package os // 与标准包冲突
  • 一个目录只包含一个包,模块复杂拆分子模块/子目录
  • 禁止相对路径导入包

举例:

// 不符合规范
import ./pkg/logger
  • 建议goimports或者IDE管理import

3.2 文件

  • 全部使用小写,不用驼峰命名方式,多个单词可以使用下划线'_',首尾不能使用下划线
  • 命名要有意义,一看文件名就能知道这个文件的大概内容,不需要再出现包名。
  • 统一使用单数形式

举例:

//符合规范:
user_info.go
user_email.go
client.go
server.go
//不符合规范
_abc.go
abc_.go
111.go

3.3 变量

  • 全局变量,采用驼峰命名方式,当遇到特有名词(缩写或简称,如:DNS)的时候,特有名词根据是否私有全部大写或小写。

例子:apiClient、URLString

  • 局部变量,采用小驼峰命名方式,声明局部变量尽量使用 :=

3.4 常量

  • 同变量规则,力求语义表达完整清楚,不要嫌名字长。
  • 如果模块复杂,为避免混淆,可按功能统一定义在package下的一个文件中。
  • 不允许下划线,第三方包例外。

3.5 结构体

  • 声明使用驼峰命名方式,禁止使用下划线命名

举例:

// 符合规范
type UserService struct
}
// 不符合规范
type User_Service struct {
}
type user_service struct {
}
  • 结构体内字段使用驼峰式命名,禁止使用下划线命名,根据实际情况使用tag

例子:

type UserService struct{
  // 符合规范
  UserName string `json:"user_name"`
  // 不符合规范
  User_Name string `json:"user_name"`
}
  • 结构体使用名词或者动名词

3.6 接口interface

  • 命名使用驼峰式命名,首字母大写,禁止使用下划线
  • 接口名以'er'为后缀,如:Reader,Writer

举例:

//符合规范
type Reader interface{
  
}
type Writer interface{
  
}
//不符合规范
type Read interface{
  
}
type Write interface{
  
}
type Test_interface interface{
  
}

3.7 函数

  • 使用驼峰式命名,禁止使用下划线
  • 建议动词或者动宾结构单词
  • 参数使用驼峰式命名,首字母使用小写,禁止使用下划线
  • 参数按紧密程度安排位置,同类型参数应该相邻
  • 参数建议不大于5个

3.8 方法

  • 与函数名规则一致
  • 如果是结构体方法,那么 Receiver 的名称应该缩写,一般使用一个或者两个字符作为 Receiver 的名称。如果 Receiver 是指针, 那么统一使用p。 如
// 接收拷贝
func (f foo) method() {
  ...
}
// 接收指针
func (p *foo) method() {
  ...
}
  • 对于Receiver命名应该统一, 要么都使用值, 要么都用指针。

3.9 错误处理

  • 错误处理的原则就是不能丢弃任何有返回err的调用,不要使用 _ 丢弃,必须全部处理
  • 接收到错误,要么返回err,或者使用log记录下来,尽早return:一旦有错误发生,马上返回
  • 尽量不要使用panic,除非你知道你在做什么

举例:

// 错误写法
if err != nil {
} else {
    
}
// 正确写法
if err != nil {
    return 
}

3.10 注释规范

注释可以帮我们很好的完成文档的工作,写得好的注释可以方便我们以后的维护。和其他语言类似,go 语言也提供了 /**/ 的块注释和 // 的单行注释两种注释风格, 在我们的项目中为了风格的统一,全部使用单行注释。go 语言自带的 godoc 工具可以根据注释生成文档,生成可以自动生成对应的网站( golang.orgopen in new window 就是使用 godoc 工具直接生成的),注释的质量决定了生成的文档的质量。

四 Restful API路由设计标准

4.1 协议

api接口统一使用https协议

4.2 域名

使用独立的二级域名,不占用主域名

4.3 版本

在URL中放入版本号

4.4 路径

在RESTful架构中,每个网址代表一种资源(resource),所以网址中不能有动词,只能有名词,而且所用的名词往往与数据库的表格名对应。一般来说,数据库中的表都是同种记录的"集合"(collection),所以API中的名词也应该使用复数。

举例来说,有一个API提供动物园(zoo)的信息,还包括各种动物和雇员的信息,则它的路径应该设计成下面这样。

4.5 HTTP动词

常用的HTTP动词有下面五个(括号里是对应的SQL命令)。

  • GET(SELECT):从服务器取出资源(一项或多项)。
  • POST(CREATE):在服务器新建一个资源。
  • PUT(UPDATE):在服务器更新资源(客户端提供改变后的完整资源)。
  • PATCH(UPDATE):在服务器更新资源(客户端提供改变的属性)。
  • DELETE(DELETE):从服务器删除资源

DEMO:

  • GET /zoos:列出所有动物园
  • POST /zoos:新建一个动物园
  • GET /zoos/ID:获取某个指定动物园的信息
  • PUT /zoos/ID:更新某个指定动物园的信息(提供该动物园的全部信息)
  • PATCH /zoos/ID:更新某个指定动物园的信息(提供该动物园的部分信息)
  • DELETE /zoos/ID:删除某个动物园
  • GET /zoos/ID/animals:列出某个指定动物园的所有动物
  • DELETE /zoos/ID/animals/ID:删除某个指定动物园的指定动物

4.6 过滤信息

常见过滤参数

  • ?limit=10:指定返回记录的数量
  • ?offset=10:指定返回记录的开始位置。
  • ?page=2&per_page=100:指定第几页,以及每页的记录数。
  • ?sortby=name&order=asc:指定返回结果按照哪个属性排序,以及排序顺序。
  • ?animal_type_id=1:指定筛选条件

4.7 状态码

  • 200 OK - [GET]:服务器成功返回用户请求的数据,该操作是幂等的(Idempotent)。
  • 201 CREATED - [POST/PUT/PATCH]:用户新建或修改数据成功。
  • 202 Accepted - [*]:表示一个请求已经进入后台排队(异步任务)
  • 204 NO CONTENT - [DELETE]:用户删除数据成功。
  • 400 INVALID REQUEST - [POST/PUT/PATCH]:用户发出的请求有错误,服务器没有进行新建或修改数据的操作,该操作是幂等的。
  • 401 Unauthorized - [*]:表示用户没有权限(令牌、用户名、密码错误)。
  • 403 Forbidden - [*] 表示用户得到授权(与401错误相对),但是访问是被禁止的。
  • 404 NOT FOUND - [*]:用户发出的请求针对的是不存在的记录,服务器没有进行操作,该操作是幂等的。
  • 406 Not Acceptable - [GET]:用户请求的格式不可得(比如用户请求JSON格式,但是只有XML格式)。
  • 410 Gone -[GET]:用户请求的资源被永久删除,且不会再得到的。
  • 422 Unprocesable entity - [POST/PUT/PATCH] 当创建一个对象时,发生一个验证错误。
  • 500 INTERNAL SERVER ERROR - [*]:服务器发生错误,用户将无法判断发出的请求是否成功。
上次编辑于:
贡献者: Hyman
评论
  • 按正序
  • 按倒序
  • 按热度
Powered by Waline v2.15.5