Skip to content

Commit 228ba4d

Browse files
committed
MLINE Add validator service
1 parent d928ed3 commit 228ba4d

File tree

14 files changed

+2032
-2
lines changed

14 files changed

+2032
-2
lines changed

code/back/gateway/Makefile

+1-1
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ GOVER=$(shell go version | perl -nle '/(go\d\S+)/; print $$1;')
44
SMARTIMPORTS=${BINDIR}/smartimports_${GOVER}
55
LINTVER=v1.61.0
66
LINTBIN=${BINDIR}/lint_${GOVER}_${LINTVER}
7-
PACKAGE=banks-api/cmd/app
7+
PACKAGE=gateway-api/cmd/app
88

99
all: format build test lint
1010

code/back/integrator/Makefile

+1-1
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ GOVER=$(shell go version | perl -nle '/(go\d\S+)/; print $$1;')
44
SMARTIMPORTS=${BINDIR}/smartimports_${GOVER}
55
LINTVER=v1.61.0
66
LINTBIN=${BINDIR}/lint_${GOVER}_${LINTVER}
7-
PACKAGE=banks-api/cmd/app
7+
PACKAGE=integrator-api/cmd/app
88

99
all: format build test lint
1010

code/back/validator/.gitignore

+4
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
/.idea
2+
/bin
3+
/vendor-proto
4+
.DS_Store

code/back/validator/Makefile

+91
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,91 @@
1+
CURDIR=$(shell pwd)
2+
BINDIR=${CURDIR}/bin
3+
GOVER=$(shell go version | perl -nle '/(go\d\S+)/; print $$1;')
4+
SMARTIMPORTS=${BINDIR}/smartimports_${GOVER}
5+
LINTVER=v1.61.0
6+
LINTBIN=${BINDIR}/lint_${GOVER}_${LINTVER}
7+
PACKAGE=validator-api/cmd/app
8+
9+
all: format build test lint
10+
11+
build: bindir
12+
GOOS=linux GOARCH=amd64 go build -ldflags "-X google.golang.org/protobuf/reflect/protoregistry.conflictPolicy=warn" -o ${BINDIR}/app ${PACKAGE}
13+
14+
test:
15+
GOLANG_PROTOBUF_REGISTRATION_CONFLICT=warn go test ./...
16+
17+
run:
18+
GOLANG_PROTOBUF_REGISTRATION_CONFLICT=warn go run ${PACKAGE}
19+
20+
lint: install-lint
21+
${LINTBIN} run
22+
23+
precommit: format build test lint
24+
echo "OK"
25+
26+
bindir:
27+
mkdir -p ${BINDIR}
28+
29+
format: install-smartimports
30+
${SMARTIMPORTS} -exclude internal/mocks
31+
32+
install-lint: bindir
33+
test -f ${LINTBIN} || \
34+
(GOBIN=${BINDIR} go install github.com/golangci/golangci-lint/cmd/golangci-lint@${LINTVER} && \
35+
mv ${BINDIR}/golangci-lint ${LINTBIN})
36+
37+
install-smartimports: bindir
38+
test -f ${SMARTIMPORTS} || \
39+
(GOBIN=${BINDIR} go install github.com/pav5000/smartimports/cmd/smartimports@latest && \
40+
mv ${BINDIR}/smartimports ${SMARTIMPORTS})
41+
42+
# Используем bin в текущей директории для установки плагинов protoc
43+
LOCAL_BIN:=$(CURDIR)/bin
44+
bin:
45+
GOBIN=$(LOCAL_BIN) go install google.golang.org/protobuf/cmd/protoc-gen-go@latest
46+
GOBIN=$(LOCAL_BIN) go install google.golang.org/grpc/cmd/protoc-gen-go-grpc@latest
47+
GOBIN=$(LOCAL_BIN) go install github.com/grpc-ecosystem/grpc-gateway/v2/protoc-gen-grpc-gateway@latest
48+
GOBIN=$(LOCAL_BIN) go install github.com/envoyproxy/protoc-gen-validate@latest
49+
50+
# Добавляем bin в текущей директории в PATH при запуске protoc
51+
PROTOC = PATH="$$PATH:$(LOCAL_BIN)" protoc
52+
53+
# Устанавливаем proto описания google/googleapis
54+
vendor-proto/google/api:
55+
git clone -b master --single-branch -n --depth=1 --filter=tree:0 \
56+
https://github.com/googleapis/googleapis vendor-proto/googleapis &&\
57+
cd vendor-proto/googleapis &&\
58+
git sparse-checkout set --no-cone google/api &&\
59+
git checkout
60+
mkdir -p vendor-proto/google
61+
mv vendor-proto/googleapis/google/api vendor-proto/google
62+
rm -rf vendor-proto/googleapis
63+
64+
# Устанавливаем proto описания google/protobuf
65+
vendor-proto/google/protobuf:
66+
git clone -b main --single-branch -n --depth=1 --filter=tree:0 \
67+
https://github.com/protocolbuffers/protobuf vendor-proto/protobuf &&\
68+
cd vendor-proto/protobuf &&\
69+
git sparse-checkout set --no-cone src/google/protobuf &&\
70+
git checkout
71+
mkdir -p vendor-proto/google
72+
mv vendor-proto/protobuf/src/google/protobuf vendor-proto/google
73+
rm -rf vendor-proto/protobuf
74+
75+
generate: generate-validator-api
76+
77+
generate-validator-api: bin vendor-proto/google/api vendor-proto/google/protobuf
78+
mkdir -p pkg/validator
79+
$(PROTOC) -I api/validator -I vendor-proto \
80+
--go_out pkg/validator --go_opt paths=source_relative \
81+
--go-grpc_out pkg/validator --go-grpc_opt paths=source_relative \
82+
--grpc-gateway_out pkg/validator --grpc-gateway_opt paths=source_relative \
83+
--validate_out="lang=go,paths=source_relative:pkg/validator" \
84+
api/validator/validator.proto
85+
86+
build-all:
87+
GOOS=linux GOARCH=amd64 make build
88+
89+
run-all: build-all
90+
sudo docker compose up --force-recreate --build
91+
#docker-compose up --force-recreate --build
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
syntax = "proto3";
2+
3+
package validator;
4+
5+
option go_package = "gateway-api/pkg/validator";
6+
7+
import "google/api/annotations.proto";
8+
import "google/protobuf/timestamp.proto";
9+
10+
// ValidatorService предоставляет методы для валидации спецификаций.
11+
service ValidatorService {
12+
// Провалидировать спецификацию.
13+
rpc ValidateSpecification(ValidateSpecificationRequest) returns (ValidationResult) {
14+
option (google.api.http) = {
15+
post: "/validator/specifications/validate"
16+
};
17+
}
18+
19+
rpc GetHello(GetHelloRequest) returns (GetHelloResponse) {
20+
option (google.api.http) = {
21+
get: "/ping"
22+
};
23+
}
24+
}
25+
26+
// Запрос на валидацию спецификации.
27+
message ValidateSpecificationRequest {
28+
Specification specification = 1; // Спецификация для валидации.
29+
}
30+
31+
// Результат валидации.
32+
message ValidationResult {
33+
bool is_valid = 1; // Является ли спецификация валидной.
34+
repeated Error errors = 2; // Список ошибок.
35+
repeated Hint hints = 3; // Список подсказок.
36+
}
37+
38+
message Specification {
39+
int64 id = 1; // Уникальный идентификатор спецификации.
40+
string content = 3; // YAML-контент спецификации.
41+
}
42+
43+
// Ошибка, найденная при валидации.
44+
message Error {
45+
string code = 1; // Код ошибки.
46+
string message = 2; // Описание ошибки.
47+
}
48+
49+
// Подсказка, найденная при валидации.
50+
message Hint {
51+
string message = 1; // Текст подсказки.
52+
}
53+
54+
message GetHelloRequest {}
55+
56+
message GetHelloResponse {
57+
string pong = 1;
58+
}

code/back/validator/cmd/app/main.go

+57
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
package main
2+
3+
import (
4+
"context"
5+
"fmt"
6+
"log"
7+
"net"
8+
9+
"github.com/grpc-ecosystem/grpc-gateway/v2/runtime"
10+
"google.golang.org/grpc"
11+
"google.golang.org/grpc/credentials/insecure"
12+
validator "validator-api/internal/app"
13+
"validator-api/internal/pkg/server"
14+
pbvalidator "validator-api/pkg/validator"
15+
)
16+
17+
const (
18+
httPort = "8080"
19+
grpcPort = "8081"
20+
)
21+
22+
func main() {
23+
ctx := context.Background()
24+
25+
listener, err := net.Listen("tcp", fmt.Sprintf(":%s", grpcPort))
26+
if err != nil {
27+
log.Fatalf("error when listen grpc: %s", err.Error())
28+
}
29+
defer listener.Close()
30+
31+
grpcServer := grpc.NewServer()
32+
integratorHandler := validator.NewValidatorHandler()
33+
pbvalidator.RegisterValidatorServiceServer(grpcServer, integratorHandler)
34+
go func() {
35+
if err := grpcServer.Serve(listener); err != nil {
36+
log.Fatalf("failed when serve: %s", err.Error())
37+
}
38+
}()
39+
40+
gatewayConn, err := grpc.NewClient(
41+
listener.Addr().String(),
42+
grpc.WithTransportCredentials(insecure.NewCredentials()),
43+
)
44+
if err != nil {
45+
log.Fatalf("failed to connect: %s", err.Error())
46+
}
47+
defer gatewayConn.Close()
48+
49+
mux := runtime.NewServeMux()
50+
if err = pbvalidator.RegisterValidatorServiceHandler(ctx, mux, gatewayConn); err != nil {
51+
log.Fatalf("failed to register handler: %s", err.Error())
52+
}
53+
54+
s := server.NewHTTPServer(mux, httPort)
55+
log.Println("launched server at", httPort)
56+
log.Fatal(s.Launch())
57+
}

code/back/validator/go.mod

+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
module validator-api
2+
3+
go 1.23.1
4+
5+
require (
6+
github.com/grpc-ecosystem/grpc-gateway/v2 v2.24.0
7+
google.golang.org/genproto/googleapis/api v0.0.0-20241118233622-e639e219e697
8+
google.golang.org/grpc v1.68.0
9+
google.golang.org/protobuf v1.35.2
10+
)
11+
12+
require (
13+
golang.org/x/net v0.29.0 // indirect
14+
golang.org/x/sys v0.25.0 // indirect
15+
golang.org/x/text v0.20.0 // indirect
16+
google.golang.org/genproto/googleapis/rpc v0.0.0-20241118233622-e639e219e697 // indirect
17+
)

code/back/validator/go.sum

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
github.com/golang/protobuf v1.5.4 h1:i7eJL8qZTpSEXOPTxNKhASYpMn+8e5Q6AdndVa1dWek=
2+
github.com/golang/protobuf v1.5.4/go.mod h1:lnTiLA8Wa4RWRcIUkrtSVa5nRhsEGBg48fD6rSs7xps=
3+
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
4+
github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
5+
github.com/grpc-ecosystem/grpc-gateway/v2 v2.24.0 h1:TmHmbvxPmaegwhDubVz0lICL0J5Ka2vwTzhoePEXsGE=
6+
github.com/grpc-ecosystem/grpc-gateway/v2 v2.24.0/go.mod h1:qztMSjm835F2bXf+5HKAPIS5qsmQDqZna/PgVt4rWtI=
7+
golang.org/x/net v0.29.0 h1:5ORfpBpCs4HzDYoodCDBbwHzdR5UrLBZ3sOnUJmFoHo=
8+
golang.org/x/net v0.29.0/go.mod h1:gLkgy8jTGERgjzMic6DS9+SP0ajcu6Xu3Orq/SpETg0=
9+
golang.org/x/sys v0.25.0 h1:r+8e+loiHxRqhXVl6ML1nO3l1+oFoWbnlu2Ehimmi34=
10+
golang.org/x/sys v0.25.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
11+
golang.org/x/text v0.20.0 h1:gK/Kv2otX8gz+wn7Rmb3vT96ZwuoxnQlY+HlJVj7Qug=
12+
golang.org/x/text v0.20.0/go.mod h1:D4IsuqiFMhST5bX19pQ9ikHC2GsaKyk/oF+pn3ducp4=
13+
google.golang.org/genproto/googleapis/api v0.0.0-20241118233622-e639e219e697 h1:pgr/4QbFyktUv9CtQ/Fq4gzEE6/Xs7iCXbktaGzLHbQ=
14+
google.golang.org/genproto/googleapis/api v0.0.0-20241118233622-e639e219e697/go.mod h1:+D9ySVjN8nY8YCVjc5O7PZDIdZporIDY3KaGfJunh88=
15+
google.golang.org/genproto/googleapis/rpc v0.0.0-20241118233622-e639e219e697 h1:LWZqQOEjDyONlF1H6afSWpAL/znlREo2tHfLoe+8LMA=
16+
google.golang.org/genproto/googleapis/rpc v0.0.0-20241118233622-e639e219e697/go.mod h1:5uTbfoYQed2U9p3KIj2/Zzm02PYhndfdmML0qC3q3FU=
17+
google.golang.org/grpc v1.68.0 h1:aHQeeJbo8zAkAa3pRzrVjZlbz6uSfeOXlJNQM0RAbz0=
18+
google.golang.org/grpc v1.68.0/go.mod h1:fmSPC5AsjSBCK54MyHRx48kpOti1/jRfOlwEWywNjWA=
19+
google.golang.org/protobuf v1.35.2 h1:8Ar7bF+apOIoThw1EdZl0p1oWvMqTHmpA2fRTyZO8io=
20+
google.golang.org/protobuf v1.35.2/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE=
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
package validator
2+
3+
import (
4+
"context"
5+
6+
pbvalidator "validator-api/pkg/validator"
7+
)
8+
9+
type ValidatorHandler struct {
10+
pbvalidator.UnimplementedValidatorServiceServer
11+
}
12+
13+
func NewValidatorHandler() *ValidatorHandler {
14+
return &ValidatorHandler{}
15+
}
16+
17+
func (h *ValidatorHandler) ValidateSpecification(context.Context, *pbvalidator.ValidateSpecificationRequest) (*pbvalidator.ValidationResult, error) {
18+
return &pbvalidator.ValidationResult{
19+
IsValid: true,
20+
Errors: []*pbvalidator.Error{
21+
{
22+
Code: "11",
23+
Message: "Некорректное значение переменной",
24+
},
25+
{
26+
Code: "26",
27+
Message: "Не существует такой команды",
28+
},
29+
},
30+
Hints: []*pbvalidator.Hint{
31+
{
32+
Message: "Вы можете определять alias для переменных",
33+
},
34+
{
35+
Message: "Данный способ определения deprecated",
36+
},
37+
},
38+
}, nil
39+
}
40+
41+
func (h *ValidatorHandler) GetHello(context.Context, *pbvalidator.GetHelloRequest) (*pbvalidator.GetHelloResponse, error) {
42+
return &pbvalidator.GetHelloResponse{
43+
Pong: "pep",
44+
}, nil
45+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
package server
2+
3+
import (
4+
"net/http"
5+
"time"
6+
)
7+
8+
type HTTPServer struct {
9+
server *http.Server
10+
}
11+
12+
func NewHTTPServer(handler http.Handler, port string) *HTTPServer {
13+
return &HTTPServer{
14+
server: &http.Server{
15+
Addr: ":" + port,
16+
Handler: handler,
17+
ReadTimeout: 60 * time.Second,
18+
WriteTimeout: 60 * time.Second,
19+
},
20+
}
21+
}
22+
23+
func (s *HTTPServer) Launch() error {
24+
return s.server.ListenAndServe()
25+
}

0 commit comments

Comments
 (0)