This is an automated email from the ASF dual-hosted git repository.

littlecui pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/servicecomb-service-center.git


The following commit(s) were added to refs/heads/master by this push:
     new b69e249f refactor policy validator (#1323)
b69e249f is described below

commit b69e249f68e62f9d560c0c4a4568759e5801b688
Author: Shawn <[email protected]>
AuthorDate: Mon Aug 8 16:55:03 2022 +0800

    refactor policy validator (#1323)
---
 datasource/mongo/ms_test.go                        |  1 -
 .../request/register_intance_json.sh               |  3 +-
 go.sum                                             | 10 +++
 server/bootstrap/bootstrap.go                      |  3 +-
 server/ext/policy/buitin.go                        | 51 +++++++++++++++
 server/resource/gov/gov_resource.go                | 25 ++++----
 server/resource/gov/gov_resource_test.go           | 30 ++++++---
 server/server.go                                   |  4 +-
 server/service/{gov => grc}/config_distributor.go  |  2 +-
 .../{gov => grc}/config_distributor_test.go        | 27 ++++----
 server/service/{gov => grc}/kie/kie_distributor.go | 75 ++++++++--------------
 server/service/{gov => grc}/mock/mock.go           |  8 +--
 server/service/{gov => grc}/policy.go              | 31 +++++----
 server/service/{gov => grc}/policy_test.go         | 12 ++--
 server/service/{gov/kie => grc}/validate.go        | 33 ++++++----
 15 files changed, 191 insertions(+), 124 deletions(-)

diff --git a/datasource/mongo/ms_test.go b/datasource/mongo/ms_test.go
index ae6f99a7..ada39f57 100644
--- a/datasource/mongo/ms_test.go
+++ b/datasource/mongo/ms_test.go
@@ -138,4 +138,3 @@ func TestSyncMicroService(t *testing.T) {
                })
        })
 }
