mirror of
https://github.com/go-kratos/kratos.git
synced 2025-01-07 23:02:12 +02:00
parent
5b0b39e3df
commit
7cbb0574b9
19
README.md
19
README.md
@ -58,17 +58,16 @@ kratos new helloworld
|
||||
cd helloworld
|
||||
# 生成proto模板
|
||||
kratos proto add api/helloworld/helloworld.proto
|
||||
# 生成service模板
|
||||
kratos proto service api/helloworld/helloworld.proto -t internal/service
|
||||
# 生成proto源码
|
||||
kratos proto client api/helloworld/helloworld.proto
|
||||
# 生成server模板
|
||||
kratos proto server api/helloworld/helloworld.proto -t internal/service
|
||||
|
||||
# 安装生成工具
|
||||
make init
|
||||
# 生成api下所有proto文件
|
||||
make proto
|
||||
# 编译cmd下所有main文件
|
||||
make build
|
||||
# 进行单元测试
|
||||
make test
|
||||
# 编译成可执行文件
|
||||
cd /cmd/helloworld
|
||||
go build
|
||||
# 运行程序
|
||||
./helloword
|
||||
```
|
||||
|
||||
### Kratos Boot
|
||||
|
19
cmd/kratos/internal/base/get.go
Normal file
19
cmd/kratos/internal/base/get.go
Normal file
@ -0,0 +1,19 @@
|
||||
package base
|
||||
|
||||
import (
|
||||
"os"
|
||||
"os/exec"
|
||||
)
|
||||
|
||||
// GoGet go get path.
|
||||
func GoGet(path ...string) error {
|
||||
for _, p := range path {
|
||||
cmd := exec.Command("go", "get", "-u", p)
|
||||
cmd.Stdout = os.Stdout
|
||||
cmd.Stderr = os.Stderr
|
||||
if err := cmd.Run(); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
@ -1,7 +1,13 @@
|
||||
package base
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"bytes"
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"os/exec"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
|
||||
"golang.org/x/mod/modfile"
|
||||
)
|
||||
@ -14,3 +20,37 @@ func ModulePath(filename string) (string, error) {
|
||||
}
|
||||
return modfile.ModulePath(modBytes), nil
|
||||
}
|
||||
|
||||
// ModuleVersion returns module version.
|
||||
func ModuleVersion(path string) (string, error) {
|
||||
stdout := &bytes.Buffer{}
|
||||
fd := exec.Command("go", "mod", "graph")
|
||||
fd.Stdout = stdout
|
||||
fd.Stderr = stdout
|
||||
if err := fd.Run(); err != nil {
|
||||
return "", err
|
||||
}
|
||||
rd := bufio.NewReader(stdout)
|
||||
for {
|
||||
line, _, err := rd.ReadLine()
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
str := string(line)
|
||||
i := strings.Index(str, "@")
|
||||
if strings.Contains(str, path+"@") && i != -1 {
|
||||
return path + str[i:], nil
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// KratosMod returns kratos mod.
|
||||
func KratosMod() string {
|
||||
gopath := os.Getenv("GOPATH")
|
||||
if path, err := ModuleVersion("github.com/go-kratos/kratos/v2"); err == nil {
|
||||
// $GOPATH/pkg/mod/github.com/go-kratos/kratos@v2
|
||||
return filepath.Join(gopath, "pkg", "mod", path)
|
||||
}
|
||||
// $GOPATH/src/github.com/go-kratos/kratos
|
||||
return filepath.Join(gopath, "src", "github.com", "go-kratos", "kratos")
|
||||
}
|
||||
|
11
cmd/kratos/internal/base/mod_test.go
Normal file
11
cmd/kratos/internal/base/mod_test.go
Normal file
@ -0,0 +1,11 @@
|
||||
package base
|
||||
|
||||
import "testing"
|
||||
|
||||
func TestModuleVersion(t *testing.T) {
|
||||
v, err := ModuleVersion("golang.org/x/mod")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
t.Log(v)
|
||||
}
|
@ -6,11 +6,11 @@ import (
|
||||
)
|
||||
|
||||
func TestRepo(t *testing.T) {
|
||||
r := NewRepo(RepoURL("https://github.com/go-kratos/service-layout.git"))
|
||||
r := NewRepo("https://github.com/go-kratos/service-layout.git")
|
||||
if err := r.Clone(context.Background()); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := r.CopyTo(context.Background(), "/tmp/test_repo"); err != nil {
|
||||
if err := r.CopyTo(context.Background(), "/tmp/test_repo", "github.com/go-kratos/kratos-layout", nil); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
package new
|
||||
package project
|
||||
|
||||
import (
|
||||
"context"
|
||||
@ -18,8 +18,8 @@ type Project struct {
|
||||
Name string
|
||||
}
|
||||
|
||||
// Generate generate template project.
|
||||
func (p *Project) Generate(ctx context.Context, dir string) error {
|
||||
// New new a project from remote repo.
|
||||
func (p *Project) New(ctx context.Context, dir string) error {
|
||||
to := path.Join(dir, p.Name)
|
||||
if _, err := os.Stat(to); !os.IsNotExist(err) {
|
||||
return fmt.Errorf("%s already exists", p.Name)
|
@ -1,4 +1,4 @@
|
||||
package new
|
||||
package project
|
||||
|
||||
import (
|
||||
"context"
|
||||
@ -29,7 +29,7 @@ func run(cmd *cobra.Command, args []string) {
|
||||
return
|
||||
}
|
||||
p := &Project{Name: args[0]}
|
||||
if err := p.Generate(ctx, wd); err != nil {
|
||||
if err := p.New(ctx, wd); err != nil {
|
||||
fmt.Fprintf(os.Stderr, "\033[31mERROR: %s\033[m\n", err)
|
||||
return
|
||||
}
|
83
cmd/kratos/internal/proto/client/client.go
Normal file
83
cmd/kratos/internal/proto/client/client.go
Normal file
@ -0,0 +1,83 @@
|
||||
package client
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"os/exec"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/base"
|
||||
"github.com/spf13/cobra"
|
||||
)
|
||||
|
||||
var (
|
||||
// CmdClient represents the source command.
|
||||
CmdClient = &cobra.Command{
|
||||
Use: "client",
|
||||
Short: "Generate the proto client code",
|
||||
Long: "Generate the proto client code. Example: kratos proto client helloworld.proto",
|
||||
Run: run,
|
||||
}
|
||||
)
|
||||
|
||||
func run(cmd *cobra.Command, args []string) {
|
||||
if len(args) == 0 {
|
||||
fmt.Println("Please enter the proto file or directory")
|
||||
return
|
||||
}
|
||||
var (
|
||||
err error
|
||||
proto = strings.TrimSpace(args[0])
|
||||
)
|
||||
if _, err = exec.LookPath("protoc-gen-go-http"); err != nil {
|
||||
// update the kratos plugins
|
||||
if err := exec.Command("kratos", "upgrade").Run(); err != nil {
|
||||
fmt.Println(err)
|
||||
}
|
||||
}
|
||||
if strings.HasSuffix(proto, ".proto") {
|
||||
err = generate(proto)
|
||||
} else {
|
||||
err = walk(proto)
|
||||
}
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
}
|
||||
}
|
||||
|
||||
func walk(dir string) error {
|
||||
if dir == "" {
|
||||
dir = "."
|
||||
}
|
||||
return filepath.Walk(dir, func(path string, info os.FileInfo, err error) error {
|
||||
if ext := filepath.Ext(path); ext != ".proto" {
|
||||
return nil
|
||||
}
|
||||
return generate(path)
|
||||
})
|
||||
}
|
||||
|
||||
// generate is used to execute the generate command for the specified proto file
|
||||
func generate(proto string) error {
|
||||
path, name := filepath.Split(proto)
|
||||
fd := exec.Command("protoc", []string{
|
||||
"--proto_path=.",
|
||||
"--proto_path=" + filepath.Join(base.KratosMod(), "api"),
|
||||
"--proto_path=" + filepath.Join(base.KratosMod(), "third_party"),
|
||||
"--proto_path=" + filepath.Join(os.Getenv("GOPATH"), "src"),
|
||||
"--go_out=paths=source_relative:.",
|
||||
"--go-grpc_out=paths=source_relative:.",
|
||||
"--go-http_out=paths=source_relative:.",
|
||||
"--go-errors_out=paths=source_relative:.",
|
||||
name,
|
||||
}...)
|
||||
fd.Stdout = os.Stdout
|
||||
fd.Stderr = os.Stderr
|
||||
fd.Dir = path
|
||||
if err := fd.Run(); err != nil {
|
||||
return err
|
||||
}
|
||||
fmt.Printf("proto: %s\n", proto)
|
||||
return nil
|
||||
}
|
@ -2,8 +2,8 @@ package proto
|
||||
|
||||
import (
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/proto/add"
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/proto/service"
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/proto/source"
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/proto/client"
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/proto/server"
|
||||
|
||||
"github.com/spf13/cobra"
|
||||
)
|
||||
@ -18,8 +18,8 @@ var CmdProto = &cobra.Command{
|
||||
|
||||
func init() {
|
||||
CmdProto.AddCommand(add.CmdAdd)
|
||||
CmdProto.AddCommand(source.CmdSource)
|
||||
CmdProto.AddCommand(service.CmdService)
|
||||
CmdProto.AddCommand(client.CmdClient)
|
||||
CmdProto.AddCommand(server.CmdServer)
|
||||
}
|
||||
|
||||
func run(cmd *cobra.Command, args []string) {
|
||||
|
@ -1,4 +1,4 @@
|
||||
package service
|
||||
package server
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
@ -12,22 +12,22 @@ import (
|
||||
"github.com/spf13/cobra"
|
||||
)
|
||||
|
||||
// CmdService represents the service command.
|
||||
var CmdService = &cobra.Command{
|
||||
Use: "service",
|
||||
Short: "Generate the proto Service implementations",
|
||||
Long: "Generate the proto Service implementations. Example: kratos proto service api/xxx.proto -target-dir=internal/service",
|
||||
// CmdServer the service command.
|
||||
var CmdServer = &cobra.Command{
|
||||
Use: "server",
|
||||
Short: "Generate the proto Server implementations",
|
||||
Long: "Generate the proto Server implementations. Example: kratos proto server api/xxx.proto -target-dir=internal/service",
|
||||
Run: run,
|
||||
}
|
||||
var targetDir string
|
||||
|
||||
func init() {
|
||||
CmdService.Flags().StringVarP(&targetDir, "-target-dir", "t", "internal/service", "generate target directory")
|
||||
CmdServer.Flags().StringVarP(&targetDir, "-target-dir", "t", "internal/service", "generate target directory")
|
||||
}
|
||||
|
||||
func run(cmd *cobra.Command, args []string) {
|
||||
if len(args) == 0 {
|
||||
fmt.Fprintln(os.Stderr, "Please specify the proto file. Example: kratos proto service api/xxx.proto")
|
||||
fmt.Fprintln(os.Stderr, "Please specify the proto file. Example: kratos proto server api/xxx.proto")
|
||||
return
|
||||
}
|
||||
reader, err := os.Open(args[0])
|
||||
@ -66,21 +66,23 @@ func run(cmd *cobra.Command, args []string) {
|
||||
res = append(res, cs)
|
||||
}),
|
||||
)
|
||||
if _, err := os.Stat(targetDir); os.IsNotExist(err) {
|
||||
fmt.Printf("Target directory: %s does not exsits\n", targetDir)
|
||||
return
|
||||
}
|
||||
for _, s := range res {
|
||||
to := path.Join(targetDir, strings.ToLower(s.Service)+".go")
|
||||
_, err := os.Stat(to)
|
||||
if !os.IsNotExist(err) {
|
||||
fmt.Fprintf(os.Stderr, "%s already exists\n", s.Service)
|
||||
continue
|
||||
}
|
||||
if err = os.MkdirAll(targetDir, os.ModeDir); err != nil {
|
||||
fmt.Fprintf(os.Stderr, "Failed to create file directory: %s\n", targetDir)
|
||||
if _, err := os.Stat(to); !os.IsNotExist(err) {
|
||||
fmt.Fprintf(os.Stderr, "%s already exists: %s\n", s.Service, to)
|
||||
continue
|
||||
}
|
||||
b, err := s.execute()
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
ioutil.WriteFile(to, b, 0644)
|
||||
if err := ioutil.WriteFile(to, b, 0644); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
fmt.Println(to)
|
||||
}
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package service
|
||||
package server
|
||||
|
||||
import (
|
||||
"bytes"
|
@ -1,28 +0,0 @@
|
||||
package source
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"log"
|
||||
"os/exec"
|
||||
|
||||
"github.com/spf13/cobra"
|
||||
)
|
||||
|
||||
// CmdSource represents the source command.
|
||||
var CmdSource = &cobra.Command{
|
||||
Use: "source",
|
||||
Short: "Generate the proto source code",
|
||||
Long: "Generate the proto source code. Example: kratos proto source ./**/*.proto",
|
||||
Run: run,
|
||||
}
|
||||
|
||||
func run(cmd *cobra.Command, args []string) {
|
||||
input := []string{"--go_out=paths=source_relative:.", "--go-grpc_out=paths=source_relative:."}
|
||||
input = append(input, args...)
|
||||
do := exec.Command("protoc", input...)
|
||||
out, err := do.CombinedOutput()
|
||||
if err != nil {
|
||||
log.Fatalf("failed to execute: %s\n", err)
|
||||
}
|
||||
fmt.Println(string(out))
|
||||
}
|
30
cmd/kratos/internal/upgrade/upgrade.go
Normal file
30
cmd/kratos/internal/upgrade/upgrade.go
Normal file
@ -0,0 +1,30 @@
|
||||
package upgrade
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/base"
|
||||
"github.com/spf13/cobra"
|
||||
)
|
||||
|
||||
// CmdUpgrade represents the upgrade command.
|
||||
var CmdUpgrade = &cobra.Command{
|
||||
Use: "upgrade",
|
||||
Short: "Upgrade the kratos tools",
|
||||
Long: "Upgrade the kratos tools. Example: kratos upgrade",
|
||||
Run: Run,
|
||||
}
|
||||
|
||||
// Run upgrade the kratos tools.
|
||||
func Run(cmd *cobra.Command, args []string) {
|
||||
err := base.GoGet(
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2",
|
||||
"github.com/go-kratos/kratos/cmd/protoc-gen-go-http/v2",
|
||||
"github.com/go-kratos/kratos/cmd/protoc-gen-go-errors/v2",
|
||||
"google.golang.org/protobuf/cmd/protoc-gen-go",
|
||||
"google.golang.org/grpc/cmd/protoc-gen-go-grpc",
|
||||
)
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
}
|
||||
}
|
@ -3,21 +3,28 @@ package main
|
||||
import (
|
||||
"log"
|
||||
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/new"
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/project"
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/proto"
|
||||
"github.com/go-kratos/kratos/cmd/kratos/v2/internal/upgrade"
|
||||
"github.com/spf13/cobra"
|
||||
)
|
||||
|
||||
var rootCmd = &cobra.Command{
|
||||
Use: "kratos",
|
||||
Short: "Kratos: An elegant toolkit for Go microservices.",
|
||||
Long: `Kratos: An elegant toolkit for Go microservices.`,
|
||||
Version: Version,
|
||||
}
|
||||
var (
|
||||
// Version is the version of the compiled software.
|
||||
Version string = "v2.0.0-alpha4"
|
||||
|
||||
rootCmd = &cobra.Command{
|
||||
Use: "kratos",
|
||||
Short: "Kratos: An elegant toolkit for Go microservices.",
|
||||
Long: `Kratos: An elegant toolkit for Go microservices.`,
|
||||
Version: Version,
|
||||
}
|
||||
)
|
||||
|
||||
func init() {
|
||||
rootCmd.AddCommand(new.CmdNew)
|
||||
rootCmd.AddCommand(project.CmdNew)
|
||||
rootCmd.AddCommand(proto.CmdProto)
|
||||
rootCmd.AddCommand(upgrade.CmdUpgrade)
|
||||
}
|
||||
|
||||
func main() {
|
||||
|
@ -1,13 +0,0 @@
|
||||
package main
|
||||
|
||||
// go build -ldflags "-X main.Version=x.y.yz"
|
||||
var (
|
||||
// Version is the version of the compiled software.
|
||||
Version string = "v2.0.0"
|
||||
// Branch is current branch name the code is built off
|
||||
Branch string
|
||||
// Revision is the short commit hash of source tree
|
||||
Revision string
|
||||
// BuildDate is the date when the binary was built.
|
||||
BuildDate string
|
||||
)
|
Loading…
Reference in New Issue
Block a user