In this paper we discuss the use of coding specification in Go language

  • 2020-10-23 20:59:44
  • OfStack

Every language has its own code specifications, and learning the naming conventions of that language will make your code easier to read and less prone to low-level mistakes.

According to personal coding habits and some articles on the Internet, this paper has sorted out some coding specifications that you can use. It may be some mainstream solutions, but it does not represent the official. This point is first stated in 1.

1. File naming

Since Windows platform file names are not case sensitive, file names should be in lowercase

Use underlined words between different words. Do not use humped names

If it is a test file, you can end it with _test.go

If the file has platform characteristics, it should be named after the filename _ platform.go, such as utils_ windows.go, utils_linux.go. The available platforms are: windows, unix, posix, plan9, darwin, bsd, linux, freebsd, nacl, netbsd, openbsd, dragonfly, bsd, notbsd, android, stubs

1 In general, the main entrance to the application should be main.go, or named after the application's all lowercase form. For example, the entrance to MyBlog can be myblog.go

2. Constant naming

There are two main styles of writing that you can see on the Internet

The first is the hump naming, such as appVersion

The second USES all caps and underscores with participle, such as APP_VERSION

These two styles are not superior to each other, but they are free to choose. Personally, I prefer to use the second style, which can be distinguished from variables.

If you want to define multiple variables, organize them using parentheses.


const (
  APP_VERSION = "0.1.0"
 CONF_PATH = "/etc/xx.conf"
)

3. Variable naming

Unlike constants, variable naming gives developers a preference over 1, which USES the hump naming method

In relatively simple environments (with a small number of objects and strong pertinence), complete words can be shortened to a single letter. For example, user can be shortened to u If the variable is of type bool, the name should start with Has, Is, Can, or Allow. For example: isExist, hasConflict. In other cases, the first word is all lowercase, followed by the first letter of each word is uppercase. For example: numShips and startDate. If the variable has a unique noun (listed below) and the variable is private, the first word is still all lowercase, such as apiClient. If the variable has a unique noun (listed below) but the variable is not private, the first word is capitalized. For example: APIClient, URLString

Here is a list of 1 common specific nouns:


// A GonicMapper that contains a list of common initialisms taken from golang/lint
var LintGonicMapper = GonicMapper{
  "API":  true,
  "ASCII": true,
  "CPU":  true,
  "CSS":  true,
  "DNS":  true,
  "EOF":  true,
  "GUID": true,
  "HTML": true,
  "HTTP": true,
  "HTTPS": true,
  "ID":  true,
  "IP":  true,
  "JSON": true,
  "LHS":  true,
  "QPS":  true,
  "RAM":  true,
  "RHS":  true,
  "RPC":  true,
  "SLA":  true,
  "SMTP": true,
  "SSH":  true,
  "TLS":  true,
  "TTL":  true,
  "UI":  true,
  "UID":  true,
  "UUID": true,
  "URI":  true,
  "URL":  true,
  "UTF8": true,
  "VM":  true,
  "XML":  true,
  "XSRF": true,
  "XSS":  true,
}

4. Function naming

The function name will still use the hump naming One thing to note, however, is that in Golang the visibility of functions is controlled by case, so use uppercase when you need to access them from outside the package When you do not need access outside the package, start with a lowercase letter

In addition, there are several rules for ordering parameters within a function

The more important the parameter is, the more important it should be Simple types should take precedence over complex types If you place arguments of the same type next to each other, you only need to write the type once

5. Interface naming

Using the hump naming, type alias can be used to define out-of-package access to type starting with uppercase.


type helloWorld interface {
  func Hello();
}

type SayHello helloWorld

When your interface has only 1 function, the interface name is usually suffixes er


type Reader interface {
  Read(p []byte) (n int, err error)
}

5. Annotation specification

Annotations can be divided into

5.1 package comments

Prior to package, if there are multiple files in a package, you only need to write it in one file
If you want to put a comment at the head of each file, you need to put a blank line before the copyright comment and Package, otherwise the copyright comment will be a comment for Package.


// Copyright 2009 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package net

If it is a particularly complex package, you can create a separate doc.go file description

5.2 Code comments

There are two ways to interpret code logic

Single-line comments use // and multi-line comments use /* comment */


//  Single-line comments 

/*
 more 
 line 
 note 
 Interpretation of the 
*/

In addition, there are a few more stringent requirements for code comments, this is personal, from the web:

All exported objects need to be annotated for their purpose; Non-exported objects are annotated as appropriate.
If the object is countable and does not have an explicitly specified number, the law of 1 USES the singular form and the general continuous tense of 1; Otherwise use the plural form.
The package, function, method, and type annotation is a complete sentence.
The first letter of a sentence type should be capitalized. The first letter of a comment for a phrase type should be lowercase.
The single-line length of an annotation cannot exceed 80 characters.
Definitions of types 1 are generally described in the singular:


// Request represents a request to run a command. type Request struct { ...

If it is an interface, then 1 is generally described in the following form:


 // FileInfo is the interface that describes a file and is returned by Stat and Lstat.
 type FileInfo interface { ...

Comments for functions and methods begin with the name of the function or method:


// Post returns *BeegoHttpRequest with POST method.

If one sentence is not enough to explain the whole problem, a more detailed description can be carried out by wrapping the line:


 // Copy copies file from source to target path.
 // It returns false and error when error occurs in underlying function calls.

If the function or method is of a judgment type (the return value is mainly of type bool), then < name > returns true if


// A GonicMapper that contains a list of common initialisms taken from golang/lint
var LintGonicMapper = GonicMapper{
  "API":  true,
  "ASCII": true,
  "CPU":  true,
  "CSS":  true,
  "DNS":  true,
  "EOF":  true,
  "GUID": true,
  "HTML": true,
  "HTTP": true,
  "HTTPS": true,
  "ID":  true,
  "IP":  true,
  "JSON": true,
  "LHS":  true,
  "QPS":  true,
  "RAM":  true,
  "RHS":  true,
  "RPC":  true,
  "SLA":  true,
  "SMTP": true,
  "SSH":  true,
  "TLS":  true,
  "TTL":  true,
  "UI":  true,
  "UID":  true,
  "UUID": true,
  "URI":  true,
  "URL":  true,
  "UTF8": true,
  "VM":  true,
  "XML":  true,
  "XSRF": true,
  "XSS":  true,
}
0

5.3 Special Notes

TODO: Remind maintainers that this part of the code is to be completed FIXME: Remind maintenance staff that BUG is available for repair NOTE: A list of issues for maintenance personnel to focus on

6. Package import

A one-line package import


// A GonicMapper that contains a list of common initialisms taken from golang/lint
var LintGonicMapper = GonicMapper{
  "API":  true,
  "ASCII": true,
  "CPU":  true,
  "CSS":  true,
  "DNS":  true,
  "EOF":  true,
  "GUID": true,
  "HTML": true,
  "HTTP": true,
  "HTTPS": true,
  "ID":  true,
  "IP":  true,
  "JSON": true,
  "LHS":  true,
  "QPS":  true,
  "RAM":  true,
  "RHS":  true,
  "RPC":  true,
  "SLA":  true,
  "SMTP": true,
  "SSH":  true,
  "TLS":  true,
  "TTL":  true,
  "UI":  true,
  "UID":  true,
  "UUID": true,
  "URI":  true,
  "URL":  true,
  "UTF8": true,
  "VM":  true,
  "XML":  true,
  "XSRF": true,
  "XSS":  true,
}
1

Multiple package imports, organize them using {}


// A GonicMapper that contains a list of common initialisms taken from golang/lint
var LintGonicMapper = GonicMapper{
  "API":  true,
  "ASCII": true,
  "CPU":  true,
  "CSS":  true,
  "DNS":  true,
  "EOF":  true,
  "GUID": true,
  "HTML": true,
  "HTTP": true,
  "HTTPS": true,
  "ID":  true,
  "IP":  true,
  "JSON": true,
  "LHS":  true,
  "QPS":  true,
  "RAM":  true,
  "RHS":  true,
  "RPC":  true,
  "SLA":  true,
  "SMTP": true,
  "SSH":  true,
  "TLS":  true,
  "TTL":  true,
  "UI":  true,
  "UID":  true,
  "UUID": true,
  "URI":  true,
  "URL":  true,
  "UTF8": true,
  "VM":  true,
  "XML":  true,
  "XSRF": true,
  "XSS":  true,
}
2

There are also 1 set of requirements for layout, depending on the source of the package

The standard library comes first, followed by the third package, followed by other packages within the project and subpackages of the current package, with each category separated by a blank line.
Try not to import packages using relative paths.


import (
  "fmt"
  "html/template"
  "net/http"
  "os"
 
  "github.com/codegangsta/cli"
  "gopkg.in/macaron.v1"
 
  "github.com/gogits/git"
  "github.com/gogits/gfm"
 
  "github.com/gogits/gogs/routers"
  "github.com/gogits/gogs/routers/repo"
  "github.com/gogits/gogs/routers/user"
)

7. Use gofmt

In addition to the naming conventions, Go has many formatting conventions, such as

Use tab for indentation A line should not exceed 80 characters at most

Therefore, you can trust gofmt to help you adjust most of the format problems. The article on gofmt is still being written and should be updated in the next few days. You can come back in a couple of days.

Reference article:

Go language (Golang) coding specification


Related articles: