Compare commits

..

13 Commits

Author SHA1 Message Date
Kevin Wan
a40254156f refactor: refactor yaml unmarshaler (#1517) 2022-02-09 17:22:52 +08:00
chenquan
05cc62f5ff chore: optimize yaml unmarshaler (#1513) 2022-02-09 16:57:00 +08:00
chenquan
9c2c90e533 chore: make error clearer (#1514) 2022-02-09 14:40:05 +08:00
Kevin Wan
822ee2e1c5 feat: update go-redis to v8, support ctx in redis methods (#1507)
* feat: update go-redis to v8, support ctx in redis methods

* fix compile errors

* chore: remove unused const

* chore: add tracing log on redis
2022-02-09 11:06:06 +08:00
anqiansong
77482c8946 fixes typo (#1511)
Co-authored-by: anqiansong <anqiansong@bytedance.com>
2022-02-08 22:16:38 +08:00
Kevin Wan
7ef0ab3119 Update readme-cn.md 2022-02-08 11:47:33 +08:00
anqiansong
8bd89a297a feature: Add goctl completion (#1505)
* feature: Add `goctl completion`

* Update const

Co-authored-by: anqiansong <anqiansong@bytedance.com>
2022-02-08 10:50:21 +08:00
Kevin Wan
bb75cc796e test: change fuzz tests (#1504) 2022-02-05 09:44:01 +08:00
Kevin Wan
0fdd8f54eb ci: add test for win (#1503)
* ci: add test for win

* ci: update check names

* ci: use go build instead of go test to verify win test

* fix: windows test failure

* chore: disable logs in tests
2022-02-05 00:06:23 +08:00
anqiansong
b1ffc464cd fix typo: goctl protoc usage (#1502)
Co-authored-by: anqiansong <anqiansong@bytedance.com>
2022-02-03 22:13:02 +08:00
Kevin Wan
50174960e4 chore: update command comment (#1501) 2022-02-02 22:02:08 +08:00
Kevin Wan
8f46eab977 fix: goctl not compile on windows (#1500) 2022-02-01 13:58:08 +08:00
Kevin Wan
ec299085f5 docs: update tal-tech to zeromico in docs (#1498) 2022-02-01 13:03:30 +08:00
69 changed files with 1353 additions and 406 deletions

View File

@@ -7,32 +7,50 @@ on:
branches: [ master ] branches: [ master ]
jobs: jobs:
build: test-linux:
name: Build name: Linux
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- name: Set up Go 1.x
uses: actions/setup-go@v2
with:
go-version: ^1.15
id: go
- name: Set up Go 1.x - name: Check out code into the Go module directory
uses: actions/setup-go@v2 uses: actions/checkout@v2
with:
go-version: ^1.15
id: go
- name: Check out code into the Go module directory - name: Get dependencies
uses: actions/checkout@v2 run: |
go get -v -t -d ./...
- name: Get dependencies - name: Lint
run: | run: |
go get -v -t -d ./... go vet -stdmethods=false $(go list ./...)
go install mvdan.cc/gofumpt@latest
test -z "$(gofumpt -s -l -extra .)" || echo "Please run 'gofumpt -l -w -extra .'"
- name: Lint - name: Test
run: | run: go test -race -coverprofile=coverage.txt -covermode=atomic ./...
go vet -stdmethods=false $(go list ./...)
go install mvdan.cc/gofumpt@latest
test -z "$(gofumpt -s -l -extra .)" || echo "Please run 'gofumpt -l -w -extra .'"
- name: Test - name: Codecov
run: go test -race -coverprofile=coverage.txt -covermode=atomic ./... uses: codecov/codecov-action@v2
- name: Codecov test-win:
uses: codecov/codecov-action@v2 name: Windows
runs-on: windows-latest
steps:
- name: Set up Go 1.x
uses: actions/setup-go@v2
with:
go-version: ^1.15
- name: Checkout codebase
uses: actions/checkout@v2
- name: Test
run: |
go mod verify
go mod download
go test -v -race ./...
cd tools/goctl && go build -v goctl.go

View File

@@ -2,6 +2,13 @@ package discov
import "errors" import "errors"
var (
// errEmptyEtcdHosts indicates that etcd hosts are empty.
errEmptyEtcdHosts = errors.New("empty etcd hosts")
// errEmptyEtcdKey indicates that etcd key is empty.
errEmptyEtcdKey = errors.New("empty etcd key")
)
// EtcdConf is the config item with the given key on etcd. // EtcdConf is the config item with the given key on etcd.
type EtcdConf struct { type EtcdConf struct {
Hosts []string Hosts []string
@@ -27,9 +34,9 @@ func (c EtcdConf) HasTLS() bool {
// Validate validates c. // Validate validates c.
func (c EtcdConf) Validate() error { func (c EtcdConf) Validate() error {
if len(c.Hosts) == 0 { if len(c.Hosts) == 0 {
return errors.New("empty etcd hosts") return errEmptyEtcdHosts
} else if len(c.Key) == 0 { } else if len(c.Key) == 0 {
return errors.New("empty etcd key") return errEmptyEtcdKey
} else { } else {
return nil return nil
} }

View File

@@ -5,6 +5,9 @@ import (
"os" "os"
) )
// errExceedFileSize indicates that the file size is exceeded.
var errExceedFileSize = errors.New("exceed file size")
// A RangeReader is used to read a range of content from a file. // A RangeReader is used to read a range of content from a file.
type RangeReader struct { type RangeReader struct {
file *os.File file *os.File
@@ -29,7 +32,7 @@ func (rr *RangeReader) Read(p []byte) (n int, err error) {
} }
if rr.stop < rr.start || rr.start >= stat.Size() { if rr.stop < rr.start || rr.start >= stat.Size() {
return 0, errors.New("exceed file size") return 0, errExceedFileSize
} }
if rr.stop-rr.start < int64(len(p)) { if rr.stop-rr.start < int64(len(p)) {

View File

@@ -51,5 +51,5 @@ func unmarshalUseNumber(decoder *json.Decoder, v interface{}) error {
} }
func formatError(v string, err error) error { func formatError(v string, err error) error {
return fmt.Errorf("string: `%s`, error: `%s`", v, err.Error()) return fmt.Errorf("string: `%s`, error: `%w`", v, err)
} }

View File

@@ -23,10 +23,9 @@ func TestPeriodLimit_RedisUnavailable(t *testing.T) {
const ( const (
seconds = 1 seconds = 1
total = 100
quota = 5 quota = 5
) )
l := NewPeriodLimit(seconds, quota, redis.NewRedis(s.Addr(), redis.NodeType), "periodlimit") l := NewPeriodLimit(seconds, quota, redis.New(s.Addr()), "periodlimit")
s.Close() s.Close()
val, err := l.Take("first") val, err := l.Take("first")
assert.NotNil(t, err) assert.NotNil(t, err)

View File

@@ -4,7 +4,6 @@ import (
"encoding/json" "encoding/json"
"errors" "errors"
"io" "io"
"io/ioutil"
"gopkg.in/yaml.v2" "gopkg.in/yaml.v2"
) )
@@ -29,39 +28,6 @@ func UnmarshalYamlReader(reader io.Reader, v interface{}) error {
return unmarshalYamlReader(reader, v, yamlUnmarshaler) return unmarshalYamlReader(reader, v, yamlUnmarshaler)
} }
func unmarshalYamlBytes(content []byte, v interface{}, unmarshaler *Unmarshaler) error {
var o interface{}
if err := yamlUnmarshal(content, &o); err != nil {
return err
}
if m, ok := o.(map[string]interface{}); ok {
return unmarshaler.Unmarshal(m, v)
}
return ErrUnsupportedType
}
func unmarshalYamlReader(reader io.Reader, v interface{}, unmarshaler *Unmarshaler) error {
content, err := ioutil.ReadAll(reader)
if err != nil {
return err
}
return unmarshalYamlBytes(content, v, unmarshaler)
}
// yamlUnmarshal YAML to map[string]interface{} instead of map[interface{}]interface{}.
func yamlUnmarshal(in []byte, out interface{}) error {
var res interface{}
if err := yaml.Unmarshal(in, &res); err != nil {
return err
}
*out.(*interface{}) = cleanupMapValue(res)
return nil
}
func cleanupInterfaceMap(in map[interface{}]interface{}) map[string]interface{} { func cleanupInterfaceMap(in map[interface{}]interface{}) map[string]interface{} {
res := make(map[string]interface{}) res := make(map[string]interface{})
for k, v := range in { for k, v := range in {
@@ -96,3 +62,40 @@ func cleanupMapValue(v interface{}) interface{} {
return Repr(v) return Repr(v)
} }
} }
func unmarshal(unmarshaler *Unmarshaler, o interface{}, v interface{}) error {
if m, ok := o.(map[string]interface{}); ok {
return unmarshaler.Unmarshal(m, v)
}
return ErrUnsupportedType
}
func unmarshalYamlBytes(content []byte, v interface{}, unmarshaler *Unmarshaler) error {
var o interface{}
if err := yamlUnmarshal(content, &o); err != nil {
return err
}
return unmarshal(unmarshaler, o, v)
}
func unmarshalYamlReader(reader io.Reader, v interface{}, unmarshaler *Unmarshaler) error {
var res interface{}
if err := yaml.NewDecoder(reader).Decode(&res); err != nil {
return err
}
return unmarshal(unmarshaler, cleanupMapValue(res), v)
}
// yamlUnmarshal YAML to map[string]interface{} instead of map[interface{}]interface{}.
func yamlUnmarshal(in []byte, out interface{}) error {
var res interface{}
if err := yaml.Unmarshal(in, &res); err != nil {
return err
}
*out.(*interface{}) = cleanupMapValue(res)
return nil
}

View File

@@ -926,14 +926,18 @@ func TestUnmarshalYamlBytesError(t *testing.T) {
} }
func TestUnmarshalYamlReaderError(t *testing.T) { func TestUnmarshalYamlReaderError(t *testing.T) {
payload := `abcd: cdef`
reader := strings.NewReader(payload)
var v struct { var v struct {
Any string Any string
} }
reader := strings.NewReader(`abcd: cdef`)
err := UnmarshalYamlReader(reader, &v) err := UnmarshalYamlReader(reader, &v)
assert.NotNil(t, err) assert.NotNil(t, err)
reader = strings.NewReader("chenquan")
err = UnmarshalYamlReader(reader, &v)
assert.ErrorIs(t, err, ErrUnsupportedType)
} }
func TestUnmarshalYamlBadReader(t *testing.T) { func TestUnmarshalYamlBadReader(t *testing.T) {
@@ -1011,6 +1015,6 @@ func TestUnmarshalYamlMapRune(t *testing.T) {
type badReader struct{} type badReader struct{}
func (b *badReader) Read(p []byte) (n int, err error) { func (b *badReader) Read(_ []byte) (n int, err error) {
return 0, io.ErrLimitReached return 0, io.ErrLimitReached
} }

View File

@@ -54,7 +54,7 @@ import (
"fmt" "fmt"
"log" "log"
"github.com/tal-tech/go-zero/core/mr" "github.com/zeromicro/go-zero/core/mr"
) )
func main() { func main() {

View File

@@ -55,7 +55,7 @@ import (
"fmt" "fmt"
"log" "log"
"github.com/tal-tech/go-zero/core/mr" "github.com/zeromicro/go-zero/core/mr"
) )
func main() { func main() {

View File

@@ -1,3 +1,6 @@
//go:build linux || darwin
// +build linux darwin
package proc package proc
import ( import (

83
core/stores/redis/hook.go Normal file
View File

@@ -0,0 +1,83 @@
package redis
import (
"context"
"strings"
"time"
red "github.com/go-redis/redis/v8"
"github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/core/mapping"
"github.com/zeromicro/go-zero/core/timex"
)
var (
startTimeKey = contextKey("startTime")
durationHook = hook{}
)
type (
contextKey string
hook struct{}
)
func (h hook) BeforeProcess(ctx context.Context, _ red.Cmder) (context.Context, error) {
return context.WithValue(ctx, startTimeKey, timex.Now()), nil
}
func (h hook) AfterProcess(ctx context.Context, cmd red.Cmder) error {
val := ctx.Value(startTimeKey)
if val == nil {
return nil
}
start, ok := val.(time.Duration)
if !ok {
return nil
}
duration := timex.Since(start)
if duration > slowThreshold.Load() {
logDuration(ctx, cmd, duration)
}
return nil
}
func (h hook) BeforeProcessPipeline(ctx context.Context, _ []red.Cmder) (context.Context, error) {
return context.WithValue(ctx, startTimeKey, timex.Now()), nil
}
func (h hook) AfterProcessPipeline(ctx context.Context, cmds []red.Cmder) error {
if len(cmds) == 0 {
return nil
}
val := ctx.Value(startTimeKey)
if val == nil {
return nil
}
start, ok := val.(time.Duration)
if !ok {
return nil
}
duration := timex.Since(start)
if duration > slowThreshold.Load()*time.Duration(len(cmds)) {
logDuration(ctx, cmds[0], duration)
}
return nil
}
func logDuration(ctx context.Context, cmd red.Cmder, duration time.Duration) {
var buf strings.Builder
for i, arg := range cmd.Args() {
if i > 0 {
buf.WriteByte(' ')
}
buf.WriteString(mapping.Repr(arg))
}
logx.WithContext(ctx).WithDuration(duration).Slowf("[REDIS] slowcall on executing: %s", buf.String())
}

View File

@@ -0,0 +1,137 @@
package redis
import (
"context"
"log"
"strings"
"testing"
"time"
red "github.com/go-redis/redis/v8"
"github.com/stretchr/testify/assert"
)
func TestHookProcessCase1(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
ctx, err := durationHook.BeforeProcess(context.Background(), nil)
if err != nil {
t.Fatal(err)
}
assert.Nil(t, durationHook.AfterProcess(ctx, red.NewCmd(context.Background())))
assert.False(t, strings.Contains(buf.String(), "slow"))
}
func TestHookProcessCase2(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
ctx, err := durationHook.BeforeProcess(context.Background(), nil)
if err != nil {
t.Fatal(err)
}
time.Sleep(slowThreshold.Load() + time.Millisecond)
assert.Nil(t, durationHook.AfterProcess(ctx, red.NewCmd(context.Background(), "foo", "bar")))
assert.True(t, strings.Contains(buf.String(), "slow"))
}
func TestHookProcessCase3(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
assert.Nil(t, durationHook.AfterProcess(context.Background(), red.NewCmd(context.Background())))
assert.True(t, buf.Len() == 0)
}
func TestHookProcessCase4(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
ctx := context.WithValue(context.Background(), startTimeKey, "foo")
assert.Nil(t, durationHook.AfterProcess(ctx, red.NewCmd(context.Background())))
assert.True(t, buf.Len() == 0)
}
func TestHookProcessPipelineCase1(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
ctx, err := durationHook.BeforeProcessPipeline(context.Background(), nil)
if err != nil {
t.Fatal(err)
}
assert.Nil(t, durationHook.AfterProcessPipeline(ctx, []red.Cmder{
red.NewCmd(context.Background()),
}))
assert.False(t, strings.Contains(buf.String(), "slow"))
}
func TestHookProcessPipelineCase2(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
ctx, err := durationHook.BeforeProcessPipeline(context.Background(), nil)
if err != nil {
t.Fatal(err)
}
time.Sleep(slowThreshold.Load() + time.Millisecond)
assert.Nil(t, durationHook.AfterProcessPipeline(ctx, []red.Cmder{
red.NewCmd(context.Background(), "foo", "bar"),
}))
assert.True(t, strings.Contains(buf.String(), "slow"))
}
func TestHookProcessPipelineCase3(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
assert.Nil(t, durationHook.AfterProcessPipeline(context.Background(), []red.Cmder{
red.NewCmd(context.Background()),
}))
assert.True(t, buf.Len() == 0)
}
func TestHookProcessPipelineCase4(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
ctx := context.WithValue(context.Background(), startTimeKey, "foo")
assert.Nil(t, durationHook.AfterProcessPipeline(ctx, []red.Cmder{
red.NewCmd(context.Background()),
}))
assert.True(t, buf.Len() == 0)
}
func TestHookProcessPipelineCase5(t *testing.T) {
writer := log.Writer()
var buf strings.Builder
log.SetOutput(&buf)
defer log.SetOutput(writer)
ctx := context.WithValue(context.Background(), startTimeKey, "foo")
assert.Nil(t, durationHook.AfterProcessPipeline(ctx, nil))
assert.True(t, buf.Len() == 0)
}

View File

@@ -1,32 +0,0 @@
package redis
import (
"strings"
red "github.com/go-redis/redis"
"github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/core/mapping"
"github.com/zeromicro/go-zero/core/timex"
)
func checkDuration(proc func(red.Cmder) error) func(red.Cmder) error {
return func(cmd red.Cmder) error {
start := timex.Now()
defer func() {
duration := timex.Since(start)
if duration > slowThreshold.Load() {
var buf strings.Builder
for i, arg := range cmd.Args() {
if i > 0 {
buf.WriteByte(' ')
}
buf.WriteString(mapping.Repr(arg))
}
logx.WithDuration(duration).Slowf("[REDIS] slowcall on executing: %s", buf.String())
}
}()
return proc(cmd)
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -1,6 +1,7 @@
package redis package redis
import ( import (
"context"
"crypto/tls" "crypto/tls"
"errors" "errors"
"io" "io"
@@ -9,8 +10,9 @@ import (
"time" "time"
"github.com/alicebob/miniredis/v2" "github.com/alicebob/miniredis/v2"
red "github.com/go-redis/redis" red "github.com/go-redis/redis/v8"
"github.com/stretchr/testify/assert" "github.com/stretchr/testify/assert"
"github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/core/stringx" "github.com/zeromicro/go-zero/core/stringx"
) )
@@ -963,13 +965,14 @@ func TestRedis_SortedSet(t *testing.T) {
assert.NotNil(t, err) assert.NotNil(t, err)
client.Zadd("second", 2, "aa") client.Zadd("second", 2, "aa")
client.Zadd("third", 3, "bbb") client.Zadd("third", 3, "bbb")
val, err = client.Zunionstore("union", ZStore{ val, err = client.Zunionstore("union", &ZStore{
Keys: []string{"second", "third"},
Weights: []float64{1, 2}, Weights: []float64{1, 2},
Aggregate: "SUM", Aggregate: "SUM",
}, "second", "third") })
assert.Nil(t, err) assert.Nil(t, err)
assert.Equal(t, int64(2), val) assert.Equal(t, int64(2), val)
_, err = New(client.Addr, badType()).Zunionstore("union", ZStore{}) _, err = New(client.Addr, badType()).Zunionstore("union", &ZStore{})
assert.NotNil(t, err) assert.NotNil(t, err)
vals, err = client.Zrange("union", 0, 10000) vals, err = client.Zrange("union", 0, 10000)
assert.Nil(t, err) assert.Nil(t, err)
@@ -987,9 +990,9 @@ func TestRedis_Pipelined(t *testing.T) {
})) }))
err := client.Pipelined( err := client.Pipelined(
func(pipe Pipeliner) error { func(pipe Pipeliner) error {
pipe.Incr("pipelined_counter") pipe.Incr(context.Background(), "pipelined_counter")
pipe.Expire("pipelined_counter", time.Hour) pipe.Expire(context.Background(), "pipelined_counter", time.Hour)
pipe.ZAdd("zadd", Z{Score: 12, Member: "zadd"}) pipe.ZAdd(context.Background(), "zadd", &Z{Score: 12, Member: "zadd"})
return nil return nil
}, },
) )
@@ -1135,6 +1138,8 @@ func TestRedis_WithPass(t *testing.T) {
} }
func runOnRedis(t *testing.T, fn func(client *Redis)) { func runOnRedis(t *testing.T, fn func(client *Redis)) {
logx.Disable()
s, err := miniredis.Run() s, err := miniredis.Run()
assert.Nil(t, err) assert.Nil(t, err)
defer func() { defer func() {
@@ -1153,6 +1158,8 @@ func runOnRedis(t *testing.T, fn func(client *Redis)) {
} }
func runOnRedisTLS(t *testing.T, fn func(client *Redis)) { func runOnRedisTLS(t *testing.T, fn func(client *Redis)) {
logx.Disable()
s, err := miniredis.RunTLS(&tls.Config{ s, err := miniredis.RunTLS(&tls.Config{
Certificates: make([]tls.Certificate, 1), Certificates: make([]tls.Certificate, 1),
InsecureSkipVerify: true, InsecureSkipVerify: true,
@@ -1182,6 +1189,6 @@ type mockedNode struct {
RedisNode RedisNode
} }
func (n mockedNode) BLPop(timeout time.Duration, keys ...string) *red.StringSliceCmd { func (n mockedNode) BLPop(ctx context.Context, timeout time.Duration, keys ...string) *red.StringSliceCmd {
return red.NewStringSliceCmd("foo", "bar") return red.NewStringSliceCmd(context.Background(), "foo", "bar")
} }

View File

@@ -3,7 +3,7 @@ package redis
import ( import (
"fmt" "fmt"
red "github.com/go-redis/redis" red "github.com/go-redis/redis/v8"
"github.com/zeromicro/go-zero/core/logx" "github.com/zeromicro/go-zero/core/logx"
) )

View File

@@ -4,7 +4,7 @@ import (
"crypto/tls" "crypto/tls"
"io" "io"
red "github.com/go-redis/redis" red "github.com/go-redis/redis/v8"
"github.com/zeromicro/go-zero/core/syncx" "github.com/zeromicro/go-zero/core/syncx"
) )
@@ -32,7 +32,8 @@ func getClient(r *Redis) (*red.Client, error) {
MinIdleConns: idleConns, MinIdleConns: idleConns,
TLSConfig: tlsConfig, TLSConfig: tlsConfig,
}) })
store.WrapProcess(checkDuration) store.AddHook(durationHook)
return store, nil return store, nil
}) })
if err != nil { if err != nil {

View File

@@ -4,7 +4,7 @@ import (
"crypto/tls" "crypto/tls"
"io" "io"
red "github.com/go-redis/redis" red "github.com/go-redis/redis/v8"
"github.com/zeromicro/go-zero/core/syncx" "github.com/zeromicro/go-zero/core/syncx"
) )
@@ -25,7 +25,7 @@ func getCluster(r *Redis) (*red.ClusterClient, error) {
MinIdleConns: idleConns, MinIdleConns: idleConns,
TLSConfig: tlsConfig, TLSConfig: tlsConfig,
}) })
store.WrapProcess(checkDuration) store.AddHook(durationHook)
return store, nil return store, nil
}) })

View File

@@ -5,7 +5,7 @@ import (
"sync/atomic" "sync/atomic"
"time" "time"
red "github.com/go-redis/redis" red "github.com/go-redis/redis/v8"
"github.com/zeromicro/go-zero/core/logx" "github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/core/stringx" "github.com/zeromicro/go-zero/core/stringx"
) )

View File

@@ -17,10 +17,12 @@ func CreateRedis() (r *redis.Redis, clean func(), err error) {
return redis.New(mr.Addr()), func() { return redis.New(mr.Addr()), func() {
ch := make(chan lang.PlaceholderType) ch := make(chan lang.PlaceholderType)
go func() { go func() {
mr.Close() mr.Close()
close(ch) close(ch)
}() }()
select { select {
case <-ch: case <-ch:
case <-time.After(time.Second): case <-time.After(time.Second):

View File

@@ -4,9 +4,12 @@ import (
"testing" "testing"
"github.com/stretchr/testify/assert" "github.com/stretchr/testify/assert"
"github.com/zeromicro/go-zero/core/logx"
) )
func TestScriptCache(t *testing.T) { func TestScriptCache(t *testing.T) {
logx.Disable()
cache := GetScriptCache() cache := GetScriptCache()
cache.SetSha("foo", "bar") cache.SetSha("foo", "bar")
cache.SetSha("bla", "blabla") cache.SetSha("bla", "blabla")

View File

@@ -7,6 +7,9 @@ import (
"github.com/zeromicro/go-zero/core/lang" "github.com/zeromicro/go-zero/core/lang"
) )
// errTimeout indicates a timeout.
var errTimeout = errors.New("timeout")
type ( type (
// Ticker interface wraps the Chan and Stop methods. // Ticker interface wraps the Chan and Stop methods.
Ticker interface { Ticker interface {
@@ -70,7 +73,7 @@ func (ft *fakeTicker) Tick() {
func (ft *fakeTicker) Wait(d time.Duration) error { func (ft *fakeTicker) Wait(d time.Duration) error {
select { select {
case <-time.After(d): case <-time.After(d):
return errors.New("timeout") return errTimeout
case <-ft.done: case <-ft.done:
return nil return nil
} }

2
go.mod
View File

@@ -7,7 +7,6 @@ require (
github.com/DATA-DOG/go-sqlmock v1.5.0 github.com/DATA-DOG/go-sqlmock v1.5.0
github.com/alicebob/miniredis/v2 v2.17.0 github.com/alicebob/miniredis/v2 v2.17.0
github.com/globalsign/mgo v0.0.0-20181015135952-eeefdecb41b8 github.com/globalsign/mgo v0.0.0-20181015135952-eeefdecb41b8
github.com/go-redis/redis v6.15.9+incompatible
github.com/go-sql-driver/mysql v1.6.0 github.com/go-sql-driver/mysql v1.6.0
github.com/golang-jwt/jwt/v4 v4.2.0 github.com/golang-jwt/jwt/v4 v4.2.0
github.com/golang/mock v1.6.0 github.com/golang/mock v1.6.0
@@ -42,6 +41,7 @@ require (
require ( require (
github.com/fatih/color v1.10.0 // indirect github.com/fatih/color v1.10.0 // indirect
github.com/go-logr/stdr v1.2.2 // indirect github.com/go-logr/stdr v1.2.2 // indirect
github.com/go-redis/redis/v8 v8.11.4
github.com/mattn/go-runewidth v0.0.13 // indirect github.com/mattn/go-runewidth v0.0.13 // indirect
github.com/openzipkin/zipkin-go v0.4.0 // indirect github.com/openzipkin/zipkin-go v0.4.0 // indirect
golang.org/x/net v0.0.0-20220114011407-0dd24b26b47d // indirect golang.org/x/net v0.0.0-20220114011407-0dd24b26b47d // indirect

9
go.sum
View File

@@ -62,8 +62,9 @@ github.com/bkaradzic/go-lz4 v1.0.0/go.mod h1:0YdlkowM3VswSROI7qDxhRvJ3sLhlFrRRwj
github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU=
github.com/cespare/xxhash v1.1.0 h1:a6HrQnmkObjyL+Gs60czilIUGqrzKutQD6XZog3p+ko= github.com/cespare/xxhash v1.1.0 h1:a6HrQnmkObjyL+Gs60czilIUGqrzKutQD6XZog3p+ko=
github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc= github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc=
github.com/cespare/xxhash/v2 v2.1.1 h1:6MnRN8NT7+YBpUIWxHtefFZOKTAPgGjpQSxqLNn0+qY=
github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
github.com/cespare/xxhash/v2 v2.1.2 h1:YRXhKfTDauu4ajMg1TPgFO5jnlC2HCbmLXMcTG5cbYE=
github.com/cespare/xxhash/v2 v2.1.2/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI=
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI= github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI=
github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU= github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU=
@@ -87,6 +88,8 @@ github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSs
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ= github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ=
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f h1:lO4WD4F/rVNCu3HqELle0jiPLLBs70cWOduZpkS1E78=
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f/go.mod h1:cuUVRXasLTGF7a8hSLbxyZXjz+1KgoB3wDUb6vlszIc=
github.com/docker/spdystream v0.0.0-20160310174837-449fdfce4d96/go.mod h1:Qh8CwZgvJUkLughtfhJv5dyTYa91l1fOUCrgjqmcifM= github.com/docker/spdystream v0.0.0-20160310174837-449fdfce4d96/go.mod h1:Qh8CwZgvJUkLughtfhJv5dyTYa91l1fOUCrgjqmcifM=
github.com/docopt/docopt-go v0.0.0-20180111231733-ee0de3bc6815/go.mod h1:WwZ+bS3ebgob9U8Nd0kOddGdZWjyMGR8Wziv+TBNwSE= github.com/docopt/docopt-go v0.0.0-20180111231733-ee0de3bc6815/go.mod h1:WwZ+bS3ebgob9U8Nd0kOddGdZWjyMGR8Wziv+TBNwSE=
github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk=
@@ -142,8 +145,8 @@ github.com/go-openapi/jsonreference v0.19.3/go.mod h1:rjx6GuL8TTa9VaixXglHmQmIL9
github.com/go-openapi/spec v0.19.3/go.mod h1:FpwSN1ksY1eteniUU7X0N/BgJ7a4WvBFVA8Lj9mJglo= github.com/go-openapi/spec v0.19.3/go.mod h1:FpwSN1ksY1eteniUU7X0N/BgJ7a4WvBFVA8Lj9mJglo=
github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk=
github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk=
github.com/go-redis/redis v6.15.9+incompatible h1:K0pv1D7EQUjfyoMql+r/jZqCLizCGKFlFgcHWWmHQjg= github.com/go-redis/redis/v8 v8.11.4 h1:kHoYkfZP6+pe04aFTnhDH6GDROa5yJdHJVNxV3F46Tg=
github.com/go-redis/redis v6.15.9+incompatible/go.mod h1:NAIEuMOZ/fxfXJIrKDQDz8wamY7mA7PouImQ2Jvg6kA= github.com/go-redis/redis/v8 v8.11.4/go.mod h1:2Z2wHZXdQpCDXEGzqMockDpNyYvi2l4Pxt6RJr792+w=
github.com/go-sql-driver/mysql v1.4.0/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w= github.com/go-sql-driver/mysql v1.4.0/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w=
github.com/go-sql-driver/mysql v1.6.0 h1:BCTh4TKNUYmOmMUcQ3IipzF5prigylS7XXjEkfCHuOE= github.com/go-sql-driver/mysql v1.6.0 h1:BCTh4TKNUYmOmMUcQ3IipzF5prigylS7XXjEkfCHuOE=
github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg= github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=

View File

@@ -89,7 +89,7 @@ go-zero 是一个集成了各种工程实践的包含 web 和 rpc 框架,有
在项目目录下通过如下命令安装: 在项目目录下通过如下命令安装:
```shell ```shell
GO111MODULE=on GOPROXY=https://goproxy.cn/,direct go get -u github.com/tal-tech/go-zero GO111MODULE=on GOPROXY=https://goproxy.cn/,direct go get -u github.com/zeromicro/go-zero
``` ```
## 5. Quick Start ## 5. Quick Start
@@ -106,10 +106,10 @@ GO111MODULE=on GOPROXY=https://goproxy.cn/,direct go get -u github.com/tal-tech/
```shell ```shell
# Go 1.15 及之前版本 # Go 1.15 及之前版本
GO111MODULE=on GOPROXY=https://goproxy.cn/,direct go get -u github.com/tal-tech/go-zero/tools/goctl@latest GO111MODULE=on GOPROXY=https://goproxy.cn/,direct go get -u github.com/zeromicro/go-zero/tools/goctl@latest
# Go 1.16 及以后版本 # Go 1.16 及以后版本
GOPROXY=https://goproxy.cn/,direct go install github.com/tal-tech/go-zero/tools/goctl@latest GOPROXY=https://goproxy.cn/,direct go install github.com/zeromicro/go-zero/tools/goctl@latest
``` ```
确保 goctl 可执行 确保 goctl 可执行
@@ -234,12 +234,13 @@ go-zero 已被许多公司用于生产部署,接入场景如在线教育、电
>46. 上海游族网络 >46. 上海游族网络
>47. 深信服 >47. 深信服
>48. 中免日上科技互联有限公司 >48. 中免日上科技互联有限公司
>48. ECLOUDVALLEY TECHNOLOGY (HK) LIMITED >49. ECLOUDVALLEY TECHNOLOGY (HK) LIMITED
>48. 馨科智(深圳)科技有限公司 >50. 馨科智(深圳)科技有限公司
>48. 成都松珀科技有限公司 >51. 成都松珀科技有限公司
>48. 亿景智联 >52. 亿景智联
>48. 上海扩博智能技术有限公司 >53. 上海扩博智能技术有限公司
>48. 一犀科技成都有限公司 >54. 一犀科技成都有限公司
>55. 北京术杰科技有限公司
如果贵公司也已使用 go-zero欢迎在 [登记地址](https://github.com/zeromicro/go-zero/issues/602) 登记,仅仅为了推广,不做其它用途。 如果贵公司也已使用 go-zero欢迎在 [登记地址](https://github.com/zeromicro/go-zero/issues/602) 登记,仅仅为了推广,不做其它用途。

View File

@@ -90,7 +90,7 @@ As below, go-zero protects the system with a couple of layers and mechanisms:
Run the following command under your project: Run the following command under your project:
```shell ```shell
go get -u github.com/tal-tech/go-zero go get -u github.com/zeromicro/go-zero
``` ```
## 6. Quick Start ## 6. Quick Start
@@ -107,10 +107,10 @@ go get -u github.com/tal-tech/go-zero
```shell ```shell
# for Go 1.15 and earlier # for Go 1.15 and earlier
GO111MODULE=on go get -u github.com/tal-tech/go-zero/tools/goctl@latest GO111MODULE=on go get -u github.com/zeromicro/go-zero/tools/goctl@latest
# for Go 1.16 and later # for Go 1.16 and later
go install github.com/tal-tech/go-zero/tools/goctl@latest go install github.com/zeromicro/go-zero/tools/goctl@latest
``` ```
make sure goctl is executable. make sure goctl is executable.

View File

@@ -8,9 +8,9 @@ import (
"text/template" "text/template"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util" "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const apiTemplate = ` const apiTemplate = `

View File

@@ -3,8 +3,8 @@ package apigen
import ( import (
"fmt" "fmt"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
) )
const ( const (

View File

@@ -4,9 +4,9 @@ import (
"errors" "errors"
"strings" "strings"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/core/logx" "github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/tools/goctl/api/parser" "github.com/zeromicro/go-zero/tools/goctl/api/parser"
"github.com/urfave/cli"
) )
// DartCommand create dart network request code // DartCommand create dart network request code

View File

@@ -7,9 +7,9 @@ import (
"path/filepath" "path/filepath"
"strings" "strings"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/api/parser" "github.com/zeromicro/go-zero/tools/goctl/api/parser"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
// DocCommand generate markdown doc file // DocCommand generate markdown doc file

View File

@@ -11,11 +11,11 @@ import (
"path/filepath" "path/filepath"
"strings" "strings"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/core/errorx" "github.com/zeromicro/go-zero/core/errorx"
"github.com/zeromicro/go-zero/tools/goctl/api/parser" "github.com/zeromicro/go-zero/tools/goctl/api/parser"
"github.com/zeromicro/go-zero/tools/goctl/api/util" "github.com/zeromicro/go-zero/tools/goctl/api/util"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const ( const (

View File

@@ -12,6 +12,7 @@ import (
"time" "time"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/core/logx" "github.com/zeromicro/go-zero/core/logx"
apiformat "github.com/zeromicro/go-zero/tools/goctl/api/format" apiformat "github.com/zeromicro/go-zero/tools/goctl/api/format"
"github.com/zeromicro/go-zero/tools/goctl/api/parser" "github.com/zeromicro/go-zero/tools/goctl/api/parser"
@@ -19,7 +20,6 @@ import (
"github.com/zeromicro/go-zero/tools/goctl/config" "github.com/zeromicro/go-zero/tools/goctl/config"
"github.com/zeromicro/go-zero/tools/goctl/util" "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const tmpFile = "%s-%d" const tmpFile = "%s-%d"

View File

@@ -3,8 +3,8 @@ package gogen
import ( import (
"fmt" "fmt"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
) )
const ( const (

View File

@@ -6,10 +6,10 @@ import (
"strings" "strings"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/core/logx" "github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/tools/goctl/api/parser" "github.com/zeromicro/go-zero/tools/goctl/api/parser"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
// JavaCommand the generate java code command entrance // JavaCommand the generate java code command entrance

View File

@@ -3,8 +3,8 @@ package ktgen
import ( import (
"errors" "errors"
"github.com/zeromicro/go-zero/tools/goctl/api/parser"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/api/parser"
) )
// KtCommand the generate kotlin code command entrance // KtCommand the generate kotlin code command entrance

View File

@@ -7,11 +7,11 @@ import (
"strings" "strings"
"text/template" "text/template"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/api/gogen" "github.com/zeromicro/go-zero/tools/goctl/api/gogen"
conf "github.com/zeromicro/go-zero/tools/goctl/config" conf "github.com/zeromicro/go-zero/tools/goctl/config"
"github.com/zeromicro/go-zero/tools/goctl/util" "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const apiTemplate = ` const apiTemplate = `

View File

@@ -3,8 +3,8 @@ package new
import ( import (
"fmt" "fmt"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
) )
const ( const (

View File

@@ -7,9 +7,9 @@ import (
"path/filepath" "path/filepath"
"strings" "strings"
"github.com/zeromicro/antlr"
"github.com/zeromicro/go-zero/tools/goctl/api/parser/g4/gen/api" "github.com/zeromicro/go-zero/tools/goctl/api/parser/g4/gen/api"
"github.com/zeromicro/go-zero/tools/goctl/util/console" "github.com/zeromicro/go-zero/tools/goctl/util/console"
"github.com/zeromicro/antlr"
) )
type ( type (

View File

@@ -5,9 +5,9 @@ import (
"sort" "sort"
"strings" "strings"
"github.com/zeromicro/antlr"
"github.com/zeromicro/go-zero/tools/goctl/api/parser/g4/gen/api" "github.com/zeromicro/go-zero/tools/goctl/api/parser/g4/gen/api"
"github.com/zeromicro/go-zero/tools/goctl/util/console" "github.com/zeromicro/go-zero/tools/goctl/util/console"
"github.com/zeromicro/antlr"
) )
type ( type (

View File

@@ -5,10 +5,10 @@ import (
"fmt" "fmt"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/core/logx" "github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/tools/goctl/api/parser" "github.com/zeromicro/go-zero/tools/goctl/api/parser"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
// TsCommand provides the entry to generate typescript codes // TsCommand provides the entry to generate typescript codes

View File

@@ -5,8 +5,8 @@ import (
"fmt" "fmt"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/zeromicro/go-zero/tools/goctl/api/parser"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/api/parser"
) )
// GoValidateApi verifies whether the api has a syntax error // GoValidateApi verifies whether the api has a syntax error

View File

@@ -6,8 +6,8 @@ import (
"os/exec" "os/exec"
"runtime" "runtime"
"github.com/zeromicro/go-zero/tools/goctl/internal/version"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/internal/version"
) )
const ( const (

View File

@@ -0,0 +1,75 @@
package completion
import (
"bytes"
"fmt"
"io/ioutil"
"os"
"path/filepath"
"runtime"
"github.com/logrusorgru/aurora"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/zeromicro/go-zero/tools/goctl/vars"
)
func Completion(c *cli.Context) error {
goos := runtime.GOOS
if goos == vars.OsWindows {
return fmt.Errorf("%q: only support unix-like OS", goos)
}
name := c.String("name")
if len(name) == 0 {
name = defaultCompletionFilename
}
if filepath.IsAbs(name) {
return fmt.Errorf("unsupport absolute path: %q", name)
}
home, err := pathx.GetAutoCompleteHome()
if err != nil {
return err
}
buffer := bytes.NewBuffer(nil)
zshF := filepath.Join(home, "zsh", defaultCompletionFilename)
err = pathx.MkdirIfNotExist(filepath.Dir(zshF))
if err != nil {
return err
}
bashF := filepath.Join(home, "bash", defaultCompletionFilename)
err = pathx.MkdirIfNotExist(filepath.Dir(bashF))
if err != nil {
return err
}
var flag = magic
err = ioutil.WriteFile(zshF, zsh, os.ModePerm)
if err != nil {
return err
}
flag |= flagZsh
err = ioutil.WriteFile(bashF, bash, os.ModePerm)
if err != nil {
return err
}
flag |= flagBash
buffer.WriteString(aurora.Green("generation auto completion success!\n").String())
buffer.WriteString(aurora.Green("executes the following script to setting shell:\n").String())
switch flag {
case magic | flagZsh:
buffer.WriteString(aurora.Blue(fmt.Sprintf("echo PROG=goctl source %s >> ~/.zshrc && source ~/.zshrc", zshF)).String())
case magic | flagBash:
buffer.WriteString(aurora.Blue(fmt.Sprintf("echo PROG=goctl source %s >> ~/.bashrc && source ~/.bashrc", bashF)).String())
case magic | flagZsh | flagBash:
buffer.WriteString(aurora.Blue(fmt.Sprintf(`echo PROG=goctl source %s >> ~/.zshrc && source ~/.zshrc
or
echo PROG=goctl source %s >> ~/.bashrc && source ~/.bashrc`, zshF, bashF)).String())
default:
return nil
}
fmt.Println(buffer.String())
return nil
}

View File

@@ -0,0 +1,9 @@
package completion
const BashCompletionFlag = `generate-goctl-completion`
const defaultCompletionFilename = "goctl_autocomplete"
const (
magic = 1 << iota
flagZsh
flagBash
)

View File

@@ -0,0 +1,51 @@
package completion
import "fmt"
var zsh = []byte(fmt.Sprintf(`#compdef $PROG
_cli_zsh_autocomplete() {
local -a opts
local cur
cur=${words[-1]}
if [[ "$cur" == "-"* ]]; then
opts=("${(@f)$(_CLI_ZSH_AUTOCOMPLETE_HACK=1 ${words[@]:0:#words[@]-1} ${cur} --%s)}")
else
opts=("${(@f)$(_CLI_ZSH_AUTOCOMPLETE_HACK=1 ${words[@]:0:#words[@]-1} --%s)}")
fi
if [[ "${opts[1]}" != "" ]]; then
_describe 'values' opts
else
_files
fi
return
}
compdef _cli_zsh_autocomplete $PROG
`, BashCompletionFlag, BashCompletionFlag))
var bash = []byte(fmt.Sprintf(`#! /bin/bash
: ${PROG:=$(basename ${BASH_SOURCE})}
_cli_bash_autocomplete() {
if [[ "${COMP_WORDS[0]}" != "source" ]]; then
local cur opts base
COMPREPLY=()
cur="${COMP_WORDS[COMP_CWORD]}"
if [[ "$cur" == "-"* ]]; then
opts=$( ${COMP_WORDS[@]:0:$COMP_CWORD} ${cur} --%s )
else
opts=$( ${COMP_WORDS[@]:0:$COMP_CWORD} --%s )
fi
COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) )
return 0
fi
}
complete -o bashdefault -o default -o nospace -F _cli_bash_autocomplete $PROG
unset PROG
`, BashCompletionFlag, BashCompletionFlag))

View File

@@ -10,9 +10,9 @@ import (
"time" "time"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util" "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const ( const (

View File

@@ -1,8 +1,8 @@
package docker package docker
import ( import (
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
) )
const ( const (

View File

@@ -13,5 +13,5 @@ require (
github.com/urfave/cli v1.22.5 github.com/urfave/cli v1.22.5
github.com/zeromicro/antlr v0.0.1 github.com/zeromicro/antlr v0.0.1
github.com/zeromicro/ddl-parser v0.0.0-20210712021150-63520aca7348 github.com/zeromicro/ddl-parser v0.0.0-20210712021150-63520aca7348
github.com/zeromicro/go-zero v1.3.0-beta github.com/zeromicro/go-zero v1.3.0
) )

View File

@@ -360,8 +360,8 @@ github.com/zeromicro/antlr v0.0.1 h1:CQpIn/dc0pUjgGQ81y98s/NGOm2Hfru2NNio2I9mQgk
github.com/zeromicro/antlr v0.0.1/go.mod h1:nfpjEwFR6Q4xGDJMcZnCL9tEfQRgszMwu3rDz2Z+p5M= github.com/zeromicro/antlr v0.0.1/go.mod h1:nfpjEwFR6Q4xGDJMcZnCL9tEfQRgszMwu3rDz2Z+p5M=
github.com/zeromicro/ddl-parser v0.0.0-20210712021150-63520aca7348 h1:OhxL9tn28gDeJVzreIUiE5oVxZCjL3tBJ0XBNw8p5R8= github.com/zeromicro/ddl-parser v0.0.0-20210712021150-63520aca7348 h1:OhxL9tn28gDeJVzreIUiE5oVxZCjL3tBJ0XBNw8p5R8=
github.com/zeromicro/ddl-parser v0.0.0-20210712021150-63520aca7348/go.mod h1:ISU/8NuPyEpl9pa17Py9TBPetMjtsiHrb9f5XGiYbo8= github.com/zeromicro/ddl-parser v0.0.0-20210712021150-63520aca7348/go.mod h1:ISU/8NuPyEpl9pa17Py9TBPetMjtsiHrb9f5XGiYbo8=
github.com/zeromicro/go-zero v1.3.0-beta h1:jNwtjGzAV6PSklpXbLCmQph7BzfH7abcUIOG9odWMsM= github.com/zeromicro/go-zero v1.3.0 h1:Eyn36yBtR043sm4YKmxR6eS3UA/GtZDktQ+UqIJ3Lm0=
github.com/zeromicro/go-zero v1.3.0-beta/go.mod h1:Hy4o1VFAt32lXaQMbaBhoFeZjA/rJqJ4PTGNdGsURcc= github.com/zeromicro/go-zero v1.3.0/go.mod h1:Hy4o1VFAt32lXaQMbaBhoFeZjA/rJqJ4PTGNdGsURcc=
go.etcd.io/etcd/api/v3 v3.5.1/go.mod h1:cbVKeC6lCfl7j/8jBhAK6aIYO9XOjdptoxU/nLQcPvs= go.etcd.io/etcd/api/v3 v3.5.1/go.mod h1:cbVKeC6lCfl7j/8jBhAK6aIYO9XOjdptoxU/nLQcPvs=
go.etcd.io/etcd/client/pkg/v3 v3.5.1/go.mod h1:IJHfcCEKxYu1Os13ZdwCwIUTUVGYTSAM3YSwc9/Ac1g= go.etcd.io/etcd/client/pkg/v3 v3.5.1/go.mod h1:IJHfcCEKxYu1Os13ZdwCwIUTUVGYTSAM3YSwc9/Ac1g=
go.etcd.io/etcd/client/v3 v3.5.1/go.mod h1:OnjH4M8OnAotwaB2l9bVgZzRFKru7/ZMoS46OtKyd3Q= go.etcd.io/etcd/client/v3 v3.5.1/go.mod h1:OnjH4M8OnAotwaB2l9bVgZzRFKru7/ZMoS46OtKyd3Q=

View File

@@ -20,6 +20,7 @@ import (
"github.com/zeromicro/go-zero/tools/goctl/api/tsgen" "github.com/zeromicro/go-zero/tools/goctl/api/tsgen"
"github.com/zeromicro/go-zero/tools/goctl/api/validate" "github.com/zeromicro/go-zero/tools/goctl/api/validate"
"github.com/zeromicro/go-zero/tools/goctl/bug" "github.com/zeromicro/go-zero/tools/goctl/bug"
"github.com/zeromicro/go-zero/tools/goctl/completion"
"github.com/zeromicro/go-zero/tools/goctl/docker" "github.com/zeromicro/go-zero/tools/goctl/docker"
"github.com/zeromicro/go-zero/tools/goctl/internal/errorx" "github.com/zeromicro/go-zero/tools/goctl/internal/errorx"
"github.com/zeromicro/go-zero/tools/goctl/internal/version" "github.com/zeromicro/go-zero/tools/goctl/internal/version"
@@ -468,7 +469,7 @@ var commands = []cli.Command{
{ {
Name: "protoc", Name: "protoc",
Usage: "generate grpc code", Usage: "generate grpc code",
UsageText: `example: goctl rpc protoc xx.proto --go_out=./pb --go-grpc=./pb --zrpc_out=.`, UsageText: `example: goctl rpc protoc xx.proto --go_out=./pb --go-grpc_out=./pb --zrpc_out=.`,
Description: "for details, see https://go-zero.dev/cn/goctl-rpc.html", Description: "for details, see https://go-zero.dev/cn/goctl-rpc.html",
Action: rpc.ZRPC, Action: rpc.ZRPC,
Flags: []cli.Flag{ Flags: []cli.Flag{
@@ -797,13 +798,29 @@ var commands = []cli.Command{
}, },
}, },
}, },
{
Name: "completion",
Usage: "generation completion script, it only works for unix-like OS",
Action: completion.Completion,
Flags: []cli.Flag{
cli.StringFlag{
Name: "name, n",
Usage: "the filename of auto complete script, default is [goctl_autocomplete]",
},
},
},
} }
func main() { func main() {
logx.Disable() logx.Disable()
load.Disable() load.Disable()
cli.BashCompletionFlag = cli.BoolFlag{
Name: completion.BashCompletionFlag,
Hidden: true,
}
app := cli.NewApp() app := cli.NewApp()
app.EnableBashCompletion = true
app.Usage = "a cli tool to generate code" app.Usage = "a cli tool to generate code"
app.Version = fmt.Sprintf("%s %s/%s", version.BuildVersion, runtime.GOOS, runtime.GOARCH) app.Version = fmt.Sprintf("%s %s/%s", version.BuildVersion, runtime.GOOS, runtime.GOARCH)
app.Commands = commands app.Commands = commands

View File

@@ -6,9 +6,9 @@ import (
"text/template" "text/template"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util" "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const ( const (

View File

@@ -0,0 +1,7 @@
//go:build windows
// +build windows
package migrate
func cancelOnSignals() {
}

View File

@@ -0,0 +1,31 @@
//go:build linux || darwin
// +build linux darwin
package migrate
import (
"os"
"os/signal"
"syscall"
"github.com/zeromicro/go-zero/core/syncx"
"github.com/zeromicro/go-zero/tools/goctl/util/console"
)
func cancelOnSignals() {
doneChan := syncx.NewDoneChan()
defer doneChan.Close()
go func(dc *syncx.DoneChan) {
c := make(chan os.Signal)
signal.Notify(c, syscall.SIGTERM, syscall.SIGKILL, syscall.SIGINT, syscall.SIGTSTP, syscall.SIGQUIT)
select {
case <-c:
console.Error(`
migrate failed, reason: "User Canceled"`)
os.Exit(0)
case <-dc.Done():
return
}
}(doneChan)
}

View File

@@ -10,16 +10,13 @@ import (
"io/fs" "io/fs"
"io/ioutil" "io/ioutil"
"os" "os"
"os/signal"
"path/filepath" "path/filepath"
"runtime" "runtime"
"strings" "strings"
"syscall"
"time" "time"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/core/syncx"
"github.com/zeromicro/go-zero/tools/goctl/util/console" "github.com/zeromicro/go-zero/tools/goctl/util/console"
"github.com/zeromicro/go-zero/tools/goctl/util/ctx" "github.com/zeromicro/go-zero/tools/goctl/util/ctx"
"github.com/zeromicro/go-zero/tools/goctl/vars" "github.com/zeromicro/go-zero/tools/goctl/vars"
@@ -71,22 +68,7 @@ func rewriteImport(verbose bool) error {
time.Sleep(200 * time.Millisecond) time.Sleep(200 * time.Millisecond)
} }
doneChan := syncx.NewDoneChan() cancelOnSignals()
defer func() {
doneChan.Close()
}()
go func(dc *syncx.DoneChan) {
c := make(chan os.Signal)
signal.Notify(c, syscall.SIGTERM, syscall.SIGKILL, syscall.SIGINT, syscall.SIGTSTP, syscall.SIGQUIT)
select {
case <-c:
console.Error(`
migrate failed, reason: "User Canceled"`)
os.Exit(0)
case <-dc.Done():
return
}
}(doneChan)
wd, err := os.Getwd() wd, err := os.Getwd()
if err != nil { if err != nil {

View File

@@ -13,7 +13,6 @@ import (
) )
const deprecatedGoZeroMod = "github.com/tal-tech/go-zero" const deprecatedGoZeroMod = "github.com/tal-tech/go-zero"
const deprecatedBuilderx = "github.com/tal-tech/go-zero/tools/goctl/model/sql/builderx" const deprecatedBuilderx = "github.com/tal-tech/go-zero/tools/goctl/model/sql/builderx"
const replacementBuilderx = "github.com/zeromicro/go-zero/core/stores/builder" const replacementBuilderx = "github.com/zeromicro/go-zero/core/stores/builder"
const goZeroMod = "github.com/zeromicro/go-zero" const goZeroMod = "github.com/zeromicro/go-zero"

View File

@@ -3,9 +3,9 @@ package generate
import ( import (
"fmt" "fmt"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/model/mongo/template" "github.com/zeromicro/go-zero/tools/goctl/model/mongo/template"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const ( const (

View File

@@ -5,11 +5,11 @@ import (
"path/filepath" "path/filepath"
"strings" "strings"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/config" "github.com/zeromicro/go-zero/tools/goctl/config"
"github.com/zeromicro/go-zero/tools/goctl/model/mongo/generate" "github.com/zeromicro/go-zero/tools/goctl/model/mongo/generate"
file "github.com/zeromicro/go-zero/tools/goctl/util" file "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
// Action provides the entry for goctl mongo code generation. // Action provides the entry for goctl mongo code generation.

View File

@@ -66,7 +66,7 @@ type User struct {
"github.com/globalsign/mgo/bson" "github.com/globalsign/mgo/bson"
cachec "github.com/zeromicro/go-zero/core/stores/cache" cachec "github.com/zeromicro/go-zero/core/stores/cache"
"github.com/tal-tech/go-zero/core/stores/mongoc" "github.com/zeromicro/go-zero/core/stores/mongoc"
) )
type UserModel interface { type UserModel interface {
@@ -196,7 +196,7 @@ OPTIONS:
--type value, -t value specified model type name --type value, -t value specified model type name
--cache, -c generate code with cache [optional] --cache, -c generate code with cache [optional]
--dir value, -d value the target dir --dir value, -d value the target dir
--style value the file naming format, see [https://github.com/tal-tech/go-zero/tree/master/tools/goctl/config/readme.md] --style value the file naming format, see [https://github.com/zeromicro/go-zero/tree/master/tools/goctl/config/readme.md]
``` ```

View File

@@ -6,6 +6,7 @@ import (
"strings" "strings"
"github.com/go-sql-driver/mysql" "github.com/go-sql-driver/mysql"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/core/logx" "github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/core/stores/postgres" "github.com/zeromicro/go-zero/core/stores/postgres"
"github.com/zeromicro/go-zero/core/stores/sqlx" "github.com/zeromicro/go-zero/core/stores/sqlx"
@@ -16,7 +17,6 @@ import (
file "github.com/zeromicro/go-zero/tools/goctl/util" file "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/console" "github.com/zeromicro/go-zero/tools/goctl/util/console"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const ( const (

View File

@@ -3,9 +3,9 @@ package gen
import ( import (
"fmt" "fmt"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/model/sql/template" "github.com/zeromicro/go-zero/tools/goctl/model/sql/template"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const ( const (

View File

@@ -6,6 +6,7 @@ import (
"sort" "sort"
"strings" "strings"
"github.com/zeromicro/ddl-parser/parser"
"github.com/zeromicro/go-zero/core/collection" "github.com/zeromicro/go-zero/core/collection"
"github.com/zeromicro/go-zero/tools/goctl/model/sql/converter" "github.com/zeromicro/go-zero/tools/goctl/model/sql/converter"
"github.com/zeromicro/go-zero/tools/goctl/model/sql/model" "github.com/zeromicro/go-zero/tools/goctl/model/sql/model"
@@ -13,7 +14,6 @@ import (
su "github.com/zeromicro/go-zero/tools/goctl/util" su "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/console" "github.com/zeromicro/go-zero/tools/goctl/util/console"
"github.com/zeromicro/go-zero/tools/goctl/util/stringx" "github.com/zeromicro/go-zero/tools/goctl/util/stringx"
"github.com/zeromicro/ddl-parser/parser"
) )
const timeImport = "time.Time" const timeImport = "time.Time"

View File

@@ -13,11 +13,11 @@ import (
"path/filepath" "path/filepath"
"strings" "strings"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/api/parser" "github.com/zeromicro/go-zero/tools/goctl/api/parser"
"github.com/zeromicro/go-zero/tools/goctl/api/spec" "github.com/zeromicro/go-zero/tools/goctl/api/spec"
"github.com/zeromicro/go-zero/tools/goctl/rpc/execx" "github.com/zeromicro/go-zero/tools/goctl/rpc/execx"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const pluginArg = "_plugin" const pluginArg = "_plugin"

View File

@@ -6,12 +6,12 @@ import (
"path/filepath" "path/filepath"
"runtime" "runtime"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/rpc/generator" "github.com/zeromicro/go-zero/tools/goctl/rpc/generator"
"github.com/zeromicro/go-zero/tools/goctl/util" "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/console" "github.com/zeromicro/go-zero/tools/goctl/util/console"
"github.com/zeromicro/go-zero/tools/goctl/util/env" "github.com/zeromicro/go-zero/tools/goctl/util/env"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
// Deprecated: use ZRPC instead. // Deprecated: use ZRPC instead.

View File

@@ -8,10 +8,10 @@ import (
"strings" "strings"
"github.com/emicklei/proto" "github.com/emicklei/proto"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/rpc/generator" "github.com/zeromicro/go-zero/tools/goctl/rpc/generator"
"github.com/zeromicro/go-zero/tools/goctl/util" "github.com/zeromicro/go-zero/tools/goctl/util"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
var ( var (
@@ -75,18 +75,18 @@ func ZRPC(c *cli.Context) error {
} }
goOut = removePluginFlag(goOut) goOut = removePluginFlag(goOut)
goOut, err = parseOutOut(src, goOut, goOpt, goPackage) goOut, err = parseOut(src, goOut, goOpt, goPackage)
if err != nil { if err != nil {
return err return err
} }
var isGoolePlugin = len(grpcOut) > 0 var isGooglePlugin = len(grpcOut) > 0
// If grpcOut is not empty means that user generates grpc code by // If grpcOut is not empty means that user generates grpc code by
// https://google.golang.org/protobuf/cmd/protoc-gen-go and // https://google.golang.org/protobuf/cmd/protoc-gen-go and
// https://google.golang.org/grpc/cmd/protoc-gen-go-grpc, // https://google.golang.org/grpc/cmd/protoc-gen-go-grpc,
// for details please see https://grpc.io/docs/languages/go/quickstart/ // for details please see https://grpc.io/docs/languages/go/quickstart/
if isGoolePlugin { if isGooglePlugin {
grpcOut, err = parseOutOut(src, grpcOut, grpcOpt, goPackage) grpcOut, err = parseOut(src, grpcOut, grpcOpt, goPackage)
if err != nil { if err != nil {
return err return err
} }
@@ -109,7 +109,7 @@ func ZRPC(c *cli.Context) error {
return err return err
} }
if isGoolePlugin && grpcOut != goOut { if isGooglePlugin && grpcOut != goOut {
return fmt.Errorf("the --go_out and --go-grpc_out must be the same") return fmt.Errorf("the --go_out and --go-grpc_out must be the same")
} }
@@ -136,9 +136,9 @@ func ZRPC(c *cli.Context) error {
return g.Generate(source, zrpcOut, nil) return g.Generate(source, zrpcOut, nil)
} }
// parseOutOut calculates the output place to grpc code, about to calculate logic for details // parseOut calculates the output place to grpc code, about to calculate logic for details
// please see https://developers.google.com/protocol-buffers/docs/reference/go-generated#invocation. // please see https://developers.google.com/protocol-buffers/docs/reference/go-generated#invocation.
func parseOutOut(sourceDir, grpcOut, grpcOpt, goPackage string) (string, error) { func parseOut(sourceDir, grpcOut, grpcOpt, goPackage string) (string, error) {
if !filepath.IsAbs(grpcOut) { if !filepath.IsAbs(grpcOut) {
grpcOut = filepath.Join(sourceDir, grpcOut) grpcOut = filepath.Join(sourceDir, grpcOut)
} }

View File

@@ -3,8 +3,8 @@ package generator
import ( import (
"fmt" "fmt"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx"
) )
const ( const (

View File

@@ -5,6 +5,7 @@ import (
"path/filepath" "path/filepath"
"github.com/logrusorgru/aurora" "github.com/logrusorgru/aurora"
"github.com/urfave/cli"
"github.com/zeromicro/go-zero/core/errorx" "github.com/zeromicro/go-zero/core/errorx"
"github.com/zeromicro/go-zero/tools/goctl/api/apigen" "github.com/zeromicro/go-zero/tools/goctl/api/apigen"
"github.com/zeromicro/go-zero/tools/goctl/api/gogen" "github.com/zeromicro/go-zero/tools/goctl/api/gogen"
@@ -15,7 +16,6 @@ import (
modelgen "github.com/zeromicro/go-zero/tools/goctl/model/sql/gen" modelgen "github.com/zeromicro/go-zero/tools/goctl/model/sql/gen"
rpcgen "github.com/zeromicro/go-zero/tools/goctl/rpc/generator" rpcgen "github.com/zeromicro/go-zero/tools/goctl/rpc/generator"
"github.com/zeromicro/go-zero/tools/goctl/util/pathx" "github.com/zeromicro/go-zero/tools/goctl/util/pathx"
"github.com/urfave/cli"
) )
const templateParentPath = "/" const templateParentPath = "/"

View File

@@ -4,8 +4,8 @@ import (
"fmt" "fmt"
"runtime" "runtime"
"github.com/zeromicro/go-zero/tools/goctl/rpc/execx"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/zeromicro/go-zero/tools/goctl/rpc/execx"
) )
// Upgrade gets the latest goctl by // Upgrade gets the latest goctl by

View File

@@ -15,9 +15,10 @@ import (
// NL defines a new line // NL defines a new line
const ( const (
NL = "\n" NL = "\n"
goctlDir = ".goctl" goctlDir = ".goctl"
gitDir = ".git" gitDir = ".git"
autoCompleteDir = ".auto_complete"
) )
var goctlHome string var goctlHome string
@@ -93,6 +94,16 @@ func GetGitHome() (string, error) {
return filepath.Join(goctlH, gitDir), nil return filepath.Join(goctlH, gitDir), nil
} }
// GetAutoCompleteHome returns the auto_complete home of goctl.
func GetAutoCompleteHome() (string, error) {
goctlH, err := GetGoctlHome()
if err != nil {
return "", err
}
return filepath.Join(goctlH, autoCompleteDir), nil
}
// GetTemplateDir returns the category path value in GoctlHome where could get it by GetGoctlHome // GetTemplateDir returns the category path value in GoctlHome where could get it by GetGoctlHome
func GetTemplateDir(category string) (string, error) { func GetTemplateDir(category string) (string, error) {
home, err := GetGoctlHome() home, err := GetGoctlHome()