feat: move folder

This commit is contained in:
daniel.w 2024-08-08 00:01:58 +08:00
parent c65291893c
commit 1953246b44
10 changed files with 161 additions and 39 deletions

18
.gitignore vendored
View File

@ -1,2 +1,20 @@
.idea/ .idea/
go.sum go.sum
# Binaries for programs and plugins
*.exe
*.exe~
*.dll
*.so
*.dylib
# Test binary, built with `go test -c`
*.test
# Output of the go coverage tool, specifically when used with LiteIDE
*.out
# IDE config
.idea
.vscode
bench.txt

View File

@ -1,7 +1,7 @@
package error package error
import ( import (
"code.30cm.net/wanderland/library-go/pkg/errors/code" "code.30cm.net/wanderland/library-go/errors/code"
"errors" "errors"
"fmt" "fmt"
"strings" "strings"

View File

@ -1,7 +1,7 @@
package error package error
import ( import (
"code.30cm.net/wanderland/library-go/pkg/errors/code" "code.30cm.net/wanderland/library-go/errors/code"
"context" "context"
"errors" "errors"
"fmt" "fmt"

View File

@ -1,17 +1,17 @@
package error package error
import ( import (
code2 "code.30cm.net/wanderland/library-go/errors/code"
"errors" "errors"
"fmt" "fmt"
"net/http" "net/http"
"code.30cm.net/wanderland/library-go/pkg/errors/code"
"google.golang.org/grpc/codes" "google.golang.org/grpc/codes"
"google.golang.org/grpc/status" "google.golang.org/grpc/status"
) )
// Scope 全域變數應由服務或模組設置 // Scope 全域變數應由服務或模組設置
var Scope = code.Unset var Scope = code2.Unset
// Err 6 碼,服務 2, 大類 2, 詳細錯誤 2 // Err 6 碼,服務 2, 大類 2, 詳細錯誤 2
type Err struct { type Err struct {
@ -60,7 +60,7 @@ func (e *Err) Category() uint32 {
// Scope 私有屬性 "scope" 的 getter 函數 // Scope 私有屬性 "scope" 的 getter 函數
func (e *Err) Scope() uint32 { func (e *Err) Scope() uint32 {
if e == nil { if e == nil {
return code.Unset return code2.Unset
} }
return e.scope return e.scope
@ -72,7 +72,7 @@ func (e *Err) CodeStr() string {
return "00000" return "00000"
} }
if e.Category() == code.CatGRPC { if e.Category() == code2.CatGRPC {
return fmt.Sprintf("%d%04d", e.Scope(), e.Category()+e.Code()) return fmt.Sprintf("%d%04d", e.Scope(), e.Category()+e.Code())
} }
@ -82,7 +82,7 @@ func (e *Err) CodeStr() string {
// Code 私有屬性 "code" 的 getter 函數 // Code 私有屬性 "code" 的 getter 函數
func (e *Err) Code() uint32 { func (e *Err) Code() uint32 {
if e == nil { if e == nil {
return code.OK return code2.OK
} }
return e.code return e.code
@ -93,7 +93,7 @@ func (e *Err) FullCode() uint32 {
return 0 return 0
} }
if e.Category() == code.CatGRPC { if e.Category() == code2.CatGRPC {
return e.Scope()*10000 + e.Category() + e.Code() return e.Scope()*10000 + e.Category() + e.Code()
} }
@ -102,30 +102,30 @@ func (e *Err) FullCode() uint32 {
// HTTPStatus 返回對應的 HTTP 狀態碼 // HTTPStatus 返回對應的 HTTP 狀態碼
func (e *Err) HTTPStatus() int { func (e *Err) HTTPStatus() int {
if e == nil || e.Code() == code.OK { if e == nil || e.Code() == code2.OK {
return http.StatusOK return http.StatusOK
} }
// 根據 code 判斷狀態碼 // 根據 code 判斷狀態碼
switch e.Code() { switch e.Code() {
case code.ResourceInsufficient: case code2.ResourceInsufficient:
// 400 // 400
return http.StatusBadRequest return http.StatusBadRequest
case code.Unauthorized, code.InsufficientPermission: case code2.Unauthorized, code2.InsufficientPermission:
// 401 // 401
return http.StatusUnauthorized return http.StatusUnauthorized
case code.InsufficientQuota: case code2.InsufficientQuota:
// 402 // 402
return http.StatusPaymentRequired return http.StatusPaymentRequired
case code.InvalidPosixTime, code.Forbidden: case code2.InvalidPosixTime, code2.Forbidden:
// 403 // 403
return http.StatusForbidden return http.StatusForbidden
case code.ResourceNotFound: case code2.ResourceNotFound:
// 404 // 404
return http.StatusNotFound return http.StatusNotFound
case code.ResourceAlreadyExist, code.InvalidResourceState: case code2.ResourceAlreadyExist, code2.InvalidResourceState:
// 409 // 409
return http.StatusConflict return http.StatusConflict
case code.NotValidImplementation: case code2.NotValidImplementation:
// 501 // 501
return http.StatusNotImplemented return http.StatusNotImplemented
default: default:
@ -133,7 +133,7 @@ func (e *Err) HTTPStatus() int {
// 根據 category 判斷狀態碼 // 根據 category 判斷狀態碼
switch e.Category() { switch e.Category() {
case code.CatInput: case code2.CatInput:
return http.StatusBadRequest return http.StatusBadRequest
default: default:
// 如果沒有符合的條件,返回狀態碼 500 // 如果沒有符合的條件,返回狀態碼 500
@ -148,7 +148,7 @@ func (e *Err) GeneralError() string {
return "" return ""
} }
errStr, ok := code.CatToStr[e.Category()] errStr, ok := code2.CatToStr[e.Category()]
if !ok { if !ok {
return "" return ""
} }
@ -210,7 +210,7 @@ func NewErr(scope, category, detail uint32, msg string) *Err {
// NewGRPCErr 創建新的 gRPC Err // NewGRPCErr 創建新的 gRPC Err
func NewGRPCErr(scope, detail uint32, msg string) *Err { func NewGRPCErr(scope, detail uint32, msg string) *Err {
return &Err{ return &Err{
category: code.CatGRPC, category: code2.CatGRPC,
code: detail, code: detail,
scope: scope, scope: scope,
msg: msg, msg: msg,

View File

@ -1,7 +1,7 @@
package error package error
import ( import (
"code.30cm.net/wanderland/library-go/pkg/errors/code" code2 "code.30cm.net/wanderland/library-go/errors/code"
"errors" "errors"
"fmt" "fmt"
"net/http" "net/http"
@ -17,7 +17,7 @@ func TestCode_GivenNilReceiver_CodeReturnOK_CodeStrReturns00000(t *testing.T) {
var e *Err = nil var e *Err = nil
// act & assert // act & assert
assert.Equal(t, code.OK, e.Code()) assert.Equal(t, code2.OK, e.Code())
assert.Equal(t, "00000", e.CodeStr()) assert.Equal(t, "00000", e.CodeStr())
assert.Equal(t, "", e.Error()) assert.Equal(t, "", e.Error())
} }
@ -103,8 +103,8 @@ func TestGeneralError_GivenNotExistCat_ShouldReturnEmptyString(t *testing.T) {
func TestGeneralError_GivenCatDB_ShouldReturnDBError(t *testing.T) { func TestGeneralError_GivenCatDB_ShouldReturnDBError(t *testing.T) {
// setup // setup
e := Err{category: code.CatDB} e := Err{category: code2.CatDB}
catErrStr := code.CatToStr[code.CatDB] catErrStr := code2.CatToStr[code2.CatDB]
// act & assert // act & assert
assert.Equal(t, catErrStr, e.GeneralError()) assert.Equal(t, catErrStr, e.GeneralError())
@ -112,13 +112,13 @@ func TestGeneralError_GivenCatDB_ShouldReturnDBError(t *testing.T) {
func TestError_GivenEmptyMsg_ShouldReturnCatGeneralErrorMessage(t *testing.T) { func TestError_GivenEmptyMsg_ShouldReturnCatGeneralErrorMessage(t *testing.T) {
// setup // setup
e := Err{category: code.CatDB, msg: ""} e := Err{category: code2.CatDB, msg: ""}
// act // act
errMsg := e.Error() errMsg := e.Error()
// assert // assert
assert.Equal(t, code.CatToStr[code.CatDB], errMsg) assert.Equal(t, code2.CatToStr[code2.CatDB], errMsg)
} }
func TestError_GivenMsg_ShouldReturnGiveMsg(t *testing.T) { func TestError_GivenMsg_ShouldReturnGiveMsg(t *testing.T) {
@ -269,20 +269,20 @@ func TestErr_HTTPStatus(t *testing.T) {
want int want int
}{ }{
{name: "nil error", err: nil, want: http.StatusOK}, {name: "nil error", err: nil, want: http.StatusOK},
{name: "invalid measurement id", err: &Err{category: code.CatResource, code: code.InvalidMeasurementID}, want: http.StatusInternalServerError}, {name: "invalid measurement id", err: &Err{category: code2.CatResource, code: code2.InvalidMeasurementID}, want: http.StatusInternalServerError},
{name: "resource already exists", err: &Err{category: code.CatResource, code: code.ResourceAlreadyExist}, want: http.StatusConflict}, {name: "resource already exists", err: &Err{category: code2.CatResource, code: code2.ResourceAlreadyExist}, want: http.StatusConflict},
{name: "invalid resource state", err: &Err{category: code.CatResource, code: code.InvalidResourceState}, want: http.StatusConflict}, {name: "invalid resource state", err: &Err{category: code2.CatResource, code: code2.InvalidResourceState}, want: http.StatusConflict},
{name: "invalid posix time", err: &Err{category: code.CatAuth, code: code.InvalidPosixTime}, want: http.StatusForbidden}, {name: "invalid posix time", err: &Err{category: code2.CatAuth, code: code2.InvalidPosixTime}, want: http.StatusForbidden},
{name: "unauthorized", err: &Err{category: code.CatAuth, code: code.Unauthorized}, want: http.StatusUnauthorized}, {name: "unauthorized", err: &Err{category: code2.CatAuth, code: code2.Unauthorized}, want: http.StatusUnauthorized},
{name: "db error", err: &Err{category: code.CatDB, code: code.DBError}, want: http.StatusInternalServerError}, {name: "db error", err: &Err{category: code2.CatDB, code: code2.DBError}, want: http.StatusInternalServerError},
{name: "insufficient permission", err: &Err{category: code.CatResource, code: code.InsufficientPermission}, want: http.StatusUnauthorized}, {name: "insufficient permission", err: &Err{category: code2.CatResource, code: code2.InsufficientPermission}, want: http.StatusUnauthorized},
{name: "resource insufficient", err: &Err{category: code.CatResource, code: code.ResourceInsufficient}, want: http.StatusBadRequest}, {name: "resource insufficient", err: &Err{category: code2.CatResource, code: code2.ResourceInsufficient}, want: http.StatusBadRequest},
{name: "invalid format", err: &Err{category: code.CatInput, code: code.InvalidFormat}, want: http.StatusBadRequest}, {name: "invalid format", err: &Err{category: code2.CatInput, code: code2.InvalidFormat}, want: http.StatusBadRequest},
{name: "resource not found", err: &Err{code: code.ResourceNotFound}, want: http.StatusNotFound}, {name: "resource not found", err: &Err{code: code2.ResourceNotFound}, want: http.StatusNotFound},
{name: "ok", err: &Err{code: code.OK}, want: http.StatusOK}, {name: "ok", err: &Err{code: code2.OK}, want: http.StatusOK},
{name: "not valid implementation", err: &Err{category: code.CatInput, code: code.NotValidImplementation}, want: http.StatusNotImplemented}, {name: "not valid implementation", err: &Err{category: code2.CatInput, code: code2.NotValidImplementation}, want: http.StatusNotImplemented},
{name: "forbidden", err: &Err{category: code.CatAuth, code: code.Forbidden}, want: http.StatusForbidden}, {name: "forbidden", err: &Err{category: code2.CatAuth, code: code2.Forbidden}, want: http.StatusForbidden},
{name: "insufficient quota", err: &Err{category: code.CatResource, code: code.InsufficientQuota}, want: http.StatusPaymentRequired}, {name: "insufficient quota", err: &Err{category: code2.CatResource, code: code2.InsufficientQuota}, want: http.StatusPaymentRequired},
} }
for _, tt := range tests { for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) { t.Run(tt.name, func(t *testing.T) {

5
go.work Normal file
View File

@ -0,0 +1,5 @@
go 1.22
use (
./errors
)

99
readme.md Normal file
View File

@ -0,0 +1,99 @@
# golang-common
## Current modules
| module | latest version |
|--------------------------------------------------------|----------------|
| [error](errors) | v1.0.0 |
## 如何新增Module
假設新增一個module叫 monitoring/grafana
- init
```bash
mkdir -p monitoring/grafana
cd ./monitoring/grafana
go mod init yt.com/backend/common.git/monitoring/grafana
go work use ./monitoring/grafana
```
- befor commit
建議測試覆蓋率盡量達到80%
```bash
before-commit-check
```
- commit
```bash
git add ./monitoring/grafana
git commit -m "feat: add monitoring/grafana module"
git tag "monitoring/grafana/v1.0.0"
git push origin monitoring/grafana/v1.0.0
```
- launch merge request and codereview
## 如何使用私有Module
強制git使用ssh方式而不是https:
```bash
git config --global --add url."git@code.30cm.net:".insteadOf "https://code.30cm.net/"
# 檢查語法
vim ~/.gitconfig
```
設定go env
```bash
export GOPRIVATE="code.30cm.net"
```
產生ssh-key
請參考 [github ssh](https://docs.github.com/en/authentication/connecting-to-github-with-ssh) , [gitlab ssh](https://docs.gitlab.com/ee/user/ssh.html)
add ssh key to the ssh-agent
請參考 [Adding your SSH key to the ssh-agent](https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent#adding-your-ssh-key-to-the-ssh-agent)
```bash
$ eval "$(ssh-agent -s)"
> Agent pid 59566
```
```bash
$ touch ~/.ssh/config
```
```
Host code.30cm.net
Hostname code.30cm.net
User Daniel.W
IdentityFile ~/.ssh/id_rsa
```
```bash
$ ssh-add --apple-use-keychain ~/.ssh/id_ed25519
```
使用 yt.com domain git clone repo
```bash
git clone git@code.30cm.net:backend/layout-template.git
```
在自己repo底下執行:
```bash
go clean -modcache
go mod tidy
or
go get -x yt.com/backend/common.git/transport/http/health@1.0.0
```