-
diff --git a/examples/service_center/request/register_intance_json.sh 
b/examples/service_center/request/register_intance_json.sh
index da799f61..a21aaf79 100644
--- a/examples/service_center/request/register_intance_json.sh
+++ b/examples/service_center/request/register_intance_json.sh
@@ -27,8 +27,9 @@ Postman-Token: bf33f47f-acfe-76fe-8c53-d1f79a46b246
        "instance": 
        {
            "endpoints": [
-                       "ase://127.0.0.1:99841"
+                       "grpc://127.0.0.1:99841"
                ],
+               "virtualAddress": "xxx.xxx.xxx.local:8080"
                "hostName":"ase",
                "status":"UP",
                "environment":"production",
diff --git a/go.sum b/go.sum
index 3165904f..6590fc44 100644
--- a/go.sum
+++ b/go.sum
@@ -264,6 +264,7 @@ github.com/go-chassis/cari 
v0.0.0-20201210041921-7b6fbef2df11/go.mod h1:MgtsEI0A
 github.com/go-chassis/cari v0.4.0/go.mod 
h1:av/19fqwEP4eOC8unL/z67AAbFDwXUCko6SKa4Avrd8=
 github.com/go-chassis/cari v0.5.0/go.mod 
h1:av/19fqwEP4eOC8unL/z67AAbFDwXUCko6SKa4Avrd8=
 github.com/go-chassis/cari v0.5.1-0.20210823023004-74041d1363c4/go.mod 
h1:av/19fqwEP4eOC8unL/z67AAbFDwXUCko6SKa4Avrd8=
+github.com/go-chassis/cari v0.5.1-0.20220216075429-46c79de3311f/go.mod 
h1:tKTzguHTGohMCgkcWNZWtA4TwfcsJrIXpfYxsQtb7uw=
 github.com/go-chassis/cari v0.6.0 
h1:cwBchwt9L8JOyO6QkzXFAsseMJ10zVSiVK8eDLD0HkA=
 github.com/go-chassis/cari v0.6.0/go.mod 
h1:mSDRCOQXGmlD69A6NG0hsv0UP1xbVPtL6HCGI6X1tqs=
 github.com/go-chassis/foundation v0.2.2-0.20201210043510-9f6d3de40234/go.mod 
h1:2PjwqpVwYEVaAldl5A58a08viH8p27pNeYaiE3ZxOBA=
@@ -272,16 +273,20 @@ github.com/go-chassis/foundation v0.3.0/go.mod 
h1:2PjwqpVwYEVaAldl5A58a08viH8p27
 github.com/go-chassis/foundation v0.4.0 
h1:z0xETnSxF+vRXWjoIhOdzt6rywjZ4sB++utEl4YgWEY=
 github.com/go-chassis/foundation v0.4.0/go.mod 
h1:6NsIUaHghTFRGfCBcZN011zl196F6OR5QvD9N+P4oWU=
 github.com/go-chassis/go-archaius v1.5.1/go.mod 
h1:QPwvvtBxvwiC48rmydoAqxopqOr93RCQ6syWsIkXPXQ=
+github.com/go-chassis/go-archaius v1.5.2-0.20210301074935-e4694f6b077b/go.mod 
h1:qjfG7opNF/QTzj7SyVIn/eIawaPhl7xeGgg8kxzFsDw=
 github.com/go-chassis/go-archaius v1.5.6 
h1:MF/yE9Mj51slccW6EmZInjFCmyfuhltRz9eu5Na4i88=
 github.com/go-chassis/go-archaius v1.5.6/go.mod 
h1:WsqeDyZsCR2qGdWEAEpywS1taxCUHRF4hPSHVMfnAkc=
 github.com/go-chassis/go-chassis-extension/protocol/grpc 
v0.0.0-20220208081606-003611df45da 
h1:DoPFX1Fy3MLEb1RvgchInKspm8DkxQhrvZ5kOcjeZAs=
 github.com/go-chassis/go-chassis-extension/protocol/grpc 
v0.0.0-20220208081606-003611df45da/go.mod 
h1:btid7R4NKuET4BCUkR74CL5EP0hk3J0jXSByjzwd9JM=
 github.com/go-chassis/go-chassis/v2 v2.3.0/go.mod 
h1:iyJ2DWSkqfnCmad/0Il9nXWHaob7RcwPGlIDRNxccH0=
+github.com/go-chassis/go-chassis/v2 
v2.3.1-0.20211217084436-360a6a6a0ef3/go.mod 
h1:oMnRaz2P+OPTtEfh2HEuiF9YzdYHQrNVPXdnbKzKO9w=
 github.com/go-chassis/go-chassis/v2 v2.4.0 
h1:BMmOS2zM/E8KDUoCNpSqalhFsW9fRjwh2Pz5wk1EGC8=
 github.com/go-chassis/go-chassis/v2 v2.4.0/go.mod 
h1:oMnRaz2P+OPTtEfh2HEuiF9YzdYHQrNVPXdnbKzKO9w=
 github.com/go-chassis/go-restful-swagger20 v1.0.3 
h1:kWfeLwMwJZVkXP1zNyFpkmR41UZ55UTcOptTteXhvEs=
 github.com/go-chassis/go-restful-swagger20 v1.0.3/go.mod 
h1:eW62fYuzlNFDvIacB6AV8bhUDCTy4myfTCv0bT9Gbb0=
 github.com/go-chassis/kie-client v0.0.0-20201210060018-938c7680a9ab/go.mod 
h1:UTdbtyN5ge/v9DmQzdVRxQP7z51Q4z6hyl+W6ZpUHFM=
+github.com/go-chassis/kie-client v0.1.0/go.mod 
h1:UTdbtyN5ge/v9DmQzdVRxQP7z51Q4z6hyl+W6ZpUHFM=
+github.com/go-chassis/kie-client v0.1.1-0.20210926011742-97eed4281056/go.mod 
h1:N4SrGTb+e9ZiuOOU9vC/AohqsDtCkY2amNAPcvpEem0=
 github.com/go-chassis/kie-client v0.2.0 
h1:9/BXLu8HaH9b7WLIrtizfhtbBaQEZlsbsk9c8z+mhgc=
 github.com/go-chassis/kie-client v0.2.0/go.mod 
h1:JCyQeOZcr3ti79tc8tix0VzkC2YpB5j7PRbsOmQGcKQ=
 github.com/go-chassis/openlog v1.1.2/go.mod 
h1:+eYCADVxWyJkwsFMUBrMxyQlNqW+UUsCxvR2LrYZUaA=
@@ -620,6 +625,7 @@ github.com/markbates/safe v1.0.1/go.mod 
h1:nAqgmRi7cY2nqMc92/bSEeQA+R4OheNU2T1kN
 github.com/mattn/go-colorable v0.0.9/go.mod 
h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
 github.com/mattn/go-colorable v0.1.4/go.mod 
h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE=
 github.com/mattn/go-colorable v0.1.6/go.mod 
h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc=
+github.com/mattn/go-colorable v0.1.7/go.mod 
h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc=
 github.com/mattn/go-colorable v0.1.9/go.mod 
h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc=
 github.com/mattn/go-colorable v0.1.11/go.mod 
h1:u5H1YNBxpqRaxsYJYSkiCWKzEfiAb1Gb520KVy5xxl4=
 github.com/mattn/go-colorable v0.1.12 
h1:jF+Du6AlPIjs2BiUiQlKOX0rt3SujHxPnksPKZbaA40=
@@ -932,6 +938,8 @@ go.etcd.io/etcd/raft/v3 v3.5.4/go.mod 
h1:SCuunjYvZFC0fBX0vxMSPjuZmpcSk+XaAcMrD6D
 go.etcd.io/etcd/server/v3 v3.5.0/go.mod 
h1:3Ah5ruV+M+7RZr0+Y/5mNLwC+eQlni+mQmOVdCRJoS4=
 go.etcd.io/etcd/server/v3 v3.5.4 
h1:CMAZd0g8Bn5NRhynW6pKhc4FRg41/0QYy3d7aNm9874=
 go.etcd.io/etcd/server/v3 v3.5.4/go.mod 
h1:S5/YTU15KxymM5l3T6b09sNOHPXqGYIZStpuuGbb65c=
+go.mongodb.org/mongo-driver v1.4.2/go.mod 
h1:WcMNYLx/IlOxLe6JRJiv2uXuCz6zBLndR4SoGjYphSc=
+go.mongodb.org/mongo-driver v1.4.6/go.mod 
h1:WcMNYLx/IlOxLe6JRJiv2uXuCz6zBLndR4SoGjYphSc=
 go.mongodb.org/mongo-driver v1.5.1 
h1:9nOVLGDfOaZ9R0tBumx/BcuqkbFpyTCU2r/Po7A2azI=
 go.mongodb.org/mongo-driver v1.5.1/go.mod 
h1:gRXCHX4Jo7J0IJ1oDQyUxF7jfy19UfxniMS4xxMmUqw=
 go.opencensus.io v0.20.1/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk=
@@ -992,6 +1000,7 @@ golang.org/x/crypto 
v0.0.0-20190211182817-74369b46fc67/go.mod h1:6SG95UA2DQfeDnf
 golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod 
h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
 golang.org/x/crypto v0.0.0-20190422162423-af44ce270edf/go.mod 
h1:WFFai1msRO1wXaEeE5yQxYXgSfI8pQAWXbQop6sCtWE=
 golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod 
h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
+golang.org/x/crypto v0.0.0-20190530122614-20be4c3c3ed5/go.mod 
h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
 golang.org/x/crypto v0.0.0-20190605123033-f99c8df09eb5/go.mod 
h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
 golang.org/x/crypto v0.0.0-20190701094942-4def268fd1a4/go.mod 
h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
 golang.org/x/crypto v0.0.0-20190820162420-60c769a6c586/go.mod 
h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
@@ -1001,6 +1010,7 @@ golang.org/x/crypto 
v0.0.0-20191206172530-e9b2fee46413/go.mod h1:LzIPMQfyMNhhGPh
 golang.org/x/crypto v0.0.0-20200302210943-78000ba7a073/go.mod 
h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
 golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod 
h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
 golang.org/x/crypto v0.0.0-20201002170205-7f63de1d35b0/go.mod 
h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
+golang.org/x/crypto v0.0.0-20210421170649-83a5a9bb288b/go.mod 
h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4=
 golang.org/x/crypto v0.0.0-20210513164829-c07d793c2f9a/go.mod 
h1:P+XmwS30IXTQdn5tA2iutPOUgjI07+tq3H3K9MVA1s8=
 golang.org/x/crypto v0.0.0-20210817164053-32db794688a5/go.mod 
h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
 golang.org/x/crypto v0.0.0-20220131195533-30dcbda58838 
h1:71vQrMauZZhcTVK6KdYM+rklehEEwb3E+ZhaE5jrPrE=
diff --git a/server/bootstrap/bootstrap.go b/server/bootstrap/bootstrap.go
index 46cb5b9d..b9aeccc5 100644
--- a/server/bootstrap/bootstrap.go
+++ b/server/bootstrap/bootstrap.go
@@ -60,7 +60,8 @@ import (
        _ "github.com/apache/servicecomb-service-center/server/rest/admin"
 
        //governance
-       _ "github.com/apache/servicecomb-service-center/server/service/gov/kie"
+       _ "github.com/apache/servicecomb-service-center/server/ext/policy"
+       _ "github.com/apache/servicecomb-service-center/server/service/grc/kie"
 
        //metrics
        _ "github.com/apache/servicecomb-service-center/server/rest/metrics"
diff --git a/server/ext/policy/buitin.go b/server/ext/policy/buitin.go
new file mode 100644
index 00000000..ddae6924
--- /dev/null
+++ b/server/ext/policy/buitin.go
@@ -0,0 +1,51 @@
+package policy
+
+import (
+       "github.com/apache/servicecomb-service-center/server/service/grc"
+       "k8s.io/kube-openapi/pkg/validation/spec"
+)
+
+func init() {
+       grc.RegisterPolicySchema("loadbalancer", &spec.Schema{
+               SchemaProps: spec.SchemaProps{
+                       Type:     []string{"object"},
+                       Required: []string{"rule"},
+                       Properties: map[string]spec.Schema{
+                               "rule": {
+                                       SchemaProps: spec.SchemaProps{Type: 
[]string{"string"}}},
+                       },
+               }})
+       grc.RegisterPolicySchema("circuitBreaker", &spec.Schema{
+               SchemaProps: spec.SchemaProps{
+                       Type: []string{"object"},
+                       Properties: map[string]spec.Schema{
+                               "minimumNumberOfCalls": {
+                                       SchemaProps: spec.SchemaProps{Type: 
[]string{"integer"}}},
+                       },
+               }})
+       grc.RegisterPolicySchema("instanceIsolation", &spec.Schema{
+               SchemaProps: spec.SchemaProps{
+                       Type: []string{"object"},
+                       Properties: map[string]spec.Schema{
+                               "minimumNumberOfCalls": {
+                                       SchemaProps: spec.SchemaProps{Type: 
[]string{"integer"}}},
+                       },
+               }})
+       grc.RegisterPolicySchema("faultInjection", &spec.Schema{
+               SchemaProps: spec.SchemaProps{
+                       Type: []string{"object"},
+                       Properties: map[string]spec.Schema{
+                               "percentage": {
+                                       SchemaProps: spec.SchemaProps{Type: 
[]string{"integer"}}},
+                       },
+               }})
+       grc.RegisterPolicySchema("bulkhead", &spec.Schema{
+               SchemaProps: spec.SchemaProps{
+                       Type: []string{"object"},
+                       Properties: map[string]spec.Schema{
+                               "maxConcurrentCalls": {
+                                       SchemaProps: spec.SchemaProps{Type: 
[]string{"integer"}}},
+                       },
+               }})
+
+}
diff --git a/server/resource/gov/gov_resource.go 
b/server/resource/gov/gov_resource.go
index 9a77b32a..ee7cfd49 100644
--- a/server/resource/gov/gov_resource.go
+++ b/server/resource/gov/gov_resource.go
@@ -26,8 +26,7 @@ import (
        model "github.com/apache/servicecomb-service-center/pkg/gov"
        "github.com/apache/servicecomb-service-center/pkg/log"
        "github.com/apache/servicecomb-service-center/pkg/rest"
-       "github.com/apache/servicecomb-service-center/server/service/gov"
-       "github.com/apache/servicecomb-service-center/server/service/gov/kie"
+       "github.com/apache/servicecomb-service-center/server/service/grc"
        "github.com/go-chassis/cari/discovery"
 )
 
@@ -63,15 +62,15 @@ func (t *Governance) Create(w http.ResponseWriter, r 
*http.Request) {
                rest.WriteError(w, discovery.ErrInvalidParams, err.Error())
                return
        }
-       err = gov.ValidateSpec(kind, p.Spec)
+       err = grc.ValidatePolicySpec(kind, p.Spec)
        if err != nil {
-               log.Error("validate policy err", err)
+               log.Error(fmt.Sprintf("validate policy [%s] err", kind), err)
                rest.WriteError(w, discovery.ErrInvalidParams, err.Error())
                return
        }
-       id, err := gov.Create(r.Context(), kind, project, p)
+       id, err := grc.Create(r.Context(), kind, project, p)
        if err != nil {
-               if _, ok := err.(*kie.ErrIllegalItem); ok {
+               if _, ok := err.(*grc.ErrIllegalItem); ok {
                        log.Error("", err)
                        rest.WriteError(w, discovery.ErrInvalidParams, 
err.Error())
                        return
@@ -101,16 +100,16 @@ func (t *Governance) Put(w http.ResponseWriter, r 
*http.Request) {
                rest.WriteError(w, discovery.ErrInvalidParams, err.Error())
                return
        }
-       err = gov.ValidateSpec(kind, p.Spec)
+       err = grc.ValidatePolicySpec(kind, p.Spec)
        if err != nil {
                log.Error("validate policy err", err)
                rest.WriteError(w, discovery.ErrInvalidParams, err.Error())
                return
        }
        log.Info(fmt.Sprintf("update %v", &p))
-       err = gov.Update(r.Context(), kind, id, project, p)
+       err = grc.Update(r.Context(), kind, id, project, p)
        if err != nil {
-               if _, ok := err.(*kie.ErrIllegalItem); ok {
+               if _, ok := err.(*grc.ErrIllegalItem); ok {
                        log.Error("", err)
                        rest.WriteError(w, discovery.ErrInvalidParams, 
err.Error())
                        return
@@ -131,9 +130,9 @@ func (t *Governance) ListOrDisPlay(w http.ResponseWriter, r 
*http.Request) {
        var body []byte
        var err error
        if kind == DisplayKey {
-               body, err = gov.Display(r.Context(), project, app, environment)
+               body, err = grc.Display(r.Context(), project, app, environment)
        } else {
-               body, err = gov.List(r.Context(), kind, project, app, 
environment)
+               body, err = grc.List(r.Context(), kind, project, app, 
environment)
        }
        if err != nil {
                processError(w, err, "list gov err")
@@ -148,7 +147,7 @@ func (t *Governance) Get(w http.ResponseWriter, r 
*http.Request) {
        kind := query.Get(KindKey)
        id := query.Get(IDKey)
        project := query.Get(ProjectKey)
-       body, err := gov.Get(r.Context(), kind, id, project)
+       body, err := grc.Get(r.Context(), kind, id, project)
        if err != nil {
                processError(w, err, "get gov err")
                return
@@ -162,7 +161,7 @@ func (t *Governance) Delete(w http.ResponseWriter, r 
*http.Request) {
        kind := query.Get(KindKey)
        id := query.Get(IDKey)
        project := query.Get(ProjectKey)
-       err := gov.Delete(r.Context(), kind, id, project)
+       err := grc.Delete(r.Context(), kind, id, project)
        if err != nil {
                processError(w, err, "delete gov err")
                return
diff --git a/server/resource/gov/gov_resource_test.go 
b/server/resource/gov/gov_resource_test.go
index d41fa690..aab89cd3 100644
--- a/server/resource/gov/gov_resource_test.go
+++ b/server/resource/gov/gov_resource_test.go
@@ -24,16 +24,20 @@ import (
        "net/http/httptest"
        "testing"
 
+       _ "github.com/apache/servicecomb-service-center/test"
+
        "github.com/apache/servicecomb-service-center/pkg/gov"
        "github.com/apache/servicecomb-service-center/pkg/log"
        "github.com/apache/servicecomb-service-center/pkg/rest"
        "github.com/apache/servicecomb-service-center/server/config"
        v1 "github.com/apache/servicecomb-service-center/server/resource/gov"
-       svc "github.com/apache/servicecomb-service-center/server/service/gov"
+       grcsvc "github.com/apache/servicecomb-service-center/server/service/grc"
        "github.com/go-chassis/go-archaius"
        "github.com/stretchr/testify/assert"
 
-       _ "github.com/apache/servicecomb-service-center/server/service/gov/mock"
+       _ "github.com/apache/servicecomb-service-center/server/service/grc/mock"
+
+       _ "github.com/apache/servicecomb-service-center/server/ext/policy"
 )
 
 func init() {
@@ -44,7 +48,7 @@ func init() {
                        },
                },
        }
-       err := svc.Init()
+       err := grcsvc.Init()
        if err != nil {
                log.Fatal("", err)
        }
@@ -53,19 +57,27 @@ func TestGovernance_Create(t *testing.T) {
        err := archaius.Init(archaius.WithMemorySource(), 
archaius.WithENVSource())
        assert.NoError(t, err)
 
-       svc.Init()
+       grcsvc.Init()
        rest.RegisterServant(&v1.Governance{})
 
-       t.Run("create policy", func(t *testing.T) {
+       t.Run("create load balancing, should success", func(t *testing.T) {
                b, _ := json.Marshal(&gov.Policy{
                        GovernancePolicy: &gov.GovernancePolicy{Name: "test"},
                        Spec: map[string]interface{}{
-                               "backoff": &gov.BackOffPolicy{InitialInterval: 
1}}})
-
-               r, _ := http.NewRequest(http.MethodPost, 
"/v1/default/gov/loadBalancer", bytes.NewBuffer(b))
+                               "rule": "rr",
+                       }})
+               r, _ := http.NewRequest(http.MethodPost, 
"/v1/default/gov/loadbalancer", bytes.NewBuffer(b))
                w := httptest.NewRecorder()
                rest.GetRouter().ServeHTTP(w, r)
                assert.Equal(t, http.StatusOK, w.Code)
        })
-
+       t.Run("create load balancing without rule, should failed", func(t 
*testing.T) {
+               b, _ := json.Marshal(&gov.Policy{
+                       GovernancePolicy: &gov.GovernancePolicy{Name: "test"},
+                       Spec:             map[string]interface{}{}})
+               r, _ := http.NewRequest(http.MethodPost, 
"/v1/default/gov/loadbalancer", bytes.NewBuffer(b))
+               w := httptest.NewRecorder()
+               rest.GetRouter().ServeHTTP(w, r)
+               assert.Equal(t, http.StatusBadRequest, w.Code)
+       })
 }
diff --git a/server/server.go b/server/server.go
index ca3933d4..fbef2fe2 100644
--- a/server/server.go
+++ b/server/server.go
@@ -32,7 +32,7 @@ import (
        "github.com/apache/servicecomb-service-center/server/config"
        "github.com/apache/servicecomb-service-center/server/event"
        
"github.com/apache/servicecomb-service-center/server/plugin/security/tlsconf"
-       "github.com/apache/servicecomb-service-center/server/service/gov"
+       "github.com/apache/servicecomb-service-center/server/service/grc"
        "github.com/apache/servicecomb-service-center/server/service/rbac"
        "github.com/go-chassis/foundation/gopool"
 )
@@ -163,7 +163,7 @@ func (s *ServiceCenterServer) startServices() {
        // load server plugins
        plugin.LoadPlugins()
        rbac.Init()
-       if err := gov.Init(); err != nil {
+       if err := grc.Init(); err != nil {
                log.Fatal("init gov failed", err)
        }
        // check version
diff --git a/server/service/gov/config_distributor.go 
b/server/service/grc/config_distributor.go
similarity index 99%
rename from server/service/gov/config_distributor.go
rename to server/service/grc/config_distributor.go
index 08a25022..4a87d906 100644
--- a/server/service/gov/config_distributor.go
+++ b/server/service/grc/config_distributor.go
@@ -15,7 +15,7 @@
  * limitations under the License.
  */
 
-package gov
+package grc
 
 import (
        "context"
diff --git a/server/service/gov/config_distributor_test.go 
b/server/service/grc/config_distributor_test.go
similarity index 81%
rename from server/service/gov/config_distributor_test.go
rename to server/service/grc/config_distributor_test.go
index 9ed9b643..857e58c1 100644
--- a/server/service/gov/config_distributor_test.go
+++ b/server/service/grc/config_distributor_test.go
@@ -15,18 +15,19 @@
  * limitations under the License.
  */
 
-package gov_test
+package grc_test
 
 import (
        "context"
        "encoding/json"
        "testing"
 
+       "github.com/stretchr/testify/assert"
+
        "github.com/apache/servicecomb-service-center/pkg/gov"
        "github.com/apache/servicecomb-service-center/server/config"
-       svc "github.com/apache/servicecomb-service-center/server/service/gov"
-       _ "github.com/apache/servicecomb-service-center/server/service/gov/mock"
-       "github.com/stretchr/testify/assert"
+       grcsvc "github.com/apache/servicecomb-service-center/server/service/grc"
+       _ "github.com/apache/servicecomb-service-center/server/service/grc/mock"
 )
 
 const Project = "default"
@@ -47,14 +48,14 @@ func init() {
                        },
                },
        }
-       err := svc.Init()
+       err := grcsvc.Init()
        if err != nil {
                panic(err)
        }
 }
 
 func TestCreate(t *testing.T) {
-       res, err := svc.Create(context.TODO(), MockKind, Project, &gov.Policy{
+       res, err := grcsvc.Create(context.TODO(), MockKind, Project, 
&gov.Policy{
                GovernancePolicy: &gov.GovernancePolicy{
                        Name: "Traffic2adminAPI",
                        Selector: gov.Selector{
@@ -70,7 +71,7 @@ func TestCreate(t *testing.T) {
 }
 
 func TestUpdate(t *testing.T) {
-       err := svc.Update(context.TODO(), MockKind, id, Project, &gov.Policy{
+       err := grcsvc.Update(context.TODO(), MockKind, id, Project, &gov.Policy{
                GovernancePolicy: &gov.GovernancePolicy{
                        Name: "Traffic2adminAPI",
                        Selector: gov.Selector{
@@ -84,7 +85,7 @@ func TestUpdate(t *testing.T) {
 }
 
 func TestDisplay(t *testing.T) {
-       res, err := svc.Create(context.TODO(), MatchGroup, Project, &gov.Policy{
+       res, err := grcsvc.Create(context.TODO(), MatchGroup, Project, 
&gov.Policy{
                GovernancePolicy: &gov.GovernancePolicy{
                        Name: "Traffic2adminAPI",
                        Selector: gov.Selector{
@@ -96,7 +97,7 @@ func TestDisplay(t *testing.T) {
        id = string(res)
        assert.NoError(t, err)
        policies := &[]*gov.DisplayData{}
-       res, err = svc.Display(context.TODO(), Project, MockApp, MockEnv)
+       res, err = grcsvc.Display(context.TODO(), Project, MockApp, MockEnv)
        assert.NoError(t, err)
        err = json.Unmarshal(res, policies)
        assert.NoError(t, err)
@@ -105,7 +106,7 @@ func TestDisplay(t *testing.T) {
 
 func TestList(t *testing.T) {
        policies := &[]*gov.Policy{}
-       res, err := svc.List(context.TODO(), MockKind, Project, MockApp, 
MockEnv)
+       res, err := grcsvc.List(context.TODO(), MockKind, Project, MockApp, 
MockEnv)
        assert.NoError(t, err)
        err = json.Unmarshal(res, policies)
        assert.NoError(t, err)
@@ -114,7 +115,7 @@ func TestList(t *testing.T) {
 
 func TestGet(t *testing.T) {
        policy := &gov.Policy{}
-       res, err := svc.Get(context.TODO(), MockKind, id, Project)
+       res, err := grcsvc.Get(context.TODO(), MockKind, id, Project)
        assert.NoError(t, err)
        err = json.Unmarshal(res, policy)
        assert.NoError(t, err)
@@ -122,8 +123,8 @@ func TestGet(t *testing.T) {
 }
 
 func TestDelete(t *testing.T) {
-       err := svc.Delete(context.TODO(), MockKind, id, Project)
+       err := grcsvc.Delete(context.TODO(), MockKind, id, Project)
        assert.NoError(t, err)
-       res, _ := svc.Get(context.TODO(), MockKind, id, Project)
+       res, _ := grcsvc.Get(context.TODO(), MockKind, id, Project)
        assert.Nil(t, res)
 }
diff --git a/server/service/gov/kie/kie_distributor.go 
b/server/service/grc/kie/kie_distributor.go
similarity index 86%
rename from server/service/gov/kie/kie_distributor.go
rename to server/service/grc/kie/kie_distributor.go
index 40899952..c0be5fbd 100644
--- a/server/service/gov/kie/kie_distributor.go
+++ b/server/service/grc/kie/kie_distributor.go
@@ -26,14 +26,15 @@ import (
        "strings"
        "time"
 
+       "github.com/ghodss/yaml"
+       "github.com/go-chassis/foundation/httpclient"
+       "github.com/go-chassis/kie-client"
+
        "github.com/apache/servicecomb-service-center/pkg/gov"
        "github.com/apache/servicecomb-service-center/pkg/log"
        "github.com/apache/servicecomb-service-center/server/config"
-       svc "github.com/apache/servicecomb-service-center/server/service/gov"
+       grcsvc "github.com/apache/servicecomb-service-center/server/service/grc"
        rbacsvc 
"github.com/apache/servicecomb-service-center/server/service/rbac"
-       "github.com/ghodss/yaml"
-       "github.com/go-chassis/foundation/httpclient"
-       "github.com/go-chassis/kie-client"
 )
 
 type Distributor struct {
@@ -41,21 +42,6 @@ type Distributor struct {
        client *kie.Client
 }
 
-const (
-       KeyPrefix       = "servicecomb."
-       KindMatchGroup  = "match-group"
-       GroupNamePrefix = "scene-"
-       StatusEnabled   = "enabled"
-       TypeText        = "text"
-       KeyApp          = "app"
-       KeyEnvironment  = "environment"
-       EnvAll          = "all"
-       Alias           = "alias"
-       Method          = "method"
-       Matches         = "matches"
-       Rules           = "rules"
-)
-
 var PolicyNames = []string{
        "retry",
        "rateLimiting",
@@ -66,21 +52,14 @@ var PolicyNames = []string{
        "loadbalancer",
 }
 
-var rule = Validator{}
-
 func (d *Distributor) Create(ctx context.Context, kind, project string, p 
*gov.Policy) ([]byte, error) {
-       if kind == KindMatchGroup {
+       if kind == grcsvc.KindMatchGroup {
                err := d.generateID(ctx, project, p)
                if err != nil {
                        return nil, err
                }
        }
-
-       err := rule.Validate(kind, p.Spec)
-       if err != nil {
-               return nil, err
-       }
-       if kind == KindMatchGroup {
+       if kind == grcsvc.KindMatchGroup {
                setAliasIfEmpty(p.Spec, p.Name)
        }
        yamlByte, err := yaml.Marshal(p.Spec)
@@ -90,8 +69,8 @@ func (d *Distributor) Create(ctx context.Context, kind, 
project string, p *gov.P
        kv := kie.KVRequest{
                Key:       toGovKeyPrefix(kind) + p.Name,
                Value:     string(yamlByte),
-               Status:    StatusEnabled,
-               ValueType: TypeText,
+               Status:    grcsvc.StatusEnabled,
+               ValueType: grcsvc.TypeText,
                Labels:    p.Selector,
        }
        res, err := d.client.Create(ctx, kv, kie.WithProject(project))
@@ -103,11 +82,7 @@ func (d *Distributor) Create(ctx context.Context, kind, 
project string, p *gov.P
 }
 
 func (d *Distributor) Update(ctx context.Context, kind, id, project string, p 
*gov.Policy) error {
-       err := rule.Validate(kind, p.Spec)
-       if err != nil {
-               return err
-       }
-       if kind == KindMatchGroup {
+       if kind == grcsvc.KindMatchGroup {
                setAliasIfEmpty(p.Spec, p.Name)
        }
        yamlByte, err := yaml.Marshal(p.Spec)
@@ -128,7 +103,7 @@ func (d *Distributor) Update(ctx context.Context, kind, id, 
project string, p *g
 }
 
 func (d *Distributor) Delete(ctx context.Context, kind, id, project string) 
error {
-       if kind == KindMatchGroup {
+       if kind == grcsvc.KindMatchGroup {
                // should remove all policies of this group
                return d.DeleteMatchGroup(ctx, id, project)
        }
@@ -142,14 +117,14 @@ func (d *Distributor) Delete(ctx context.Context, kind, 
id, project string) erro
 }
 
 func (d *Distributor) DeleteMatchGroup(ctx context.Context, id string, project 
string) error {
-       policy, err := d.getPolicy(ctx, KindMatchGroup, id, project)
+       policy, err := d.getPolicy(ctx, grcsvc.KindMatchGroup, id, project)
        if err != nil {
                log.Error("kie get failed", err)
                return err
        }
 
        ops := []kie.GetOption{
-               kie.WithKey("wildcard(" + KeyPrefix + "*." + policy.Name + ")"),
+               kie.WithKey("wildcard(" + grcsvc.KeyPrefix + "*." + policy.Name 
+ ")"),
                kie.WithLabels(policy.Selector),
                kie.WithRevision(0),
                kie.WithGetProject(project),
@@ -176,7 +151,7 @@ func (d *Distributor) DeleteMatchGroup(ctx context.Context, 
id string, project s
 }
 
 func (d *Distributor) Display(ctx context.Context, project, app, env string) 
([]byte, error) {
-       list, _, err := d.listDataByKind(ctx, KindMatchGroup, project, app, env)
+       list, _, err := d.listDataByKind(ctx, grcsvc.KindMatchGroup, project, 
app, env)
        if err != nil {
                return nil, err
        }
@@ -197,7 +172,7 @@ func (d *Distributor) Display(ctx context.Context, project, 
app, env string) ([]
        }
        r := make([]*gov.DisplayData, 0, list.Total)
        for _, item := range list.Data {
-               match, err := d.transform(item, KindMatchGroup)
+               match, err := d.transform(item, grcsvc.KindMatchGroup)
                if err != nil {
                        log.Warn(fmt.Sprintf("transform config failed: key is 
[%s], value is [%s]", item.Key, item.Value))
                        continue
@@ -270,7 +245,7 @@ func (d *Distributor) getPolicy(ctx context.Context, kind 
string, id string, pro
 }
 
 func (d *Distributor) Type() string {
-       return svc.ConfigDistributorKie
+       return grcsvc.ConfigDistributorKie
 }
 func (d *Distributor) Name() string {
        return d.name
@@ -290,7 +265,7 @@ func initClient(endpoint string) *kie.Client {
        return client
 }
 
-func new(opts config.DistributorOptions) (svc.ConfigDistributor, error) {
+func new(opts config.DistributorOptions) (grcsvc.ConfigDistributor, error) {
        return &Distributor{name: opts.Name, client: 
initClient(opts.Endpoint)}, nil
 }
 
@@ -323,11 +298,11 @@ func (d *Distributor) listDataByKind(ctx context.Context, 
kind, project, app, en
                kie.WithGetProject(project),
        }
        labels := map[string]string{}
-       if env != EnvAll {
-               labels[KeyEnvironment] = env
+       if env != grcsvc.EnvAll {
+               labels[grcsvc.KeyEnvironment] = env
        }
        if app != "" {
-               labels[KeyApp] = app
+               labels[grcsvc.KeyApp] = app
        }
        if len(labels) > 0 {
                ops = append(ops, kie.WithLabels(labels))
@@ -344,8 +319,8 @@ func (d *Distributor) generateID(ctx context.Context, 
project string, p *gov.Pol
        if p.Name != "" {
                return nil
        }
-       kind := KindMatchGroup
-       list, _, err := d.listDataByKind(ctx, kind, project, 
p.Selector[KeyApp], p.Selector[KeyEnvironment])
+       kind := grcsvc.KindMatchGroup
+       list, _, err := d.listDataByKind(ctx, kind, project, 
p.Selector[grcsvc.KeyApp], p.Selector[grcsvc.KeyEnvironment])
        if err != nil {
                return err
        }
@@ -376,7 +351,7 @@ func getID() string {
        for i := 0; i < 4; i++ {
                result = append(result, b[r.Intn(len(b))])
        }
-       return GroupNamePrefix + string(result)
+       return grcsvc.GroupNamePrefix + string(result)
 }
 
 func (d *Distributor) transform(kv *kie.KVDoc, kind string) (*gov.Policy, 
error) {
@@ -404,9 +379,9 @@ func (d *Distributor) transform(kv *kie.KVDoc, kind string) 
(*gov.Policy, error)
 }
 
 func toGovKeyPrefix(kind string) string {
-       return KeyPrefix + toSnake(kind) + "."
+       return grcsvc.KeyPrefix + toSnake(kind) + "."
 }
 
 func init() {
-       svc.InstallDistributor(svc.ConfigDistributorKie, new)
+       grcsvc.InstallDistributor(grcsvc.ConfigDistributorKie, new)
 }
diff --git a/server/service/gov/mock/mock.go b/server/service/grc/mock/mock.go
similarity index 93%
rename from server/service/gov/mock/mock.go
rename to server/service/grc/mock/mock.go
index 7ec32eda..0636c34d 100644
--- a/server/service/gov/mock/mock.go
+++ b/server/service/grc/mock/mock.go
@@ -27,7 +27,7 @@ import (
 
        "github.com/apache/servicecomb-service-center/pkg/gov"
        "github.com/apache/servicecomb-service-center/server/config"
-       svc "github.com/apache/servicecomb-service-center/server/service/gov"
+       grcsvc "github.com/apache/servicecomb-service-center/server/service/grc"
 )
 
 type Distributor struct {
@@ -126,14 +126,14 @@ func (d *Distributor) Get(ctx context.Context, kind, id, 
project string) ([]byte
 }
 
 func (d *Distributor) Type() string {
-       return svc.ConfigDistributorMock
+       return grcsvc.ConfigDistributorMock
 }
 func (d *Distributor) Name() string {
        return d.name
 }
-func new(opts config.DistributorOptions) (svc.ConfigDistributor, error) {
+func new(opts config.DistributorOptions) (grcsvc.ConfigDistributor, error) {
        return &Distributor{name: opts.Name, lbPolicies: 
map[string]*gov.Policy{}}, nil
 }
 func init() {
-       svc.InstallDistributor(svc.ConfigDistributorMock, new)
+       grcsvc.InstallDistributor(grcsvc.ConfigDistributorMock, new)
 }
diff --git a/server/service/gov/policy.go b/server/service/grc/policy.go
similarity index 61%
rename from server/service/gov/policy.go
rename to server/service/grc/policy.go
index c9dbfec9..03791b0b 100644
--- a/server/service/gov/policy.go
+++ b/server/service/grc/policy.go
@@ -15,7 +15,8 @@
  * limitations under the License.
  */
 
-package gov
+//Package grc include API of governance(grc is the abbreviation of governance)
+package grc
 
 import (
        "errors"
@@ -32,21 +33,29 @@ import (
 
 type ValueType string
 
-//policies saves kind and policy schemas
-var policies = make(map[string]*spec.Schema)
+//policySchemas saves policy kind and schema
+var policySchemas = make(map[string]*spec.Schema)
 
-//RegisterPolicy register a contract of one kind of policy
+//RegisterPolicySchema register a contract of one kind of policy
 //this API is not thread safe, only use it during sc init
-func RegisterPolicy(kind string, schema *spec.Schema) {
-       policies[kind] = schema
+func RegisterPolicySchema(kind string, schema *spec.Schema) {
+       policySchemas[kind] = schema
+       log.Info("register policy schema: " + kind)
 }
 
-//ValidateSpec validates spec attributes
-func ValidateSpec(kind string, spec interface{}) error {
-       schema, ok := policies[kind]
+// ValidatePolicySpec validates spec attributes
+// it first us legacy mechanism Validate 3 kinds of policy.
+// then it use new mechanism to validate all of other policy
+func ValidatePolicySpec(kind string, spec interface{}) error {
+       // TODO this legacy API should be removed. after 3 kinds of policy 
schema is registered by "RegisterPolicySchema"
+       err := Validate(kind, spec)
+       if err != nil {
+               return err
+       }
+       schema, ok := policySchemas[kind]
        if !ok {
-               log.Warn(fmt.Sprintf("can not recognize %s", kind))
-               return nil
+               log.Warn(fmt.Sprintf("can not recognize policy %s", kind))
+               return &ErrIllegalItem{"not support kind yet", kind}
        }
        validator := validate.NewSchemaValidator(schema, nil, "", 
strfmt.Default)
        errs := validator.Validate(spec).Errors
diff --git a/server/service/gov/policy_test.go 
b/server/service/grc/policy_test.go
similarity index 87%
rename from server/service/gov/policy_test.go
rename to server/service/grc/policy_test.go
index 46ddd98b..610a1513 100644
--- a/server/service/gov/policy_test.go
+++ b/server/service/grc/policy_test.go
@@ -15,14 +15,14 @@
  * limitations under the License.
  */
 
-package gov_test
+package grc_test
 
 import (
+       "github.com/apache/servicecomb-service-center/server/service/grc"
        "testing"
 
        "k8s.io/kube-openapi/pkg/validation/spec"
 
-       "github.com/apache/servicecomb-service-center/server/service/gov"
        "github.com/stretchr/testify/assert"
 )
 
@@ -45,9 +45,9 @@ func TestPolicySchema_Validate(t *testing.T) {
                                                SchemaProps: 
spec.SchemaProps{Type: []string{"integer"}}},
                                },
                        }}
-               gov.RegisterPolicy("custom", schema)
+               grc.RegisterPolicySchema("custom", schema)
                t.Run("given right content, should no error", func(t 
*testing.T) {
-                       err := gov.ValidateSpec("custom", 
map[string]interface{}{
+                       err := grc.ValidatePolicySpec("custom", 
map[string]interface{}{
                                "allow":   true,
                                "timeout": "5s",
                                "name":    "a",
@@ -58,7 +58,7 @@ func TestPolicySchema_Validate(t *testing.T) {
                        assert.NoError(t, err)
                })
                t.Run("given value with wrong type, should return error", 
func(t *testing.T) {
-                       err := gov.ValidateSpec("custom", 
map[string]interface{}{
+                       err := grc.ValidatePolicySpec("custom", 
map[string]interface{}{
                                "allow":   "str",
                                "timeout": "5s",
                                "name":    "a",
@@ -69,7 +69,7 @@ func TestPolicySchema_Validate(t *testing.T) {
                        assert.Error(t, err)
                })
                t.Run("do not give required value, should return error", func(t 
*testing.T) {
-                       err := gov.ValidateSpec("custom", 
map[string]interface{}{
+                       err := grc.ValidatePolicySpec("custom", 
map[string]interface{}{
                                "allow":   true,
                                "timeout": "5s",
                                "age":     10,
diff --git a/server/service/gov/kie/validate.go b/server/service/grc/validate.go
similarity index 82%
rename from server/service/gov/kie/validate.go
rename to server/service/grc/validate.go
index b487af65..f19c40df 100644
--- a/server/service/gov/kie/validate.go
+++ b/server/service/grc/validate.go
@@ -15,14 +15,26 @@
  * limitations under the License.
  */
 
-package kie
+package grc
 
 import (
        "fmt"
 )
 
-type Validator struct {
-}
+const (
+       KeyPrefix       = "servicecomb."
+       KindMatchGroup  = "match-group"
+       GroupNamePrefix = "scene-"
+       StatusEnabled   = "enabled"
+       TypeText        = "text"
+       KeyApp          = "app"
+       KeyEnvironment  = "environment"
+       EnvAll          = "all"
+       Alias           = "alias"
+       Method          = "method"
+       Matches         = "matches"
+       Rules           = "rules"
+)
 
 type ErrIllegalItem struct {
        err string
@@ -37,7 +49,11 @@ func (e *ErrIllegalItem) Error() string {
        return fmt.Sprintf("illegal item : %v , msg: %s", e.val, e.err)
 }
 
-func (d *Validator) Validate(kind string, spec interface{}) error {
+// Validate is a legacy API, it is not extensible due to its bad design pattern
+// Please use grc.RegisterPolicySchema
+// it only response for validate 3 kinds of policy. if it is not this 3 kinds, 
it will not return error,
+// it return nil error, and let grc.ValidatePolicySpec to do the job
+func Validate(kind string, spec interface{}) error {
        switch kind {
        case "match-group":
                return matchValidate(spec)
@@ -45,16 +61,9 @@ func (d *Validator) Validate(kind string, spec interface{}) 
error {
                return retryValidate(spec)
        case "rate-limiting":
                return rateLimitingValidate(spec)
-       case "circuit-breaker":
-       case "instance-isolation":
-       case "fault-injection":
-       case "bulkhead":
-       case "loadbalancer":
-               return nil
        default:
-               return &ErrIllegalItem{"not support kind yet", kind}
+               return nil
        }
-       return nil
 }
 
 func matchValidate(val interface{}) error {

Reply via email to