-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Add grpc client and server #16
- Loading branch information
Showing
7 changed files
with
291 additions
and
5 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
package main | ||
|
||
import ( | ||
"context" | ||
"log" | ||
|
||
pb "github.com/lc-1010/OneBlogService/proto" | ||
"google.golang.org/grpc" | ||
"google.golang.org/grpc/credentials/insecure" | ||
) | ||
|
||
func main() { | ||
ctx := context.Background() | ||
clientConn, _ := GetClientConn(ctx, "localhost:8004", nil) | ||
defer clientConn.Close() | ||
tagServiceClient := pb.NewTagServiceClient(clientConn) | ||
resp, _ := tagServiceClient.GetTagList(ctx, &pb.GetTagListRequst{Name: "rust"}) | ||
log.Printf("resp:%v", resp) | ||
} | ||
|
||
func GetClientConn(ctx context.Context, target string, opts []grpc.DialOption) (*grpc.ClientConn, error) { | ||
opts = append(opts, grpc.WithTransportCredentials(insecure.NewCredentials())) | ||
return grpc.DialContext(ctx, target, opts...) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,66 @@ | ||
package main | ||
|
||
import ( | ||
"flag" | ||
"log" | ||
"net" | ||
"net/http" | ||
|
||
pb "github.com/lc-1010/OneBlogService/proto" | ||
"github.com/lc-1010/OneBlogService/server" | ||
"google.golang.org/grpc" | ||
"google.golang.org/grpc/reflection" | ||
) | ||
|
||
var grpcPort string | ||
var httpPort string | ||
|
||
func init() { | ||
flag.StringVar(&grpcPort, "grpc_port", "8001", "grpc启动端口") | ||
flag.StringVar(&httpPort, "http_port", "8002", "http启动端口") | ||
flag.Parse() | ||
} | ||
|
||
func RunHttpServer(port string) error { | ||
serveMux := http.NewServeMux() //多路复用 | ||
|
||
serveMux.HandleFunc("/ping", func(w http.ResponseWriter, r *http.Request) { | ||
_, _ = w.Write([]byte(`pong`)) | ||
}) | ||
return http.ListenAndServe(":"+port, serveMux) | ||
} | ||
|
||
func RunGrpcServer(port string) error { | ||
s := grpc.NewServer() | ||
pb.RegisterTagServiceServer(s, server.NewTagServer()) | ||
reflection.Register(s) | ||
lis, err := net.Listen("tcp", ":"+port) | ||
if err != nil { | ||
return err | ||
} | ||
return s.Serve(lis) | ||
} | ||
|
||
// grpcurl -plaintext localhost:8001 proto.TagService.GetTagList | ||
// curl 127.0.0.1:8002/ping | ||
func main() { | ||
|
||
errs := make(chan error) | ||
go func() { | ||
err := RunHttpServer(httpPort) | ||
if err != nil { | ||
errs <- err | ||
} | ||
}() | ||
go func() { | ||
err := RunGrpcServer(grpcPort) | ||
if err != nil { | ||
errs <- err | ||
} | ||
}() | ||
|
||
err := <-errs | ||
if err != nil { | ||
log.Fatalf("Run Server err:%v", err) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
package main | ||
|
||
import ( | ||
"log" | ||
"net" | ||
|
||
pb "github.com/lc-1010/OneBlogService/proto" | ||
"github.com/lc-1010/OneBlogService/server" | ||
"google.golang.org/grpc" | ||
"google.golang.org/grpc/reflection" | ||
) | ||
|
||
var port string | ||
|
||
func main() { | ||
port = "8004" | ||
s := grpc.NewServer() | ||
tag := server.NewTagServer() | ||
pb.RegisterTagServiceServer(s, tag) | ||
reflection.Register(s) | ||
lis, err := net.Listen("tcp", ":"+port) | ||
if err != nil { | ||
log.Fatalf("net.Listen err:%v", err) | ||
|
||
} | ||
err = s.Serve(lis) | ||
if err != nil { | ||
log.Fatalf("serve err:%v", err) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,69 @@ | ||
package blog_api | ||
|
||
import ( | ||
"context" | ||
"encoding/json" | ||
"fmt" | ||
"io/ioutil" | ||
"log" | ||
"net/http" | ||
) | ||
|
||
const ( | ||
APP_KEY = "APP_KEY" | ||
APP_SECRET = "APP_SECRET" | ||
) | ||
|
||
// API blog api sdk | ||
type API struct { | ||
URL string | ||
Client *http.Client | ||
} | ||
|
||
// AccessToken | ||
type AccessToken struct { | ||
Token string `json:"token"` | ||
} | ||
|
||
// NewAPI creates a new API instance. | ||
// | ||
// It takes a URL string as a parameter and returns a pointer to an API object. | ||
func NewAPI(url string) *API { | ||
return &API{URL: url, Client: http.DefaultClient} | ||
} | ||
|
||
func (a *API) getAccessToken(c context.Context) (string, error) { | ||
|
||
body, err := a.httpGet(c, fmt.Sprintf("%s?app_key=%s&app_secret=%s", "auth", APP_KEY, APP_SECRET)) | ||
if err != nil { | ||
return "", err | ||
} | ||
var accessToken AccessToken | ||
_ = json.Unmarshal(body, &accessToken) | ||
return accessToken.Token, nil | ||
} | ||
|
||
// httpGet get function | ||
func (a *API) httpGet(ctx context.Context, path string) ([]byte, error) { | ||
resp, err := http.Get(fmt.Sprintf("%s/%s", a.URL, path)) | ||
if err != nil { | ||
return nil, err | ||
} | ||
defer resp.Body.Close() | ||
body, _ := ioutil.ReadAll(resp.Body) | ||
return body, nil | ||
} | ||
|
||
func (a *API) GetTagList(ctx context.Context, name string) ([]byte, error) { | ||
token, err := a.getAccessToken(ctx) | ||
if err != nil { | ||
log.Println(err) | ||
return nil, err | ||
} | ||
|
||
body, err := a.httpGet(ctx, fmt.Sprintf("%s?token=%s&name=%s", "api/v1/tags", token, name)) | ||
if err != nil { | ||
return nil, err | ||
} | ||
return body, nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
package errcode | ||
|
||
import ( | ||
pb "github.com/lc-1010/OneBlogService/proto" | ||
|
||
"google.golang.org/grpc/codes" | ||
"google.golang.org/grpc/status" | ||
) | ||
|
||
func TogRPCError(err *Error) error { | ||
s, _ := status.New(ToRPCCode(err.Code()), err.Msg()). | ||
WithDetails(&pb.Error{ | ||
Code: int32(err.Code()), | ||
Message: err.Msg()}) | ||
return s.Err() | ||
} | ||
|
||
func ToRPCCode(code int) codes.Code { | ||
var statusCode codes.Code | ||
|
||
switch code { | ||
case ServerError.Code(): | ||
statusCode = codes.Internal | ||
case InvalidParams.Code(): | ||
statusCode = codes.InvalidArgument | ||
case UnauthoerizedTokenError.Code(): | ||
statusCode = codes.Unauthenticated | ||
case UnauthoerizedTokenTimeout.Code(): | ||
statusCode = codes.DeadlineExceeded | ||
case NotFound.Code(): | ||
statusCode = codes.NotFound | ||
case TooManyRequests.Code(): | ||
statusCode = codes.ResourceExhausted | ||
case MethodNotAllowed.Code(): | ||
statusCode = codes.Unimplemented | ||
default: | ||
statusCode = codes.Unknown | ||
|
||
} | ||
return statusCode | ||
} | ||
|
||
type Status struct { | ||
*status.Status | ||
} | ||
|
||
func ToRPCStatus(code int, msg string) *Status { | ||
s, _ := status.New(ToRPCCode((code)), msg). | ||
WithDetails(&pb.Error{Code: int32(code), | ||
Message: msg}) | ||
return &Status{s} | ||
} | ||
|
||
func FromError(err error) *Status { | ||
s, _ := status.FromError(err) | ||
return &Status{s} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,40 @@ | ||
package server | ||
|
||
import ( | ||
"context" | ||
"encoding/json" | ||
|
||
"github.com/lc-1010/OneBlogService/pkg/blog_api" | ||
"github.com/lc-1010/OneBlogService/pkg/errcode" | ||
pb "github.com/lc-1010/OneBlogService/proto" | ||
"google.golang.org/grpc" | ||
"google.golang.org/grpc/credentials/insecure" | ||
) | ||
|
||
type TagService struct { | ||
pb.UnimplementedTagServiceServer | ||
} | ||
|
||
func NewTagServer() *TagService { | ||
return &TagService{} | ||
} | ||
|
||
// GetTagList(context.Context, *GetTagListRequst) (*GetTagListReply, error) | ||
func (t *TagService) GetTagList(c context.Context, r *pb.GetTagListRequst) (*pb.GetTagListReply, error) { | ||
api := blog_api.NewAPI("http://127.0.0.1:8000") | ||
body, err := api.GetTagList(c, r.GetName()) | ||
if err != nil { | ||
return nil, errcode.TogRPCError(errcode.ErrorGetTagListFail) | ||
} | ||
tagList := pb.GetTagListReply{} | ||
err = json.Unmarshal(body, &tagList) | ||
if err != nil { | ||
return nil, errcode.TogRPCError(errcode.ServerError) | ||
} | ||
return &tagList, nil | ||
} | ||
|
||
func GetClientConn(ctx context.Context, target string, opts []grpc.DialOption) (*grpc.ClientConn, error) { | ||
opts = append(opts, grpc.WithTransportCredentials(insecure.NewCredentials())) | ||
return grpc.DialContext(ctx, target, opts...) | ||
} |