From 48a025b257c040f05eb97e8c643306c1f9d1d2a4 Mon Sep 17 00:00:00 2001 From: huanggze Date: Wed, 19 Jun 2019 20:17:13 +0800 Subject: [PATCH 1/6] fix: update metrics for node disk usage and capacity Signed-off-by: huanggze --- pkg/models/metrics/metricsruleconst.go | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/pkg/models/metrics/metricsruleconst.go b/pkg/models/metrics/metricsruleconst.go index 449d2f2bc..d14a2aeb1 100644 --- a/pkg/models/metrics/metricsruleconst.go +++ b/pkg/models/metrics/metricsruleconst.go @@ -400,10 +400,10 @@ var RulePromQLTmplMap = MetricMap{ "cluster_disk_read_throughput": "sum(node:data_volume_throughput_bytes_read:sum)", "cluster_disk_write_throughput": "sum(node:data_volume_throughput_bytes_written:sum)", - "cluster_disk_size_usage": `sum(max(node_filesystem_size_bytes{device=~"/dev/[vsh]d.+", job="node-exporter"} - node_filesystem_avail_bytes{device=~"/dev/[vsh]d.+", job="node-exporter"}) by (device, instance))`, + "cluster_disk_size_usage": `sum(max(node_filesystem_size_bytes{device=~"/dev/.*", job="node-exporter"} - node_filesystem_avail_bytes{device=~"/dev/.*", job="node-exporter"}) by (device, instance))`, "cluster_disk_size_utilisation": `cluster:disk_utilization:ratio`, - "cluster_disk_size_capacity": `sum(max(node_filesystem_size_bytes{device=~"/dev/[vsh]d.+", job="node-exporter"}) by (device, instance))`, - "cluster_disk_size_available": `sum(max(node_filesystem_avail_bytes{device=~"/dev/[vsh]d.+", job="node-exporter"}) by (device, instance))`, + "cluster_disk_size_capacity": `sum(max(node_filesystem_size_bytes{device=~"/dev/.*", job="node-exporter"}) by (device, instance))`, + "cluster_disk_size_available": `sum(max(node_filesystem_avail_bytes{device=~"/dev/.*", job="node-exporter"}) by (device, instance))`, "cluster_disk_inode_total": `sum(node:node_inodes_total:)`, "cluster_disk_inode_usage": `sum(node:node_inodes_total:) - sum(node:node_inodes_free:)`, @@ -481,9 +481,9 @@ var RulePromQLTmplMap = MetricMap{ "node_disk_read_throughput": "node:data_volume_throughput_bytes_read:sum", "node_disk_write_throughput": "node:data_volume_throughput_bytes_written:sum", - "node_disk_size_capacity": `sum(max(node_filesystem_size_bytes{device=~"/dev/[vsh]d.+", job="node-exporter"} * on (namespace, pod) group_left(node) node_namespace_pod:kube_pod_info:$1) by (device, node)) by (node)`, + "node_disk_size_capacity": `sum(max(node_filesystem_size_bytes{device=~"/dev/.*", job="node-exporter"} * on (namespace, pod) group_left(node) node_namespace_pod:kube_pod_info:$1) by (device, node)) by (node)`, "node_disk_size_available": `node:disk_space_available:$1`, - "node_disk_size_usage": `sum(max((node_filesystem_size_bytes{device=~"/dev/[vsh]d.+", job="node-exporter"} - node_filesystem_avail_bytes{device=~"/dev/[vsh]d.+", job="node-exporter"}) * on (namespace, pod) group_left(node) node_namespace_pod:kube_pod_info:$1) by (device, node)) by (node)`, + "node_disk_size_usage": `sum(max((node_filesystem_size_bytes{device=~"/dev/.*", job="node-exporter"} - node_filesystem_avail_bytes{device=~"/dev/.*", job="node-exporter"}) * on (namespace, pod) group_left(node) node_namespace_pod:kube_pod_info:$1) by (device, node)) by (node)`, "node_disk_size_utilisation": `node:disk_space_utilization:ratio$1`, "node_disk_inode_total": `node:node_inodes_total:$1`, From 4283814a6853d25b22a0639dbb4266b7da34821f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E4=B8=8D=E7=BE=81?= Date: Thu, 20 Jun 2019 16:23:24 +0800 Subject: [PATCH 2/6] fix: get application details failed (#481) Signed-off-by: hongming --- cmd/ks-iam/app/options/options.go | 2 + cmd/ks-iam/app/server.go | 2 +- pkg/apis/iam/v1alpha2/register.go | 2 +- pkg/apiserver/iam/auth.go | 6 +- .../namespace/namespace_controller.go | 2 +- pkg/models/applications/applications.go | 15 ++++ pkg/models/iam/im.go | 71 ++++++++++++++++--- pkg/models/resources/nodes.go | 6 ++ pkg/models/resources/resources.go | 1 + 9 files changed, 94 insertions(+), 13 deletions(-) diff --git a/cmd/ks-iam/app/options/options.go b/cmd/ks-iam/app/options/options.go index 9de464ec6..85c678447 100644 --- a/cmd/ks-iam/app/options/options.go +++ b/cmd/ks-iam/app/options/options.go @@ -28,6 +28,7 @@ type ServerRunOptions struct { AdminPassword string TokenExpireTime string JWTSecret string + AuthRateLimit string } func NewServerRunOptions() *ServerRunOptions { @@ -42,5 +43,6 @@ func (s *ServerRunOptions) AddFlags(fs *pflag.FlagSet) { fs.StringVar(&s.AdminPassword, "admin-password", "passw0rd", "default administrator's password") fs.StringVar(&s.TokenExpireTime, "token-expire-time", "2h", "token expire time,valid time units are \"ns\",\"us\",\"ms\",\"s\",\"m\",\"h\"") fs.StringVar(&s.JWTSecret, "jwt-secret", "", "jwt secret") + fs.StringVar(&s.AuthRateLimit, "auth-rate-limit", "5/30m", "specifies the maximum number of authentication attempts permitted and time interval,valid time units are \"s\",\"m\",\"h\"") s.GenericServerRunOptions.AddFlags(fs) } diff --git a/cmd/ks-iam/app/server.go b/cmd/ks-iam/app/server.go index cd9e31c6d..17239a7ba 100644 --- a/cmd/ks-iam/app/server.go +++ b/cmd/ks-iam/app/server.go @@ -75,7 +75,7 @@ func Run(s *options.ServerRunOptions) error { initializeAdminJenkins() initializeDevOpsDatabase() - err = iam.Init(s.AdminEmail, s.AdminPassword, expireTime) + err = iam.Init(s.AdminEmail, s.AdminPassword, expireTime, s.AuthRateLimit) jwtutil.Setup(s.JWTSecret) if err != nil { diff --git a/pkg/apis/iam/v1alpha2/register.go b/pkg/apis/iam/v1alpha2/register.go index 719dd0007..0771f0c5b 100644 --- a/pkg/apis/iam/v1alpha2/register.go +++ b/pkg/apis/iam/v1alpha2/register.go @@ -116,7 +116,7 @@ func addWebService(c *restful.Container) error { Returns(http.StatusOK, ok, iam.TokenReview{}). Metadata(restfulspec.KeyOpenAPITags, tags)) ws.Route(ws.POST("/login"). - To(iam.LoginHandler). + To(iam.Login). Doc("KubeSphere APIs support token-based authentication via the Authtoken request header. The POST Login API is used to retrieve the authentication token. After the authentication token is obtained, it must be inserted into the Authtoken header for all requests."). Reads(iam.LoginRequest{}). Returns(http.StatusOK, ok, models.Token{}). diff --git a/pkg/apiserver/iam/auth.go b/pkg/apiserver/iam/auth.go index 49245654e..2a0cde349 100644 --- a/pkg/apiserver/iam/auth.go +++ b/pkg/apiserver/iam/auth.go @@ -55,7 +55,7 @@ const ( KindTokenReview = "TokenReview" ) -func LoginHandler(req *restful.Request, resp *restful.Response) { +func Login(req *restful.Request, resp *restful.Response) { var loginRequest LoginRequest err := req.ReadEntity(&loginRequest) @@ -70,6 +70,10 @@ func LoginHandler(req *restful.Request, resp *restful.Response) { token, err := iam.Login(loginRequest.Username, loginRequest.Password, ip) if err != nil { + if serviceError, ok := err.(restful.ServiceError); ok { + resp.WriteHeaderAndEntity(serviceError.Code, errors.New(serviceError.Message)) + return + } resp.WriteHeaderAndEntity(http.StatusUnauthorized, errors.Wrap(err)) return } diff --git a/pkg/controller/namespace/namespace_controller.go b/pkg/controller/namespace/namespace_controller.go index 81917aa44..b9035d658 100644 --- a/pkg/controller/namespace/namespace_controller.go +++ b/pkg/controller/namespace/namespace_controller.go @@ -60,7 +60,7 @@ var ( defaultRoles = []rbac.Role{ {ObjectMeta: metav1.ObjectMeta{Name: "admin", Annotations: map[string]string{constants.DescriptionAnnotationKey: adminDescription, constants.CreatorAnnotationKey: constants.System}}, Rules: []rbac.PolicyRule{{Verbs: []string{"*"}, APIGroups: []string{"*"}, Resources: []string{"*"}}}}, {ObjectMeta: metav1.ObjectMeta{Name: "operator", Annotations: map[string]string{constants.DescriptionAnnotationKey: operatorDescription, constants.CreatorAnnotationKey: constants.System}}, Rules: []rbac.PolicyRule{{Verbs: []string{"get", "list", "watch"}, APIGroups: []string{"*"}, Resources: []string{"*"}}, - {Verbs: []string{"*"}, APIGroups: []string{"", "apps", "extensions", "batch", "logging.kubesphere.io", "monitoring.kubesphere.io", "iam.kubesphere.io", "resources.kubesphere.io", "autoscaling", "alerting.kubesphere.io", "app.k8s.io", "servicemesh.kubesphere.io"}, Resources: []string{"*"}}}}, + {Verbs: []string{"*"}, APIGroups: []string{"", "apps", "extensions", "batch", "logging.kubesphere.io", "monitoring.kubesphere.io", "iam.kubesphere.io", "resources.kubesphere.io", "autoscaling", "alerting.kubesphere.io", "app.k8s.io", "servicemesh.kubesphere.io", "operations.kubesphere.io"}, Resources: []string{"*"}}}}, {ObjectMeta: metav1.ObjectMeta{Name: "viewer", Annotations: map[string]string{constants.DescriptionAnnotationKey: viewerDescription, constants.CreatorAnnotationKey: constants.System}}, Rules: []rbac.PolicyRule{{Verbs: []string{"get", "list", "watch"}, APIGroups: []string{"*"}, Resources: []string{"*"}}}}, } ) diff --git a/pkg/models/applications/applications.go b/pkg/models/applications/applications.go index c90a00cdf..78b792f83 100644 --- a/pkg/models/applications/applications.go +++ b/pkg/models/applications/applications.go @@ -148,6 +148,11 @@ func getWorkLoads(namespace string, clusterRoles []openpitrix.ClusterRole) (*wor item, err := informers.SharedInformerFactory().Apps().V1().Deployments().Lister().Deployments(namespace).Get(name) if err != nil { + // app not ready + if errors.IsNotFound(err) { + continue + } + glog.Error(err) return nil, err } @@ -159,6 +164,11 @@ func getWorkLoads(namespace string, clusterRoles []openpitrix.ClusterRole) (*wor name := strings.Split(workLoadName, openpitrix.DaemonSuffix)[0] item, err := informers.SharedInformerFactory().Apps().V1().DaemonSets().Lister().DaemonSets(namespace).Get(name) if err != nil { + // app not ready + if errors.IsNotFound(err) { + continue + } + glog.Error(err) return nil, err } works.Daemonsets = append(works.Daemonsets, *item) @@ -169,6 +179,11 @@ func getWorkLoads(namespace string, clusterRoles []openpitrix.ClusterRole) (*wor name := strings.Split(workLoadName, openpitrix.StateSuffix)[0] item, err := informers.SharedInformerFactory().Apps().V1().StatefulSets().Lister().StatefulSets(namespace).Get(name) if err != nil { + // app not ready + if errors.IsNotFound(err) { + continue + } + glog.Error(err) return nil, err } works.Statefulsets = append(works.Statefulsets, *item) diff --git a/pkg/models/iam/im.go b/pkg/models/iam/im.go index 0ab9cae4e..bbe9e49b0 100644 --- a/pkg/models/iam/im.go +++ b/pkg/models/iam/im.go @@ -56,10 +56,12 @@ import ( ) var ( - adminEmail string - adminPassword string - tokenExpireTime time.Duration - initUsers []initUser + adminEmail string + adminPassword string + tokenExpireTime time.Duration + maxAuthFailed int + authTimeInterval time.Duration + initUsers []initUser ) type initUser struct { @@ -68,14 +70,17 @@ type initUser struct { } const ( - userInitFile = "/etc/ks-iam/users.json" + userInitFile = "/etc/ks-iam/users.json" + authRateLimitRegex = `(\d+)/(\d+[s|m|h])` + defaultMaxAuthFailed = 5 + defaultAuthTimeInterval = 30 * time.Minute ) -func Init(email, password string, t time.Duration) error { +func Init(email, password string, expireTime time.Duration, authRateLimit string) error { adminEmail = email adminPassword = password - tokenExpireTime = t - + tokenExpireTime = expireTime + maxAuthFailed, authTimeInterval = parseAuthRateLimit(authRateLimit) conn, err := ldapclient.Client() if err != nil { @@ -101,6 +106,23 @@ func Init(email, password string, t time.Duration) error { return nil } +func parseAuthRateLimit(authRateLimit string) (int, time.Duration) { + regex := regexp.MustCompile(authRateLimitRegex) + groups := regex.FindStringSubmatch(authRateLimit) + + maxCount := defaultMaxAuthFailed + timeInterval := defaultAuthTimeInterval + + if len(groups) == 3 { + maxCount, _ = strconv.Atoi(groups[1]) + timeInterval, _ = time.ParseDuration(groups[2]) + } else { + glog.Warning("invalid auth rate limit", authRateLimit) + } + + return maxCount, timeInterval +} + func checkAndCreateDefaultGroup(conn ldap.Client) error { groupSearchRequest := ldap.NewSearchRequest( @@ -203,9 +225,23 @@ func createGroupsBaseDN(conn ldap.Client) error { // User login func Login(username string, password string, ip string) (*models.Token, error) { + redisClient := redis.Client() + + records, err := redisClient.Keys(fmt.Sprintf("kubesphere:authfailed:%s:*", username)).Result() + + if err != nil { + glog.Error(err) + return nil, err + } + + if len(records) >= maxAuthFailed { + return nil, restful.NewError(http.StatusTooManyRequests, "auth rate limit exceeded") + } + conn, err := ldapclient.Client() if err != nil { + glog.Error(err) return nil, err } @@ -237,7 +273,13 @@ func Login(username string, password string, ip string) (*models.Token, error) { err = conn.Bind(dn, password) if err != nil { - glog.Errorln("auth error", username, err) + glog.Infoln("auth failed", username, err) + + if ldap.IsErrorWithCode(err, ldap.LDAPResultInvalidCredentials) { + loginFailedRecord := fmt.Sprintf("kubesphere:authfailed:%s:%d", username, time.Now().UnixNano()) + redisClient.Set(loginFailedRecord, "", authTimeInterval) + } + return nil, err } @@ -876,6 +918,17 @@ func UpdateUser(user *models.User) (*models.User, error) { return nil, err } + // clear auth failed record + if user.Password != "" { + redisClient := redis.Client() + + records, err := redisClient.Keys(fmt.Sprintf("kubesphere:authfailed:%s:*", user.Username)).Result() + + if err == nil { + redisClient.Del(records...) + } + } + return GetUserInfo(user.Username) } func DeleteGroup(path string) error { diff --git a/pkg/models/resources/nodes.go b/pkg/models/resources/nodes.go index 6daa02c61..38e607f0b 100644 --- a/pkg/models/resources/nodes.go +++ b/pkg/models/resources/nodes.go @@ -18,6 +18,7 @@ package resources import ( + "fmt" "kubesphere.io/kubesphere/pkg/constants" "kubesphere.io/kubesphere/pkg/informers" "kubesphere.io/kubesphere/pkg/params" @@ -45,6 +46,11 @@ func (*nodeSearcher) match(match map[string]string, item *v1.Node) bool { if !sliceutil.HasString(names, item.Name) { return false } + case Role: + labelKey := fmt.Sprintf("node-role.kubernetes.io/%s", v) + if _, ok := item.Labels[labelKey]; !ok { + return false + } case Keyword: if !strings.Contains(item.Name, v) && !searchFuzzy(item.Labels, "", v) && !searchFuzzy(item.Annotations, "", v) { return false diff --git a/pkg/models/resources/resources.go b/pkg/models/resources/resources.go index 428ee70fb..4017cced5 100644 --- a/pkg/models/resources/resources.go +++ b/pkg/models/resources/resources.go @@ -61,6 +61,7 @@ const ( Label = "label" OwnerKind = "ownerKind" OwnerName = "ownerName" + Role = "role" CreateTime = "createTime" UpdateTime = "updateTime" LastScheduleTime = "lastScheduleTime" From 8d01fb68abfdd97f2ca1a89472b2b6f1f2e7bc9b Mon Sep 17 00:00:00 2001 From: huanggze Date: Thu, 20 Jun 2019 21:44:32 +0800 Subject: [PATCH 3/6] api doc: change the path parameter from workload_kind to kind Signed-off-by: huanggze --- pkg/apis/monitoring/v1alpha2/register.go | 8 ++++---- pkg/simple/client/prometheus/prometheusclient.go | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/pkg/apis/monitoring/v1alpha2/register.go b/pkg/apis/monitoring/v1alpha2/register.go index 5cfd54887..4f9d97dbe 100644 --- a/pkg/apis/monitoring/v1alpha2/register.go +++ b/pkg/apis/monitoring/v1alpha2/register.go @@ -227,10 +227,10 @@ func addWebService(c *restful.Container) error { // Only use this api to monitor status of pods under the {workload} // To monitor a specific workload, try the next two apis with "resources_filter" - ws.Route(ws.GET("/namespaces/{namespace}/workloads/{workload_kind}/{workload}").To(monitoring.MonitorSpecificWorkload). + ws.Route(ws.GET("/namespaces/{namespace}/workloads/{kind}/{workload}").To(monitoring.MonitorSpecificWorkload). Doc("Get specific workload metrics under a given namespace."). Param(ws.PathParameter("namespace", "Specify the target namespace.").DataType("string").Required(true)). - Param(ws.PathParameter("workload_kind", "Specify the target workload kind. One of deployment, daemonset, statefulset. Other values will be interpreted as any of three.").DataType("string").Required(true).DefaultValue("(.*)")). + Param(ws.PathParameter("kind", "Specify the target workload kind. One of deployment, daemonset, statefulset. Other values will be interpreted as any of three.").DataType("string").Required(true).DefaultValue("(.*)")). Param(ws.PathParameter("workload", "Specify the target workload.").DataType("string").Required(true)). Param(ws.QueryParameter("metrics_filter", "Metrics filter in regexp pattern, eg. workload_cpu|workload_memory.").DataType("string").Required(false)). Param(ws.QueryParameter("step", "Used to get metrics over a range of time. Query resolution step. eg. 10m.").DataType("string").Required(false)). @@ -243,10 +243,10 @@ func addWebService(c *restful.Container) error { Consumes(restful.MIME_JSON, restful.MIME_XML). Produces(restful.MIME_JSON) - ws.Route(ws.GET("/namespaces/{namespace}/workloads/{workload_kind}").To(monitoring.MonitorAllWorkloadsOfSpecificKind). + ws.Route(ws.GET("/namespaces/{namespace}/workloads/{kind}").To(monitoring.MonitorAllWorkloadsOfSpecificKind). Doc("Get all workload-level metrics of a specific workload kind under a given namespace."). Param(ws.PathParameter("namespace", "Specify the target namespace.").DataType("string").Required(true)). - Param(ws.PathParameter("workload_kind", "Specify the target workload kind. One of deployment, daemonset, statefulset. Other values will be interpreted as any of three.").DataType("string").Required(true).DefaultValue("(.*)")). + Param(ws.PathParameter("kind", "Specify the target workload kind. One of deployment, daemonset, statefulset. Other values will be interpreted as any of three.").DataType("string").Required(true).DefaultValue("(.*)")). Param(ws.QueryParameter("metrics_filter", "Metrics filter in regexp pattern, eg. node_cpu|node_memory.").DataType("string").Required(false)). Param(ws.QueryParameter("resources_filter", "Workload filter in regexp pattern.").DataType("string").Required(false)). Param(ws.QueryParameter("sort_metric", "Sort workloads by the specified metric. Valid only if type is rank.").DataType("string").Required(false)). diff --git a/pkg/simple/client/prometheus/prometheusclient.go b/pkg/simple/client/prometheus/prometheusclient.go index 4ed4b5257..6f8fabbd6 100644 --- a/pkg/simple/client/prometheus/prometheusclient.go +++ b/pkg/simple/client/prometheus/prometheusclient.go @@ -114,7 +114,7 @@ func ParseMonitoringRequestParams(request *restful.Request) *MonitoringRequestPa nsName := strings.Trim(request.PathParameter("namespace"), " ") podName := strings.Trim(request.PathParameter("pod"), " ") containerName := strings.Trim(request.PathParameter("container"), " ") - workloadKind := strings.Trim(request.PathParameter("workload_kind"), " ") + workloadKind := strings.Trim(request.PathParameter("kind"), " ") componentName := strings.Trim(request.PathParameter("component"), " ") var requestParams = MonitoringRequestParams{ From f92e30934389187605d70f0c74fe3a14d6a884dd Mon Sep 17 00:00:00 2001 From: huanggze Date: Thu, 20 Jun 2019 22:12:21 +0800 Subject: [PATCH 4/6] api doc: remove apis for fluent bit filter plugins Signed-off-by: huanggze --- pkg/apis/logging/v1alpha2/register.go | 14 -------------- 1 file changed, 14 deletions(-) diff --git a/pkg/apis/logging/v1alpha2/register.go b/pkg/apis/logging/v1alpha2/register.go index 705579bf4..1e2d23035 100644 --- a/pkg/apis/logging/v1alpha2/register.go +++ b/pkg/apis/logging/v1alpha2/register.go @@ -186,20 +186,6 @@ func addWebService(c *restful.Container) error { Consumes(restful.MIME_JSON, restful.MIME_XML). Produces(restful.MIME_JSON) - ws.Route(ws.GET("/fluentbit/filters").To(logging.LoggingQueryFluentbitFilters). - Filter(filter.Logging). - Doc("List all Fluent bit filter plugins. This API is work-in-process."). - Metadata(restfulspec.KeyOpenAPITags, []string{"Logging", "setting"})). - Consumes(restful.MIME_JSON, restful.MIME_XML). - Produces(restful.MIME_JSON) - - ws.Route(ws.POST("/fluentbit/filters").To(logging.LoggingUpdateFluentbitFilters). - Filter(filter.Logging). - Doc("Add a new Fluent bit filter plugin. This API is work-in-process."). - Metadata(restfulspec.KeyOpenAPITags, []string{"Logging", "setting"})). - Consumes(restful.MIME_JSON, restful.MIME_XML). - Produces(restful.MIME_JSON) - ws.Route(ws.GET("/fluentbit/outputs").To(logging.LoggingQueryFluentbitOutputs). Filter(filter.Logging). Doc("List all Fluent bit output plugins."). From 24d13e44f7bb91707c336211d02069e2b997206b Mon Sep 17 00:00:00 2001 From: hongming Date: Fri, 21 Jun 2019 11:47:29 +0800 Subject: [PATCH 5/6] update api docs (#490) * update api docs Signed-off-by: hongming * fix: kube-apiserver host in kubeconfig Signed-off-by: hongming --- pkg/apis/iam/v1alpha2/register.go | 66 +++++++++---------- pkg/apis/operations/v1alpha2/register.go | 4 -- pkg/apis/resources/v1alpha2/register.go | 47 +++++++++---- pkg/apis/tenant/v1alpha2/register.go | 14 ++-- pkg/apiserver/iam/am.go | 2 +- pkg/apiserver/iam/groups.go | 8 +-- pkg/apiserver/iam/im.go | 10 +-- pkg/apiserver/iam/workspaces.go | 4 +- pkg/apiserver/resources/application.go | 4 +- pkg/apiserver/resources/user.go | 4 +- pkg/apiserver/tenant/tenant.go | 6 +- .../workloadstatuses/workloadstatuses.go | 4 +- pkg/models/applications/applications.go | 4 +- pkg/models/kubeconfig/kubeconfig.go | 2 +- pkg/simple/client/k8s/k8sclient.go | 6 +- 15 files changed, 98 insertions(+), 87 deletions(-) diff --git a/pkg/apis/iam/v1alpha2/register.go b/pkg/apis/iam/v1alpha2/register.go index 0771f0c5b..955448c50 100644 --- a/pkg/apis/iam/v1alpha2/register.go +++ b/pkg/apis/iam/v1alpha2/register.go @@ -121,10 +121,10 @@ func addWebService(c *restful.Container) error { Reads(iam.LoginRequest{}). Returns(http.StatusOK, ok, models.Token{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/users/{username}"). + ws.Route(ws.GET("/users/{user}"). To(iam.DescribeUser). - Doc("Describes the specified user."). - Param(ws.PathParameter("username", "username")). + Doc("Describe the specified user."). + Param(ws.PathParameter("user", "username")). Returns(http.StatusOK, ok, models.User{}). Metadata(restfulspec.KeyOpenAPITags, tags)) ws.Route(ws.POST("/users"). @@ -133,23 +133,23 @@ func addWebService(c *restful.Container) error { Reads(CreateUserRequest{}). Returns(http.StatusOK, ok, errors.Error{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.DELETE("/users/{username}"). + ws.Route(ws.DELETE("/users/{user}"). To(iam.DeleteUser). Doc("Remove a specified user."). - Param(ws.PathParameter("username", "username")). + Param(ws.PathParameter("user", "username")). Returns(http.StatusOK, ok, errors.Error{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.PUT("/users/{username}"). + ws.Route(ws.PUT("/users/{user}"). To(iam.UpdateUser). Doc("Updates information about the specified user."). - Param(ws.PathParameter("username", "username")). + Param(ws.PathParameter("user", "username")). Reads(UserUpdateRequest{}). Returns(http.StatusOK, ok, errors.Error{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/users/{username}/log"). - To(iam.UserLoginLog). + ws.Route(ws.GET("/users/{user}/logs"). + To(iam.UserLoginLogs). Doc("This method is used to retrieve the \"login logs\" for the specified user."). - Param(ws.PathParameter("username", "username")). + Param(ws.PathParameter("user", "username")). Returns(http.StatusOK, ok, LoginLog{}). Metadata(restfulspec.KeyOpenAPITags, tags)) ws.Route(ws.GET("/users"). @@ -160,43 +160,39 @@ func addWebService(c *restful.Container) error { ws.Route(ws.GET("/groups"). To(iam.ListGroups). Doc("List all user groups."). - Returns(http.StatusOK, ok, []models.Group{}). - Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/groups/{path}"). + Returns(http.StatusOK, ok, []models.Group{})) + ws.Route(ws.GET("/groups/{group}"). To(iam.DescribeGroup). - Doc("Describes the specified user group."). - Param(ws.PathParameter("path", "user group path separated by colon.")). - Returns(http.StatusOK, ok, models.Group{}). - Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/groups/{path}/users"). + Doc("Describe the specified user group."). + Param(ws.PathParameter("group", "user group path separated by colon.")). + Returns(http.StatusOK, ok, models.Group{})) + ws.Route(ws.GET("/groups/{group}/users"). To(iam.ListGroupUsers). Doc("List all users in the specified user group."). - Param(ws.PathParameter("path", "user group path separated by colon.")). - Returns(http.StatusOK, ok, []models.User{}). - Metadata(restfulspec.KeyOpenAPITags, tags)) + Param(ws.PathParameter("group", "user group path separated by colon.")). + Returns(http.StatusOK, ok, []models.User{})) ws.Route(ws.POST("/groups"). To(iam.CreateGroup). Doc("Create a user group."). Reads(models.Group{}). - Returns(http.StatusOK, ok, models.Group{}). - Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.DELETE("/groups/{path}"). + Returns(http.StatusOK, ok, models.Group{})) + ws.Route(ws.DELETE("/groups/{group}"). To(iam.DeleteGroup). Doc("Delete a user group."). - Param(ws.PathParameter("path", "user group path separated by colon.")). + Param(ws.PathParameter("group", "user group path separated by colon.")). Returns(http.StatusOK, ok, errors.Error{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.PUT("/groups/{path}"). + ws.Route(ws.PUT("/groups/{group}"). To(iam.UpdateGroup). Doc("Updates information about the user group."). - Param(ws.PathParameter("path", "user group path separated by colon.")). + Param(ws.PathParameter("group", "user group path separated by colon.")). Reads(models.Group{}). Returns(http.StatusOK, ok, models.Group{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/users/{username}/roles"). + ws.Route(ws.GET("/users/{user}/roles"). To(iam.ListUserRoles). Doc("This method is used to retrieve all the roles that are assigned to the user."). - Param(ws.PathParameter("username", "username")). + Param(ws.PathParameter("user", "username")). Returns(http.StatusOK, ok, iam.RoleList{}). Metadata(restfulspec.KeyOpenAPITags, tags)) ws.Route(ws.GET("/namespaces/{namespace}/roles"). @@ -267,7 +263,7 @@ func addWebService(c *restful.Container) error { Metadata(restfulspec.KeyOpenAPITags, tags)) ws.Route(ws.GET("/workspaces/{workspace}/roles/{role}"). To(iam.DescribeWorkspaceRole). - Doc("Describes the workspace role."). + Doc("Describe the workspace role."). Param(ws.PathParameter("workspace", "workspace name")). Param(ws.PathParameter("role", "workspace role name")). Returns(http.StatusOK, ok, rbacv1.ClusterRole{}). @@ -292,18 +288,18 @@ func addWebService(c *restful.Container) error { Reads(InviteUserRequest{}). Returns(http.StatusOK, ok, errors.Error{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.DELETE("/workspaces/{workspace}/members/{username}"). + ws.Route(ws.DELETE("/workspaces/{workspace}/members/{member}"). To(iam.RemoveUser). Doc("Remove members from workspace."). Param(ws.PathParameter("workspace", "workspace name")). - Param(ws.PathParameter("username", "username")). + Param(ws.PathParameter("member", "username")). Returns(http.StatusOK, ok, errors.Error{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/workspaces/{workspace}/members/{username}"). + ws.Route(ws.GET("/workspaces/{workspace}/members/{member}"). To(iam.DescribeWorkspaceUser). - Doc("Describes the specified user."). + Doc("Describe the specified user."). Param(ws.PathParameter("workspace", "workspace name")). - Param(ws.PathParameter("username", "username")). + Param(ws.PathParameter("member", "username")). Returns(http.StatusOK, ok, DescribeWorkspaceUserResponse{}). Metadata(restfulspec.KeyOpenAPITags, tags)) c.Add(ws) diff --git a/pkg/apis/operations/v1alpha2/register.go b/pkg/apis/operations/v1alpha2/register.go index b3b23d755..06352280c 100644 --- a/pkg/apis/operations/v1alpha2/register.go +++ b/pkg/apis/operations/v1alpha2/register.go @@ -19,7 +19,6 @@ package v1alpha2 import ( "github.com/emicklei/go-restful" - "github.com/emicklei/go-restful-openapi" "k8s.io/apimachinery/pkg/runtime/schema" "kubesphere.io/kubesphere/pkg/apiserver/operations" "kubesphere.io/kubesphere/pkg/apiserver/runtime" @@ -38,20 +37,17 @@ var ( func addWebService(c *restful.Container) error { - tags := []string{"Operations"} ok := "ok" webservice := runtime.NewWebService(GroupVersion) webservice.Route(webservice.POST("/nodes/{node}/drainage"). To(operations.DrainNode). - Metadata(restfulspec.KeyOpenAPITags, tags). Doc("Drain node"). Param(webservice.PathParameter("node", "node name")). Returns(http.StatusOK, ok, errors.Error{})) webservice.Route(webservice.POST("/namespaces/{namespace}/jobs/{job}"). To(operations.RerunJob). - Metadata(restfulspec.KeyOpenAPITags, tags). Doc("Job rerun"). Param(webservice.PathParameter("job", "job name")). Param(webservice.PathParameter("namespace", "job's namespace")). diff --git a/pkg/apis/resources/v1alpha2/register.go b/pkg/apis/resources/v1alpha2/register.go index 824adfa66..9777f568d 100644 --- a/pkg/apis/resources/v1alpha2/register.go +++ b/pkg/apis/resources/v1alpha2/register.go @@ -25,6 +25,7 @@ import ( "k8s.io/apimachinery/pkg/runtime/schema" "kubesphere.io/kubesphere/pkg/apiserver/components" "kubesphere.io/kubesphere/pkg/apiserver/git" + "kubesphere.io/kubesphere/pkg/apiserver/operations" "kubesphere.io/kubesphere/pkg/apiserver/quotas" "kubesphere.io/kubesphere/pkg/apiserver/registries" "kubesphere.io/kubesphere/pkg/apiserver/resources" @@ -74,6 +75,15 @@ func addWebService(c *restful.Container) error { DefaultValue("limit=10,page=1")). Returns(http.StatusOK, ok, models.PageableResponse{})) + webservice.Route(webservice.POST("/namespaces/{namespace}/jobs/{job}"). + To(operations.RerunJob). + Metadata(restfulspec.KeyOpenAPITags, tags). + Doc("Rerun job whether the job is complete or not"). + Param(webservice.PathParameter("job", "job name")). + Param(webservice.PathParameter("namespace", "job's namespace")). + Param(webservice.QueryParameter("a", "action")). + Returns(http.StatusOK, ok, errors.Error{})) + tags = []string{"Cluster resources"} webservice.Route(webservice.GET("/{resources}"). @@ -91,6 +101,15 @@ func addWebService(c *restful.Container) error { DataFormat("limit=%d,page=%d"). DefaultValue("limit=10,page=1"))) + webservice.Route(webservice.POST("/nodes/{node}/drainage"). + To(operations.DrainNode). + Metadata(restfulspec.KeyOpenAPITags, tags). + Doc("Drain node"). + Param(webservice.PathParameter("node", "node name")). + Returns(http.StatusOK, ok, errors.Error{})) + + c.Add(webservice) + tags = []string{"Applications"} webservice.Route(webservice.GET("/applications"). @@ -124,13 +143,13 @@ func addWebService(c *restful.Container) error { DataFormat("limit=%d,page=%d"). DefaultValue("limit=10,page=1"))) - webservice.Route(webservice.GET("/namespaces/{namespace}/applications/{cluster_id}"). + webservice.Route(webservice.GET("/namespaces/{namespace}/applications/{application}"). To(resources.DescribeApplication). Returns(http.StatusOK, ok, applications.Application{}). Metadata(restfulspec.KeyOpenAPITags, tags). Doc("Describe application"). Param(webservice.PathParameter("namespace", "namespace name")). - Param(webservice.PathParameter("cluster_id", "application id"))) + Param(webservice.PathParameter("application", "application id"))) webservice.Route(webservice.POST("/namespaces/{namespace}/applications"). To(resources.DeployApplication). @@ -140,28 +159,28 @@ func addWebService(c *restful.Container) error { Returns(http.StatusOK, ok, errors.Error{}). Param(webservice.PathParameter("namespace", "namespace name"))) - webservice.Route(webservice.DELETE("/namespaces/{namespace}/applications/{cluster_id}"). + webservice.Route(webservice.DELETE("/namespaces/{namespace}/applications/{application}"). To(resources.DeleteApplication). Doc("Delete application"). Metadata(restfulspec.KeyOpenAPITags, tags). Returns(http.StatusOK, ok, errors.Error{}). Param(webservice.PathParameter("namespace", "namespace name")). - Param(webservice.PathParameter("cluster_id", "application id"))) + Param(webservice.PathParameter("application", "application id"))) tags = []string{"User resources"} - webservice.Route(webservice.GET("/users/{username}/kubectl"). + webservice.Route(webservice.GET("/users/{user}/kubectl"). To(resources.GetKubectl). Doc("get user's kubectl pod"). - Param(webservice.PathParameter("username", "username")). + Param(webservice.PathParameter("user", "username")). Metadata(restfulspec.KeyOpenAPITags, tags). Returns(http.StatusOK, ok, models.PodInfo{})) - webservice.Route(webservice.GET("/users/{username}/kubeconfig"). + webservice.Route(webservice.GET("/users/{user}/kubeconfig"). Produces("text/plain"). To(resources.GetKubeconfig). Doc("get users' kubeconfig"). - Param(webservice.PathParameter("username", "username")). + Param(webservice.PathParameter("user", "username")). Returns(http.StatusOK, ok, ""). Metadata(restfulspec.KeyOpenAPITags, tags)) @@ -178,7 +197,7 @@ func addWebService(c *restful.Container) error { Doc(""). Param(webservice.PathParameter("component", "component name")). Returns(http.StatusOK, ok, models.Component{})) - webservice.Route(webservice.GET("/health"). + webservice.Route(webservice.GET("/componenthealth"). To(components.GetSystemHealthStatus). Metadata(restfulspec.KeyOpenAPITags, tags). Doc(""). @@ -202,7 +221,7 @@ func addWebService(c *restful.Container) error { tags = []string{"Registries"} - webservice.Route(webservice.POST("registries/verify"). + webservice.Route(webservice.POST("registry/verify"). To(registries.RegistryVerify). Metadata(restfulspec.KeyOpenAPITags, tags). Doc("docker registry verify"). @@ -279,17 +298,17 @@ func addWebService(c *restful.Container) error { tags = []string{"WorkloadStatus"} - webservice.Route(webservice.GET("/workloadstatuses"). + webservice.Route(webservice.GET("/abnormalworkloads"). Doc("get abnormal workloads' count of whole cluster"). Metadata(restfulspec.KeyOpenAPITags, tags). Returns(http.StatusOK, ok, status.WorkLoadStatus{}). - To(workloadstatuses.GetClusterResourceStatus)) - webservice.Route(webservice.GET("/namespaces/{namespace}/workloadstatuses"). + To(workloadstatuses.GetClusterAbnormalWorkloads)) + webservice.Route(webservice.GET("/namespaces/{namespace}/abnormalworkloads"). Doc("get abnormal workloads' count of specified namespace"). Param(webservice.PathParameter("namespace", "the name of namespace")). Metadata(restfulspec.KeyOpenAPITags, tags). Returns(http.StatusOK, ok, status.WorkLoadStatus{}). - To(workloadstatuses.GetNamespacesResourceStatus)) + To(workloadstatuses.GetNamespacedAbnormalWorkloads)) c.Add(webservice) diff --git a/pkg/apis/tenant/v1alpha2/register.go b/pkg/apis/tenant/v1alpha2/register.go index 51b4f3ed1..eedcdc32e 100644 --- a/pkg/apis/tenant/v1alpha2/register.go +++ b/pkg/apis/tenant/v1alpha2/register.go @@ -87,10 +87,10 @@ func addWebService(c *restful.Container) error { Doc("List the namespaces for the current user"). Returns(http.StatusOK, ok, []v1.Namespace{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/workspaces/{workspace}/members/{username}/namespaces"). + ws.Route(ws.GET("/workspaces/{workspace}/members/{member}/namespaces"). To(tenant.ListNamespacesByUsername). Param(ws.PathParameter("workspace", "workspace name")). - Param(ws.PathParameter("username", "workspace member's username")). + Param(ws.PathParameter("member", "workspace member's username")). Doc("List the namespaces for the workspace member"). Returns(http.StatusOK, ok, []v1.Namespace{}). Metadata(restfulspec.KeyOpenAPITags, tags)) @@ -120,10 +120,10 @@ func addWebService(c *restful.Container) error { DataFormat("key=%s,key~%s")). Doc("List devops projects for the current user"). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/workspaces/{workspace}/members/{username}/devops"). + ws.Route(ws.GET("/workspaces/{workspace}/members/{member}/devops"). To(tenant.ListDevopsProjectsByUsername). Param(ws.PathParameter("workspace", "workspace name")). - Param(ws.PathParameter("username", "workspace member's username")). + Param(ws.PathParameter("member", "workspace member's username")). Param(ws.QueryParameter(params.PagingParam, "page"). Required(false). DataFormat("limit=%d,page=%d"). @@ -141,14 +141,14 @@ func addWebService(c *restful.Container) error { Reads(devops.DevOpsProject{}). Returns(http.StatusOK, RespOK, devops.DevOpsProject{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.DELETE("/workspaces/{workspace}/devops/{id}"). + ws.Route(ws.DELETE("/workspaces/{workspace}/devops/{devops}"). To(tenant.DeleteDevopsProject). Param(ws.PathParameter("workspace", "workspace name")). - Param(ws.PathParameter("id", "devops project id")). + Param(ws.PathParameter("devops", "devops project id")). Doc("Delete devops project"). Returns(http.StatusOK, RespOK, devops.DevOpsProject{}). Metadata(restfulspec.KeyOpenAPITags, tags)) - ws.Route(ws.GET("/logging"). + ws.Route(ws.GET("/logs"). To(tenant.LogQuery). Doc("Query cluster-level logs in a multi-tenants environment"). Param(ws.QueryParameter("operation", "Query operation type. One of query, statistics, histogram.").DataType("string").Required(true)). diff --git a/pkg/apiserver/iam/am.go b/pkg/apiserver/iam/am.go index 51aa7b4b6..21699c72c 100644 --- a/pkg/apiserver/iam/am.go +++ b/pkg/apiserver/iam/am.go @@ -116,7 +116,7 @@ func ListNamespaceUsers(req *restful.Request, resp *restful.Response) { func ListUserRoles(req *restful.Request, resp *restful.Response) { - username := req.PathParameter("username") + username := req.PathParameter("user") roles, err := iam.GetUserRoles("", username) diff --git a/pkg/apiserver/iam/groups.go b/pkg/apiserver/iam/groups.go index cd0cce07b..9b978ce6c 100644 --- a/pkg/apiserver/iam/groups.go +++ b/pkg/apiserver/iam/groups.go @@ -61,7 +61,7 @@ func CreateGroup(req *restful.Request, resp *restful.Response) { } func DeleteGroup(req *restful.Request, resp *restful.Response) { - path := req.PathParameter("path") + path := req.PathParameter("group") if path == "" { resp.WriteHeaderAndEntity(http.StatusBadRequest, errors.Wrap(fmt.Errorf("group path must not be null"))) @@ -84,7 +84,7 @@ func DeleteGroup(req *restful.Request, resp *restful.Response) { } func UpdateGroup(req *restful.Request, resp *restful.Response) { - groupPathInPath := req.PathParameter("path") + groupPathInPath := req.PathParameter("group") var group models.Group @@ -108,7 +108,7 @@ func UpdateGroup(req *restful.Request, resp *restful.Response) { func DescribeGroup(req *restful.Request, resp *restful.Response) { - path := req.PathParameter("path") + path := req.PathParameter("group") group, err := iam.DescribeGroup(path) @@ -127,7 +127,7 @@ func DescribeGroup(req *restful.Request, resp *restful.Response) { func ListGroupUsers(req *restful.Request, resp *restful.Response) { - path := req.PathParameter("path") + path := req.PathParameter("group") group, err := iam.DescribeGroup(path) diff --git a/pkg/apiserver/iam/im.go b/pkg/apiserver/iam/im.go index 2a2ef4007..aa39cc02f 100644 --- a/pkg/apiserver/iam/im.go +++ b/pkg/apiserver/iam/im.go @@ -77,7 +77,7 @@ func CreateUser(req *restful.Request, resp *restful.Response) { } func DeleteUser(req *restful.Request, resp *restful.Response) { - username := req.PathParameter("username") + username := req.PathParameter("user") operator := req.HeaderParameter(constants.UserNameHeader) @@ -98,7 +98,7 @@ func DeleteUser(req *restful.Request, resp *restful.Response) { func UpdateUser(req *restful.Request, resp *restful.Response) { - usernameInPath := req.PathParameter("username") + usernameInPath := req.PathParameter("user") usernameInHeader := req.HeaderParameter(constants.UserNameHeader) var user models.User @@ -161,8 +161,8 @@ func isUserManager(username string) (bool, error) { return false, nil } -func UserLoginLog(req *restful.Request, resp *restful.Response) { - username := req.PathParameter("username") +func UserLoginLogs(req *restful.Request, resp *restful.Response) { + username := req.PathParameter("user") logs, err := iam.LoginLog(username) if err != nil { @@ -187,7 +187,7 @@ func UserLoginLog(req *restful.Request, resp *restful.Response) { func DescribeUser(req *restful.Request, resp *restful.Response) { - username := req.PathParameter("username") + username := req.PathParameter("user") user, err := iam.DescribeUser(username) diff --git a/pkg/apiserver/iam/workspaces.go b/pkg/apiserver/iam/workspaces.go index b850b4dcb..be0f46194 100644 --- a/pkg/apiserver/iam/workspaces.go +++ b/pkg/apiserver/iam/workspaces.go @@ -77,7 +77,7 @@ func DescribeWorkspaceRole(req *restful.Request, resp *restful.Response) { func DescribeWorkspaceUser(req *restful.Request, resp *restful.Response) { workspace := req.PathParameter("workspace") - username := req.PathParameter("username") + username := req.PathParameter("member") workspaceRole, err := iam.GetUserWorkspaceRole(workspace, username) @@ -132,7 +132,7 @@ func InviteUser(req *restful.Request, resp *restful.Response) { func RemoveUser(req *restful.Request, resp *restful.Response) { workspace := req.PathParameter("workspace") - username := req.PathParameter("username") + username := req.PathParameter("member") err := workspaces.RemoveUser(workspace, username) if err != nil { diff --git a/pkg/apiserver/resources/application.go b/pkg/apiserver/resources/application.go index ea705c4b0..77b10c2f7 100644 --- a/pkg/apiserver/resources/application.go +++ b/pkg/apiserver/resources/application.go @@ -117,7 +117,7 @@ func ListNamespacedApplication(req *restful.Request, resp *restful.Response) { } func DescribeApplication(req *restful.Request, resp *restful.Response) { - clusterId := req.PathParameter("cluster_id") + clusterId := req.PathParameter("application") namespaceName := req.PathParameter("namespace") app, err := applications.GetApp(clusterId) if err != nil { @@ -166,7 +166,7 @@ func DeployApplication(req *restful.Request, resp *restful.Response) { } func DeleteApplication(req *restful.Request, resp *restful.Response) { - clusterId := req.PathParameter("cluster_id") + clusterId := req.PathParameter("application") namespaceName := req.PathParameter("namespace") app, err := applications.GetApp(clusterId) if err != nil { diff --git a/pkg/apiserver/resources/user.go b/pkg/apiserver/resources/user.go index 03b376322..5e8bf2945 100644 --- a/pkg/apiserver/resources/user.go +++ b/pkg/apiserver/resources/user.go @@ -29,7 +29,7 @@ import ( func GetKubectl(req *restful.Request, resp *restful.Response) { - user := req.PathParameter("username") + user := req.PathParameter("user") kubectlPod, err := kubectl.GetKubectlPod(user) @@ -43,7 +43,7 @@ func GetKubectl(req *restful.Request, resp *restful.Response) { func GetKubeconfig(req *restful.Request, resp *restful.Response) { - user := req.PathParameter("username") + user := req.PathParameter("user") kubectlConfig, err := kubeconfig.GetKubeConfig(user) diff --git a/pkg/apiserver/tenant/tenant.go b/pkg/apiserver/tenant/tenant.go index 99355bfdf..488c94cdd 100644 --- a/pkg/apiserver/tenant/tenant.go +++ b/pkg/apiserver/tenant/tenant.go @@ -107,7 +107,7 @@ func ListNamespacesByUsername(req *restful.Request, resp *restful.Response) { func ListNamespaces(req *restful.Request, resp *restful.Response) { workspace := req.PathParameter("workspace") - username := req.PathParameter("username") + username := req.PathParameter("member") // /workspaces/{workspace}/members/{username}/namespaces if username == "" { // /workspaces/{workspace}/namespaces @@ -218,7 +218,7 @@ func ListDevopsProjectsByUsername(req *restful.Request, resp *restful.Response) func ListDevopsProjects(req *restful.Request, resp *restful.Response) { workspace := req.PathParameter("workspace") - username := req.PathParameter(constants.UserNameHeader) + username := req.PathParameter("member") if username == "" { username = req.HeaderParameter(constants.UserNameHeader) } @@ -245,7 +245,7 @@ func ListDevopsProjects(req *restful.Request, resp *restful.Response) { } func DeleteDevopsProject(req *restful.Request, resp *restful.Response) { - projectId := req.PathParameter("id") + projectId := req.PathParameter("devops") workspaceName := req.PathParameter("workspace") username := req.HeaderParameter(constants.UserNameHeader) diff --git a/pkg/apiserver/workloadstatuses/workloadstatuses.go b/pkg/apiserver/workloadstatuses/workloadstatuses.go index 934441283..75e8f8fe4 100644 --- a/pkg/apiserver/workloadstatuses/workloadstatuses.go +++ b/pkg/apiserver/workloadstatuses/workloadstatuses.go @@ -26,7 +26,7 @@ import ( "kubesphere.io/kubesphere/pkg/models/status" ) -func GetClusterResourceStatus(req *restful.Request, resp *restful.Response) { +func GetClusterAbnormalWorkloads(req *restful.Request, resp *restful.Response) { res, err := status.GetClusterResourceStatus() if err != nil { resp.WriteHeaderAndEntity(http.StatusInternalServerError, errors.Wrap(err)) @@ -35,7 +35,7 @@ func GetClusterResourceStatus(req *restful.Request, resp *restful.Response) { resp.WriteAsJson(res) } -func GetNamespacesResourceStatus(req *restful.Request, resp *restful.Response) { +func GetNamespacedAbnormalWorkloads(req *restful.Request, resp *restful.Response) { res, err := status.GetNamespacesResourceStatus(req.PathParameter("namespace")) if err != nil { resp.WriteHeaderAndEntity(http.StatusInternalServerError, errors.Wrap(err)) diff --git a/pkg/models/applications/applications.go b/pkg/models/applications/applications.go index 78b792f83..80fb63528 100644 --- a/pkg/models/applications/applications.go +++ b/pkg/models/applications/applications.go @@ -45,8 +45,8 @@ type Application struct { Version string `json:"version" description:"application version"` VersionId string `json:"version_id" description:"application version id"` Status string `json:"status" description:"application status"` - UpdateTime time.Time `json:"updateTime" description:"update time"` - CreateTime time.Time `json:"createTime" description:"create name"` + UpdateTime time.Time `json:"updateTime" description:"the last time this application was updated"` + CreateTime time.Time `json:"createTime" description:"application creation time"` App string `json:"app" description:"application template name"` AppId string `json:"app_id" description:"application template id"` Description string `json:"description,omitempty" description:"application description"` diff --git a/pkg/models/kubeconfig/kubeconfig.go b/pkg/models/kubeconfig/kubeconfig.go index cef159e23..2c052a501 100644 --- a/pkg/models/kubeconfig/kubeconfig.go +++ b/pkg/models/kubeconfig/kubeconfig.go @@ -217,7 +217,7 @@ func createKubeConfig(username string) (string, error) { return "", err } base64ServerCa := base64.StdEncoding.EncodeToString(serverCa) - tmpClusterInfo := clusterInfo{CertificateAuthorityData: base64ServerCa, Server: k8s.KubeConfig.Host} + tmpClusterInfo := clusterInfo{CertificateAuthorityData: base64ServerCa, Server: k8s.MasterURL} tmpCluster := cluster{Cluster: tmpClusterInfo, Name: clusterName} tmpKubeConfig.Clusters = append(tmpKubeConfig.Clusters, tmpCluster) diff --git a/pkg/simple/client/k8s/k8sclient.go b/pkg/simple/client/k8s/k8sclient.go index 62f8a56da..399233707 100644 --- a/pkg/simple/client/k8s/k8sclient.go +++ b/pkg/simple/client/k8s/k8sclient.go @@ -34,12 +34,12 @@ var ( k8sClient *kubernetes.Clientset k8sClientOnce sync.Once KubeConfig *rest.Config - masterURL string + MasterURL string ) func init() { flag.StringVar(&kubeConfigFile, "kubeconfig", "", "path to kubeconfig file") - flag.StringVar(&masterURL, "master-url", "", "kube-apiserver url, only needed when out of cluster") + flag.StringVar(&MasterURL, "master-url", "", "kube-apiserver url, only needed when out of cluster") } func Client() *kubernetes.Clientset { @@ -63,7 +63,7 @@ func Client() *kubernetes.Clientset { func Config() (kubeConfig *rest.Config, err error) { if _, err = os.Stat(kubeConfigFile); err == nil { - kubeConfig, err = clientcmd.BuildConfigFromFlags(masterURL, kubeConfigFile) + kubeConfig, err = clientcmd.BuildConfigFromFlags(MasterURL, kubeConfigFile) } else { kubeConfig, err = rest.InClusterConfig() } From bade7af87e5b099f4570e3e009d0e8337517f7cd Mon Sep 17 00:00:00 2001 From: hongming Date: Fri, 21 Jun 2019 15:22:33 +0800 Subject: [PATCH 6/6] fix: duplicate root path Signed-off-by: hongming --- pkg/apis/resources/v1alpha2/register.go | 2 -- 1 file changed, 2 deletions(-) diff --git a/pkg/apis/resources/v1alpha2/register.go b/pkg/apis/resources/v1alpha2/register.go index 9777f568d..c78ca754c 100644 --- a/pkg/apis/resources/v1alpha2/register.go +++ b/pkg/apis/resources/v1alpha2/register.go @@ -108,8 +108,6 @@ func addWebService(c *restful.Container) error { Param(webservice.PathParameter("node", "node name")). Returns(http.StatusOK, ok, errors.Error{})) - c.Add(webservice) - tags = []string{"Applications"} webservice.Route(webservice.GET("/applications").