Merge pull request #584 from wonderflow/remove

remove annotation for apiversion and kind, use discoverymapper instead
This commit is contained in:
Jianbo Sun
2020-11-12 15:58:53 +08:00
committed by GitHub
52 changed files with 436 additions and 466 deletions
-2
View File
@@ -11,8 +11,6 @@ const (
)
const (
AnnAPIVersion = "definition.oam.dev/apiVersion"
AnnKind = "definition.oam.dev/kind"
AnnDescription = "definition.oam.dev/description"
LabelPodSpecable = "workload.oam.dev/podspecable"
@@ -2,9 +2,6 @@ apiVersion: core.oam.dev/v1alpha2
kind: ScopeDefinition
metadata:
name: healthscopes.core.oam.dev
annotations:
definition.oam.dev/apiVersion: core.oam.dev/v1alpha2
definition.oam.dev/kind: HealthScope
namespace: default
spec:
workloadRefsPath: spec.workloadRefs
@@ -3,8 +3,6 @@ kind: TraitDefinition
metadata:
name: autoscale
annotations:
definition.oam.dev/apiVersion: standard.oam.dev/v1alpha1
definition.oam.dev/kind: Autoscaler
definition.oam.dev/description: "Automatically scale workloads"
spec:
appliesToWorkloads:
@@ -2,8 +2,6 @@ apiVersion: core.oam.dev/v1alpha2
kind: TraitDefinition
metadata:
annotations:
definition.oam.dev/apiVersion: core.oam.dev/v1alpha2
definition.oam.dev/kind: ManualScalerTrait
definition.oam.dev/description: "Scale replica for workload"
name: scaler
spec:
@@ -3,8 +3,6 @@ kind: TraitDefinition
metadata:
name: metric
annotations:
definition.oam.dev/apiVersion: standard.oam.dev/v1alpha1
definition.oam.dev/kind: MetricsTrait
definition.oam.dev/description: "Add metric monitoring for workload"
spec:
appliesToWorkloads:
@@ -3,8 +3,6 @@ kind: TraitDefinition
metadata:
name: route
annotations:
definition.oam.dev/apiVersion: standard.oam.dev/v1alpha1
definition.oam.dev/kind: Route
definition.oam.dev/description: "Add a route for workload"
spec:
appliesToWorkloads:
@@ -3,8 +3,6 @@ kind: WorkloadDefinition
metadata:
name: task
annotations:
definition.oam.dev/apiVersion: "v1"
definition.oam.dev/kind: "Job"
definition.oam.dev/description: "One-time task/job"
spec:
definitionRef:
@@ -3,8 +3,6 @@ kind: WorkloadDefinition
metadata:
name: webservice
annotations:
definition.oam.dev/apiVersion: "apps/v1"
definition.oam.dev/kind: "Deployment"
definition.oam.dev/description: "Long running service with network routes"
spec:
definitionRef:
@@ -3,8 +3,6 @@ kind: WorkloadDefinition
metadata:
name: worker
annotations:
definition.oam.dev/apiVersion: "apps/v1"
definition.oam.dev/kind: "Deployment"
definition.oam.dev/description: "Backend worker without ports exposed"
spec:
definitionRef:
-2
View File
@@ -25,8 +25,6 @@ kind: TraitDefinition
metadata:
name: kubewatch
annotations:
definition.oam.dev/apiVersion: labs.bitnami.com/v1alpha1
definition.oam.dev/kind: KubeWatch
definition.oam.dev/description: "Add a watch for resource"
spec:
appliesToWorkloads:
@@ -3,8 +3,6 @@ kind: WorkloadDefinition
metadata:
name: rds
annotations:
definition.oam.dev/apiVersion: "database.example.org/v1alpha1"
definition.oam.dev/kind: "PostgreSQLInstance"
definition.oam.dev/description: "RDS on Ali Cloud"
spec:
definitionRef:
@@ -3,8 +3,6 @@ kind: WorkloadDefinition
metadata:
name: webservice
annotations:
definition.oam.dev/apiVersion: "standard.oam.dev/v1alpha1"
definition.oam.dev/kind: "PodSpecWorkload"
definition.oam.dev/description: "Flight tracker web ui"
spec:
definitionRef:
@@ -2,9 +2,6 @@ apiVersion: core.oam.dev/v1alpha2
kind: TraitDefinition
metadata:
name: autoscalers.standard.oam.dev
annotations:
definition.oam.dev/apiVersion: standard.oam.dev/v1alpha1
definition.oam.dev/kind: Autoscaler
spec:
appliesToWorkloads:
- webservice
@@ -3,8 +3,6 @@ kind: TraitDefinition
metadata:
name: route
annotations:
definition.oam.dev/apiVersion: standard.oam.dev/v1alpha1
definition.oam.dev/kind: Route
definition.oam.dev/description: "Add a route for workload"
spec:
appliesToWorkloads:
@@ -21,8 +19,6 @@ kind: WorkloadDefinition
metadata:
name: webservice
annotations:
definition.oam.dev/apiVersion: "standard.oam.dev/v1alpha1"
definition.oam.dev/kind: "PodSpecWorkload"
definition.oam.dev/description: "Long running service with ports exposed"
spec:
definitionRef:
@@ -3,8 +3,6 @@ kind: TraitDefinition
metadata:
name: autoscale
annotations:
definition.oam.dev/apiVersion: standard.oam.dev/v1alpha1
definition.oam.dev/kind: Autoscaler
definition.oam.dev/description: "Automatically scale workloads"
spec:
appliesToWorkloads:
@@ -2,8 +2,6 @@ apiVersion: core.oam.dev/v1alpha2
kind: TraitDefinition
metadata:
annotations:
definition.oam.dev/apiVersion: core.oam.dev/v1alpha2
definition.oam.dev/kind: ManualScalerTrait
definition.oam.dev/description: "Scale replica for workload"
name: scaler
spec:
@@ -3,8 +3,6 @@ kind: TraitDefinition
metadata:
name: metric
annotations:
definition.oam.dev/apiVersion: standard.oam.dev/v1alpha1
definition.oam.dev/kind: MetricsTrait
definition.oam.dev/description: "Add metric monitoring for workload"
spec:
appliesToWorkloads:
@@ -3,8 +3,6 @@ kind: TraitDefinition
metadata:
name: route
annotations:
definition.oam.dev/apiVersion: standard.oam.dev/v1alpha1
definition.oam.dev/kind: Route
definition.oam.dev/description: "Add a route for workload"
spec:
appliesToWorkloads:
@@ -3,8 +3,6 @@ kind: WorkloadDefinition
metadata:
name: task
annotations:
definition.oam.dev/apiVersion: "v1"
definition.oam.dev/kind: "Job"
definition.oam.dev/description: "One-time task/job"
spec:
definitionRef:
@@ -3,8 +3,6 @@ kind: WorkloadDefinition
metadata:
name: webservice
annotations:
definition.oam.dev/apiVersion: "apps/v1"
definition.oam.dev/kind: "Deployment"
definition.oam.dev/description: "Long running service with network routes"
spec:
definitionRef:
@@ -3,8 +3,6 @@ kind: WorkloadDefinition
metadata:
name: worker
annotations:
definition.oam.dev/apiVersion: "apps/v1"
definition.oam.dev/kind: "Deployment"
definition.oam.dev/description: "Backend worker without ports exposed"
spec:
definitionRef:
+7 -1
View File
@@ -5,6 +5,8 @@ import (
"fmt"
"strings"
"github.com/crossplane/oam-kubernetes-runtime/pkg/oam/discoverymapper"
"github.com/gosuri/uitable"
"github.com/spf13/cobra"
"sigs.k8s.io/controller-runtime/pkg/client"
@@ -94,7 +96,11 @@ func NewCapInstallCommand(c types.Args, ioStreams cmdutil.IOStreams) *cobra.Comm
if err != nil {
return err
}
if _, err = oam.AddCapabilityIntoCluster(newClient, args[0]); err != nil {
mapper, err := discoverymapper.New(c.Config)
if err != nil {
return err
}
if _, err = oam.AddCapabilityIntoCluster(newClient, mapper, args[0]); err != nil {
return err
}
return nil
+8 -7
View File
@@ -51,7 +51,7 @@ func NewDashboardCommand(c types.Args, ioStreams cmdutil.IOStreams, frontendSour
if !runtimeReady {
return nil
}
return SetupAPIServer(newClient, cmd, o)
return SetupAPIServer(c, cmd, o)
},
Annotations: map[string]string{
types.TagCommandType: types.TypeSystem,
@@ -124,8 +124,7 @@ func (o *Options) GetStaticPath() error {
return nil
}
func SetupAPIServer(kubeClient client.Client, cmd *cobra.Command, o Options) error {
func SetupAPIServer(c types.Args, cmd *cobra.Command, o Options) error {
// setup logging
var w io.Writer
if len(o.logFilePath) > 0 {
@@ -154,12 +153,14 @@ func SetupAPIServer(kubeClient client.Client, cmd *cobra.Command, o Options) err
}
//Setup RESTful server
server := server.APIServer{}
server, err := server.New(c, o.port, o.staticPath)
if err != nil {
return err
}
errCh := make(chan error, 1)
cmd.Printf("Serving at %v\nstatic dir is %v", o.port, o.staticPath)
server.Launch(kubeClient, o.port, o.staticPath, errCh)
server.Launch(errCh)
select {
case err = <-errCh:
return err
@@ -207,5 +208,5 @@ func CheckVelaRuntimeInstalledAndReady(ioStreams cmdutil.IOStreams, c client.Cli
white.Sprint("vela install --help")))
return false, nil
}
return PrintTrackVelaRuntimeStatus(context.Background(), c, ioStreams)
return PrintTrackVelaRuntimeStatus(context.Background(), c, ioStreams, 5*time.Minute)
}
+1 -1
View File
@@ -65,7 +65,7 @@ func NewEnvInitCommand(c types.Args, ioStreams cmdutil.IOStreams) *cobra.Command
return err
}
if syncCluster {
if err := RefreshDefinitions(ctx, newClient, ioStreams, true); err != nil {
if err := RefreshDefinitions(ctx, c, ioStreams, true); err != nil {
return err
}
}
+1 -3
View File
@@ -9,8 +9,6 @@ import (
cmdutil "github.com/oam-dev/kubevela/pkg/commands/util"
"github.com/oam-dev/kubevela/pkg/plugins"
"github.com/oam-dev/kubevela/pkg/utils/system"
"sigs.k8s.io/controller-runtime/pkg/client"
)
type refreshStatus string
@@ -22,7 +20,7 @@ const (
deleted refreshStatus = "Deleted"
)
func RefreshDefinitions(ctx context.Context, c client.Client, ioStreams cmdutil.IOStreams, silentOutput bool) error {
func RefreshDefinitions(ctx context.Context, c types.Args, ioStreams cmdutil.IOStreams, silentOutput bool) error {
dir, _ := system.GetCapabilityDir()
oldCaps, err := plugins.LoadAllInstalledCapability()
+48 -9
View File
@@ -4,6 +4,8 @@ import (
"context"
"fmt"
"io"
"io/ioutil"
"os"
"time"
"github.com/openservicemesh/osm/pkg/cli"
@@ -17,6 +19,7 @@ import (
"github.com/oam-dev/kubevela/api/types"
cmdutil "github.com/oam-dev/kubevela/pkg/commands/util"
"github.com/oam-dev/kubevela/pkg/plugins"
"github.com/oam-dev/kubevela/pkg/utils/helm"
)
@@ -35,7 +38,8 @@ type initCmd struct {
client client.Client
chartPath string
chartArgs chartArgs
waitReady bool
waitReady string
c types.Args
}
type chartArgs struct {
@@ -103,6 +107,7 @@ func NewInstallCommand(c types.Args, chartContent string, ioStreams cmdutil.IOSt
}
i.client = newClient
i.namespace = types.DefaultOAMNS
i.c = c
return i.run(ioStreams, chartContent)
},
Annotations: map[string]string{
@@ -115,12 +120,17 @@ func NewInstallCommand(c types.Args, chartContent string, ioStreams cmdutil.IOSt
flag.StringVarP(&i.chartArgs.imagePullPolicy, "image-pull-policy", "", "IfNotPresent", "vela core image pull policy, this will align to chart value image.pullPolicy")
flag.StringVarP(&i.chartArgs.imageRepo, "image-repo", "", "oamdev/vela-core", "vela core image repo, this will align to chart value image.repo")
flag.StringVarP(&i.chartArgs.imageTag, "image-tag", "", "latest", "vela core image repo, this will align to chart value image.tag")
flag.BoolVarP(&i.waitReady, "wait", "w", false, "wait until vela-core is ready to serve")
flag.StringVarP(&i.waitReady, "wait", "w", "0s", "wait until vela-core is ready to serve, default will not wait")
return cmd
}
func (i *initCmd) run(ioStreams cmdutil.IOStreams, chartSource string) error {
waitDuration, err := time.ParseDuration(i.waitReady)
if err != nil {
return fmt.Errorf("invalid wait timeoout duration %v, should use '120s', '5m' like format", err)
}
ioStreams.Info("- Installing Vela Core Chart:")
exist, err := cmdutil.DoesNamespaceExist(i.client, types.DefaultOAMNS)
if err != nil {
@@ -145,14 +155,16 @@ func (i *initCmd) run(ioStreams cmdutil.IOStreams, chartSource string) error {
return err
}
}
if err := RefreshDefinitions(context.Background(), i.client, ioStreams, false); err != nil {
if err = CheckCapabilityReady(context.Background(), i.c, waitDuration); err != nil {
return err
}
if err := RefreshDefinitions(context.Background(), i.c, ioStreams, false); err != nil {
return err
}
ioStreams.Info("- Finished successfully.")
if i.waitReady {
_, err := PrintTrackVelaRuntimeStatus(context.Background(), i.client, ioStreams)
if waitDuration > 0 {
_, err := PrintTrackVelaRuntimeStatus(context.Background(), i.client, ioStreams, waitDuration)
if err != nil {
return err
}
@@ -160,6 +172,34 @@ func (i *initCmd) run(ioStreams cmdutil.IOStreams, chartSource string) error {
return nil
}
// MUST wait to install capability succeed
func CheckCapabilityReady(ctx context.Context, c types.Args, timeout time.Duration) error {
if timeout < 2*time.Minute {
timeout = 2 * time.Minute
}
tmpdir, err := ioutil.TempDir(".", "tmpcap")
if err != nil {
return err
}
defer os.RemoveAll(tmpdir)
start := time.Now()
spiner := newTrackingSpinner("Waiting Capability ready to install ...")
spiner.Start()
defer spiner.Stop()
for {
_, err = plugins.GetCapabilitiesFromCluster(ctx, types.DefaultOAMNS, c, tmpdir, nil)
if err == nil {
return nil
}
if time.Since(start) > timeout {
return fmt.Errorf("timeout checking capability ready: %v", err)
}
time.Sleep(5 * time.Second)
}
}
func (i *initCmd) resolveValues() (map[string]interface{}, error) {
finalValues := map[string]interface{}{}
valuesConfig := []string{
@@ -222,9 +262,8 @@ func GetOAMReleaseVersion(ns string) (string, error) {
return "", errors.New("oam-kubernetes-runtime not found in your kubernetes cluster, try `vela install` to install")
}
func PrintTrackVelaRuntimeStatus(ctx context.Context, c client.Client, ioStreams cmdutil.IOStreams) (bool, error) {
trackTimeout := 5 * time.Minute
trackInterval := 2 * time.Second
func PrintTrackVelaRuntimeStatus(ctx context.Context, c client.Client, ioStreams cmdutil.IOStreams, trackTimeout time.Duration) (bool, error) {
trackInterval := 5 * time.Second
ioStreams.Info("\nIt may take 1-2 minutes before KubeVela runtime is ready.")
start := time.Now()
+1 -6
View File
@@ -10,7 +10,6 @@ import (
"github.com/gosuri/uitable"
cmdutil "github.com/oam-dev/kubevela/pkg/commands/util"
"github.com/spf13/cobra"
"sigs.k8s.io/controller-runtime/pkg/client"
)
func NewTraitsCommand(c types.Args, ioStreams cmdutil.IOStreams) *cobra.Command {
@@ -25,11 +24,7 @@ func NewTraitsCommand(c types.Args, ioStreams cmdutil.IOStreams) *cobra.Command
Example: `vela traits`,
RunE: func(cmd *cobra.Command, args []string) error {
if syncCluster {
newClient, err := client.New(c.Config, client.Options{Scheme: c.Schema})
if err != nil {
return err
}
if err := RefreshDefinitions(ctx, newClient, ioStreams, true); err != nil {
if err := RefreshDefinitions(ctx, c, ioStreams, true); err != nil {
return err
}
}
-10
View File
@@ -6,8 +6,6 @@ import (
"os"
"strings"
"github.com/oam-dev/kubevela/api/types"
"github.com/AlecAivazis/survey/v2"
corev1alpha2 "github.com/crossplane/oam-kubernetes-runtime/apis/core/v1alpha2"
"github.com/spf13/cobra"
@@ -63,14 +61,6 @@ func GetComponent(ctx context.Context, c client.Client, componentName string, na
return component, err
}
func GetAPIVersionKindFromTrait(td corev1alpha2.TraitDefinition) (string, string) {
return td.Annotations[types.AnnAPIVersion], td.Annotations[types.AnnKind]
}
func GetAPIVersionKindFromWorkload(td corev1alpha2.WorkloadDefinition) (string, string) {
return td.Annotations[types.AnnAPIVersion], td.Annotations[types.AnnKind]
}
func PrintFlags(cmd *cobra.Command, subcmds []*cobra.Command) {
cmd.Println("Flags:")
for _, sub := range subcmds {
+1 -6
View File
@@ -9,7 +9,6 @@ import (
"github.com/gosuri/uitable"
"github.com/spf13/cobra"
"sigs.k8s.io/controller-runtime/pkg/client"
)
func NewWorkloadsCommand(c types.Args, ioStreams cmdutil.IOStreams) *cobra.Command {
@@ -23,11 +22,7 @@ func NewWorkloadsCommand(c types.Args, ioStreams cmdutil.IOStreams) *cobra.Comma
Example: `vela workloads`,
RunE: func(cmd *cobra.Command, args []string) error {
if syncCluster {
newClient, err := client.New(c.Config, client.Options{Scheme: c.Schema})
if err != nil {
return err
}
if err := RefreshDefinitions(ctx, newClient, ioStreams, true); err != nil {
if err := RefreshDefinitions(ctx, c, ioStreams, true); err != nil {
return err
}
}
+19 -13
View File
@@ -10,6 +10,8 @@ import (
"strings"
"github.com/crossplane/oam-kubernetes-runtime/apis/core/v1alpha2"
"github.com/crossplane/oam-kubernetes-runtime/pkg/oam/discoverymapper"
"github.com/crossplane/oam-kubernetes-runtime/pkg/oam/util"
"github.com/ghodss/yaml"
apierrors "k8s.io/apimachinery/pkg/api/errors"
v1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@@ -59,7 +61,7 @@ func SyncCapabilityFromCenter(capName, capURL, capToken string) error {
return client.SyncCapabilityFromCenter()
}
func AddCapabilityIntoCluster(c client.Client, capability string) (string, error) {
func AddCapabilityIntoCluster(c client.Client, mapper discoverymapper.DiscoveryMapper, capability string) (string, error) {
ss := strings.Split(capability, "/")
if len(ss) < 2 {
return "", errors.New("invalid format for " + capability + ", please follow format <center>/<name>")
@@ -67,13 +69,13 @@ func AddCapabilityIntoCluster(c client.Client, capability string) (string, error
repoName := ss[0]
name := ss[1]
ioStreams := cmdutil.IOStreams{In: os.Stdin, Out: os.Stdout, ErrOut: os.Stderr}
if err := InstallCapability(c, repoName, name, ioStreams); err != nil {
if err := InstallCapability(c, mapper, repoName, name, ioStreams); err != nil {
return "", err
}
return fmt.Sprintf("Successfully installed capability %s from %s", name, repoName), nil
}
func InstallCapability(client client.Client, centerName, capabilityName string, ioStreams cmdutil.IOStreams) error {
func InstallCapability(client client.Client, mapper discoverymapper.DiscoveryMapper, centerName, capabilityName string, ioStreams cmdutil.IOStreams) error {
dir, _ := system.GetCapCenterDir()
repoDir := filepath.Join(dir, centerName)
tp, err := GetSyncedCapabilities(centerName, capabilityName)
@@ -100,11 +102,13 @@ func InstallCapability(client client.Client, centerName, capabilityName string,
return err
}
}
if apiVerion, kind := cmdutil.GetAPIVersionKindFromWorkload(wd); apiVerion != "" && kind != "" {
tp.CrdInfo = &types.CrdInfo{
APIVersion: apiVerion,
Kind: kind,
}
gvk, err := util.GetGVKFromDefinition(mapper, wd.Spec.Reference)
if err != nil {
return err
}
tp.CrdInfo = &types.CrdInfo{
APIVersion: gvk.GroupVersion().String(),
Kind: gvk.Kind,
}
if err = client.Create(context.Background(), &wd); err != nil && !apierrors.IsAlreadyExists(err) {
return err
@@ -126,11 +130,13 @@ func InstallCapability(client client.Client, centerName, capabilityName string,
return err
}
}
if apiVerion, kind := cmdutil.GetAPIVersionKindFromTrait(td); apiVerion != "" && kind != "" {
tp.CrdInfo = &types.CrdInfo{
APIVersion: apiVerion,
Kind: kind,
}
gvk, err := util.GetGVKFromDefinition(mapper, td.Spec.Reference)
if err != nil {
return err
}
tp.CrdInfo = &types.CrdInfo{
APIVersion: gvk.GroupVersion().String(),
Kind: gvk.Kind,
}
if err = client.Create(context.Background(), &td); err != nil && !apierrors.IsAlreadyExists(err) {
return err
+3 -6
View File
@@ -7,7 +7,6 @@ import (
"github.com/crossplane/oam-kubernetes-runtime/apis/core"
certmanager "github.com/wonderflow/cert-manager-api/pkg/apis/certmanager/v1"
clientgoscheme "k8s.io/client-go/kubernetes/scheme"
"sigs.k8s.io/controller-runtime/pkg/client"
"github.com/oam-dev/kubevela/api/types"
"github.com/oam-dev/kubevela/api/v1alpha1"
@@ -27,17 +26,15 @@ func init() {
// +kubebuilder:scaffold:scheme
}
func InitKubeClient() (client.Client, error) {
func InitArgs() (types.Args, error) {
restConf, err := config.GetConfig()
if err != nil {
fmt.Println("get kubeConfig err", err)
os.Exit(1)
}
commandArgs := types.Args{
return types.Args{
Config: restConf,
Schema: Scheme,
}
return client.New(commandArgs.Config, client.Options{Scheme: commandArgs.Schema})
}, nil
}
-58
View File
@@ -3,13 +3,10 @@ package oam
import (
"context"
"fmt"
"os"
"strconv"
"strings"
"cuelang.org/go/cue"
plur "github.com/gertd/go-pluralize"
"github.com/gin-gonic/gin"
"github.com/spf13/pflag"
"sigs.k8s.io/controller-runtime/pkg/client"
@@ -18,7 +15,6 @@ import (
cmdutil "github.com/oam-dev/kubevela/pkg/commands/util"
"github.com/oam-dev/kubevela/pkg/plugins"
"github.com/oam-dev/kubevela/pkg/server/apis"
env2 "github.com/oam-dev/kubevela/pkg/utils/env"
)
func ListTraitDefinitions(workloadName *string) ([]types.Capability, error) {
@@ -198,41 +194,6 @@ func AddOrUpdateTrait(env *types.EnvMeta, appName string, componentName string,
return app, app.Save(env.Name)
}
func AttachTrait(c *gin.Context, body apis.TraitBody) (string, error) {
// Prepare
var appObj *application.Application
fs := pflag.NewFlagSet("trait", pflag.ContinueOnError)
for _, f := range body.Flags {
fs.String(f.Name, f.Value, "")
}
var staging = false
var err error
if body.Staging != "" {
staging, err = strconv.ParseBool(body.Staging)
if err != nil {
return "", err
}
}
traitAlias := body.Name
template, err := plugins.GetInstalledCapabilityWithCapAlias(types.TypeTrait, traitAlias)
if err != nil {
return "", err
}
// Run step
env, err := env2.GetEnvByName(body.EnvName)
if err != nil {
return "", err
}
appObj, err = AddOrUpdateTrait(env, body.AppName, body.ComponentName, fs, template)
if err != nil {
return "", err
}
kubeClient := c.MustGet("KubeClient")
io := cmdutil.IOStreams{In: os.Stdin, Out: os.Stdout, ErrOut: os.Stderr}
return TraitOperationRun(c, kubeClient.(client.Client), env, appObj, staging, io)
}
func TraitOperationRun(ctx context.Context, c client.Client, env *types.EnvMeta, appObj *application.Application,
staging bool, io cmdutil.IOStreams) (string, error) {
if staging {
@@ -260,22 +221,3 @@ func PrepareDetachTrait(envName string, traitType string, componentName string,
}
return appObj, appObj.Save(envName)
}
func DetachTrait(c *gin.Context, envName string, traitType string, componentName string, appName string, staging bool) (string, error) {
var appObj *application.Application
var err error
if appName == "" {
appName = componentName
}
if appObj, err = PrepareDetachTrait(envName, traitType, componentName, appName); err != nil {
return "", err
}
// Run
env, err := env2.GetEnvByName(envName)
if err != nil {
return "", err
}
kubeClient := c.MustGet("KubeClient")
io := cmdutil.IOStreams{In: os.Stdin, Out: os.Stdout, ErrOut: os.Stderr}
return TraitOperationRun(c, kubeClient.(client.Client), env, appObj, staging, io)
}
+40 -16
View File
@@ -7,8 +7,11 @@ import (
"net/http"
"path/filepath"
"github.com/crossplane/oam-kubernetes-runtime/pkg/oam/util"
"github.com/crossplane/oam-kubernetes-runtime/pkg/oam/discoverymapper"
"github.com/oam-dev/kubevela/api/types"
cmdutil "github.com/oam-dev/kubevela/pkg/commands/util"
"github.com/oam-dev/kubevela/pkg/cue"
"github.com/oam-dev/kubevela/pkg/utils/system"
"github.com/pkg/errors"
@@ -21,7 +24,7 @@ import (
const DescriptionUndefined = "description not defined"
func GetCapabilitiesFromCluster(ctx context.Context, namespace string, c client.Client, syncDir string, selector labels.Selector) ([]types.Capability, error) {
func GetCapabilitiesFromCluster(ctx context.Context, namespace string, c types.Args, syncDir string, selector labels.Selector) ([]types.Capability, error) {
workloads, _, err := GetWorkloadsFromCluster(ctx, namespace, c, syncDir, selector)
if err != nil {
return nil, err
@@ -34,10 +37,19 @@ func GetCapabilitiesFromCluster(ctx context.Context, namespace string, c client.
return workloads, nil
}
func GetWorkloadsFromCluster(ctx context.Context, namespace string, c client.Client, syncDir string, selector labels.Selector) ([]types.Capability, []error, error) {
func GetWorkloadsFromCluster(ctx context.Context, namespace string, c types.Args, syncDir string, selector labels.Selector) ([]types.Capability, []error, error) {
newClient, err := client.New(c.Config, client.Options{Scheme: c.Schema})
if err != nil {
return nil, nil, err
}
dm, err := discoverymapper.New(c.Config)
if err != nil {
return nil, nil, err
}
var templates []types.Capability
var workloadDefs corev1alpha2.WorkloadDefinitionList
err := c.List(ctx, &workloadDefs, &client.ListOptions{Namespace: namespace, LabelSelector: selector})
err = newClient.List(ctx, &workloadDefs, &client.ListOptions{Namespace: namespace, LabelSelector: selector})
if err != nil {
return nil, nil, fmt.Errorf("list WorkloadDefinition err: %s", err)
}
@@ -49,21 +61,31 @@ func GetWorkloadsFromCluster(ctx context.Context, namespace string, c client.Cli
templateErrors = append(templateErrors, errors.Wrapf(err, "handle workload template `%s` failed", wd.Name))
continue
}
if apiVersion, kind := cmdutil.GetAPIVersionKindFromWorkload(wd); apiVersion != "" && kind != "" {
tmp.CrdInfo = &types.CrdInfo{
APIVersion: apiVersion,
Kind: kind,
}
gvk, err := util.GetGVKFromDefinition(dm, wd.Spec.Reference)
if err != nil {
return nil, nil, err
}
tmp.CrdInfo = &types.CrdInfo{
APIVersion: gvk.GroupVersion().String(),
Kind: gvk.Kind,
}
templates = append(templates, tmp)
}
return templates, templateErrors, nil
}
func GetTraitsFromCluster(ctx context.Context, namespace string, c client.Client, syncDir string, selector labels.Selector) ([]types.Capability, []error, error) {
func GetTraitsFromCluster(ctx context.Context, namespace string, c types.Args, syncDir string, selector labels.Selector) ([]types.Capability, []error, error) {
newClient, err := client.New(c.Config, client.Options{Scheme: c.Schema})
if err != nil {
return nil, nil, err
}
dm, err := discoverymapper.New(c.Config)
if err != nil {
return nil, nil, err
}
var templates []types.Capability
var traitDefs corev1alpha2.TraitDefinitionList
err := c.List(ctx, &traitDefs, &client.ListOptions{Namespace: namespace, LabelSelector: selector})
err = newClient.List(ctx, &traitDefs, &client.ListOptions{Namespace: namespace, LabelSelector: selector})
if err != nil {
return nil, nil, fmt.Errorf("list TraitDefinition err: %s", err)
}
@@ -75,11 +97,13 @@ func GetTraitsFromCluster(ctx context.Context, namespace string, c client.Client
templateErrors = append(templateErrors, errors.Wrapf(err, "handle trait template `%s` failed\n", td.Name))
continue
}
if apiVersion, kind := cmdutil.GetAPIVersionKindFromTrait(td); apiVersion != "" && kind != "" {
tmp.CrdInfo = &types.CrdInfo{
APIVersion: apiVersion,
Kind: kind,
}
gvk, err := util.GetGVKFromDefinition(dm, td.Spec.Reference)
if err != nil {
return nil, nil, err
}
tmp.CrdInfo = &types.CrdInfo{
APIVersion: gvk.GroupVersion().String(),
Kind: gvk.Kind,
}
templates = append(templates, tmp)
}
+18 -7
View File
@@ -16,7 +16,6 @@ import (
)
var _ = Describe("DefinitionFiles", func() {
route := types.Capability{
Name: "routes.test",
Type: types.TypeTrait,
@@ -29,13 +28,17 @@ var _ = Describe("DefinitionFiles", func() {
},
},
Description: "description not defined",
CrdName: "routes.test",
CrdName: "routes.standard.oam.dev",
CrdInfo: &types.CrdInfo{
APIVersion: "standard.oam.dev/v1alpha1",
Kind: "Route",
},
}
deployment := types.Capability{
Name: "deployments.testapps",
Type: types.TypeWorkload,
CrdName: "deployments.testapps",
CrdName: "deployments.apps",
Description: "description not defined",
Parameters: []types.Parameter{
{
@@ -58,6 +61,10 @@ var _ = Describe("DefinitionFiles", func() {
Usage: "Which port do you want customer traffic sent to",
},
},
CrdInfo: &types.CrdInfo{
APIVersion: "apps/v1",
Kind: "Deployment",
},
}
websvc := types.Capability{
@@ -80,7 +87,11 @@ var _ = Describe("DefinitionFiles", func() {
Default: int64(6379),
Usage: "Which port do you want customer traffic sent to",
}},
CrdName: "webservice.testapps",
CrdName: "deployments.apps",
CrdInfo: &types.CrdInfo{
APIVersion: "apps/v1",
Kind: "Deployment",
},
}
req, _ := labels.NewRequirement("usecase", selection.Equals, []string{"forplugintest"})
@@ -89,7 +100,7 @@ var _ = Describe("DefinitionFiles", func() {
// Notice!! DefinitionPath Object is Cluster Scope object
// which means objects created in other DefinitionNamespace will also affect here.
It("gettrait", func() {
traitDefs, _, err := GetTraitsFromCluster(context.Background(), DefinitionNamespace, k8sClient, definitionDir, selector)
traitDefs, _, err := GetTraitsFromCluster(context.Background(), DefinitionNamespace, types.Args{Config: cfg, Schema: scheme}, definitionDir, selector)
Expect(err).Should(BeNil())
logf.Log.Info(fmt.Sprintf("Getting trait definitions %v", traitDefs))
for i := range traitDefs {
@@ -105,7 +116,7 @@ var _ = Describe("DefinitionFiles", func() {
// Notice!! DefinitionPath Object is Cluster Scope object
// which means objects created in other DefinitionNamespace will also affect here.
It("getworkload", func() {
workloadDefs, _, err := GetWorkloadsFromCluster(context.Background(), DefinitionNamespace, k8sClient, definitionDir, selector)
workloadDefs, _, err := GetWorkloadsFromCluster(context.Background(), DefinitionNamespace, types.Args{Config: cfg, Schema: scheme}, definitionDir, selector)
Expect(err).Should(BeNil())
logf.Log.Info(fmt.Sprintf("Getting workload definitions %v", workloadDefs))
for i := range workloadDefs {
@@ -118,7 +129,7 @@ var _ = Describe("DefinitionFiles", func() {
Expect(workloadDefs).Should(Equal([]types.Capability{deployment, websvc}))
})
It("getall", func() {
alldef, err := GetCapabilitiesFromCluster(context.Background(), DefinitionNamespace, k8sClient, definitionDir, selector)
alldef, err := GetCapabilitiesFromCluster(context.Background(), DefinitionNamespace, types.Args{Config: cfg, Schema: scheme}, definitionDir, selector)
Expect(err).Should(BeNil())
logf.Log.Info(fmt.Sprintf("Getting all definitions %v", alldef))
for i := range alldef {
+3 -48
View File
@@ -33,6 +33,7 @@ import (
// http://onsi.github.io/ginkgo/ to learn more about Ginkgo.
var cfg *rest.Config
var scheme *runtime.Scheme
var k8sClient client.Client
var testEnv *envtest.Environment
var definitionDir string
@@ -53,7 +54,7 @@ var _ = BeforeSuite(func(done Done) {
By("bootstrapping test environment")
useExistCluster := false
testEnv = &envtest.Environment{
CRDDirectoryPaths: []string{filepath.Join("..", "config", "crd", "bases")},
CRDDirectoryPaths: []string{filepath.Join("..", "..", "charts", "vela-core", "crds")},
UseExistingCluster: &useExistCluster,
}
@@ -61,63 +62,17 @@ var _ = BeforeSuite(func(done Done) {
cfg, err = testEnv.Start()
Expect(err).ToNot(HaveOccurred())
Expect(cfg).ToNot(BeNil())
scheme := runtime.NewScheme()
scheme = runtime.NewScheme()
Expect(corev1alpha2.AddToScheme(scheme)).NotTo(HaveOccurred())
Expect(clientgoscheme.AddToScheme(scheme)).NotTo(HaveOccurred())
Expect(v1beta1.AddToScheme(scheme)).NotTo(HaveOccurred())
k8sClient, err = client.New(cfg, client.Options{Scheme: scheme})
Expect(err).ToNot(HaveOccurred())
Expect(k8sClient).ToNot(BeNil())
crd := v1beta1.CustomResourceDefinition{
ObjectMeta: metav1.ObjectMeta{
Name: "traitdefinitions.core.oam.dev",
},
Spec: v1beta1.CustomResourceDefinitionSpec{
Group: "core.oam.dev",
Names: v1beta1.CustomResourceDefinitionNames{
Kind: "TraitDefinition",
ListKind: "TraitDefinitionList",
Plural: "traitdefinitions",
Singular: "traitdefinition",
},
Versions: []v1beta1.CustomResourceDefinitionVersion{
{
Name: "v1alpha2",
Served: true,
Storage: true,
},
},
},
}
Expect(k8sClient.Create(context.Background(), &crd)).Should(SatisfyAny(BeNil(), &util.AlreadyExistMatcher{}))
crd = v1beta1.CustomResourceDefinition{
ObjectMeta: metav1.ObjectMeta{
Name: "workloaddefinitions.core.oam.dev",
},
Spec: v1beta1.CustomResourceDefinitionSpec{
Group: "core.oam.dev",
Names: v1beta1.CustomResourceDefinitionNames{
Kind: "WorkloadDefinition",
ListKind: "WorkloadDefinitionList",
Plural: "workloaddefinitions",
Singular: "workloaddefinition",
},
Versions: []v1beta1.CustomResourceDefinitionVersion{
{
Name: "v1alpha2",
Served: true,
Storage: true,
},
},
},
}
definitionDir, err = system.GetCapabilityDir()
Expect(err).Should(BeNil())
Expect(os.MkdirAll(definitionDir, 0755)).Should(BeNil())
Expect(k8sClient.Create(context.Background(), &crd)).Should(SatisfyAny(BeNil(), &util.AlreadyExistMatcher{}))
Expect(k8sClient.Create(ctx, &corev1.Namespace{ObjectMeta: metav1.ObjectMeta{Name: DefinitionNamespace}})).Should(SatisfyAny(BeNil(), &util.AlreadyExistMatcher{}))
-3
View File
@@ -1,9 +1,6 @@
apiVersion: core.oam.dev/v1alpha2
kind: TraitDefinition
metadata:
annotations:
definition.oam.dev/apiVersion: core.oam.dev/v1alpha2
definition.oam.dev/kind: ManualScalerTrait
name: scaler
namespace: default
spec:
+1 -3
View File
@@ -6,12 +6,10 @@ metadata:
usecase: forplugintest
spec:
definitionRef:
name: routes.test
name: routes.standard.oam.dev
extension:
template: |
output: {
apiVersion: "apps/v1"
kind: "Route"
spec: {
domain: parameter.domain
}
+1 -1
View File
@@ -6,7 +6,7 @@ metadata:
usecase: forplugintest
spec:
definitionRef:
name: webservice.testapps
name: deployments.apps
extension:
template: |
output: {
+1 -1
View File
@@ -6,7 +6,7 @@ metadata:
usecase: forplugintest
spec:
definitionRef:
name: deployments.testapps
name: deployments.apps
extension:
template: |
output: {
+26 -5
View File
@@ -5,23 +5,44 @@ import (
"net/http"
"time"
"github.com/oam-dev/kubevela/api/types"
"github.com/crossplane/oam-kubernetes-runtime/pkg/oam/discoverymapper"
ctrl "sigs.k8s.io/controller-runtime"
"sigs.k8s.io/controller-runtime/pkg/client"
)
type APIServer struct {
server *http.Server
server *http.Server
KubeClient client.Client
dm discoverymapper.DiscoveryMapper
}
func (s *APIServer) Launch(kubeClient client.Client, port, staticPath string, errChan chan<- error) {
s.server = &http.Server{
func New(c types.Args, port, staticPath string) (*APIServer, error) {
newClient, err := client.New(c.Config, client.Options{Scheme: c.Schema})
if err != nil {
return nil, err
}
dm, err := discoverymapper.New(c.Config)
if err != nil {
return nil, err
}
s := &APIServer{
KubeClient: newClient,
dm: dm,
}
server := &http.Server{
Addr: port,
Handler: setupRoute(kubeClient, staticPath),
Handler: s.setupRoute(staticPath),
ReadTimeout: 5 * time.Second,
WriteTimeout: 10 * time.Second,
}
s.server.SetKeepAlivesEnabled(true)
server.SetKeepAlivesEnabled(true)
s.server = server
return s, nil
}
func (s *APIServer) Launch(errChan chan<- error) {
go func() {
err := s.server.ListenAndServe()
if err != nil && err != http.ErrServerClosed {
@@ -1,21 +1,17 @@
package handler
package server
import (
"github.com/oam-dev/kubevela/pkg/oam"
"github.com/oam-dev/kubevela/pkg/server/util"
"github.com/oam-dev/kubevela/pkg/utils/env"
"sigs.k8s.io/controller-runtime/pkg/client"
"github.com/gin-gonic/gin"
"github.com/oam-dev/kubevela/pkg/oam"
)
func UpdateApps(c *gin.Context) {
func (s *APIServer) UpdateApps(c *gin.Context) {
}
func GetApp(c *gin.Context) {
kubeClient := c.MustGet("KubeClient")
func (s *APIServer) GetApp(c *gin.Context) {
envName := c.Param("envName")
envMeta, err := env.GetEnvByName(envName)
if err != nil {
@@ -25,7 +21,7 @@ func GetApp(c *gin.Context) {
namespace := envMeta.Namespace
appName := c.Param("appName")
ctx := util.GetContext(c)
applicationMeta, err := oam.RetrieveApplicationStatusByName(ctx, kubeClient.(client.Client), appName, namespace)
applicationMeta, err := oam.RetrieveApplicationStatusByName(ctx, s.KubeClient, appName, namespace)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err)
return
@@ -33,8 +29,7 @@ func GetApp(c *gin.Context) {
util.AssembleResponse(c, applicationMeta, nil)
}
func ListApps(c *gin.Context) {
kubeClient := c.MustGet("KubeClient")
func (s *APIServer) ListApps(c *gin.Context) {
envName := c.Param("envName")
envMeta, err := env.GetEnvByName(envName)
if err != nil {
@@ -44,7 +39,7 @@ func ListApps(c *gin.Context) {
namespace := envMeta.Namespace
ctx := util.GetContext(c)
applicationMetaList, err := oam.ListApplications(ctx, kubeClient.(client.Client), oam.Option{Namespace: namespace})
applicationMetaList, err := oam.ListApplications(ctx, s.KubeClient, oam.Option{Namespace: namespace})
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
@@ -52,8 +47,7 @@ func ListApps(c *gin.Context) {
util.AssembleResponse(c, applicationMetaList, nil)
}
func DeleteApps(c *gin.Context) {
kubeClient := c.MustGet("KubeClient")
func (s *APIServer) DeleteApps(c *gin.Context) {
envName := c.Param("envName")
envMeta, err := env.GetEnvByName(envName)
if err != nil {
@@ -63,7 +57,7 @@ func DeleteApps(c *gin.Context) {
appName := c.Param("appName")
o := oam.DeleteOptions{
Client: kubeClient.(client.Client),
Client: s.KubeClient,
Env: envMeta,
AppName: appName,
}
@@ -1,4 +1,4 @@
package handler
package server
import (
"github.com/oam-dev/kubevela/pkg/oam"
@@ -6,10 +6,9 @@ import (
"github.com/oam-dev/kubevela/pkg/server/util"
"github.com/gin-gonic/gin"
"sigs.k8s.io/controller-runtime/pkg/client"
)
func AddCapabilityCenter(c *gin.Context) {
func (s *APIServer) AddCapabilityCenter(c *gin.Context) {
var body plugins.CapCenterConfig
if err := c.ShouldBindJSON(&body); err != nil {
util.HandleError(c, util.StatusInternalServerError, "the add capability center request body is invalid")
@@ -22,7 +21,7 @@ func AddCapabilityCenter(c *gin.Context) {
util.AssembleResponse(c, "Successfully configured capability center and synchronized from remote", nil)
}
func ListCapabilityCenters(c *gin.Context) {
func (s *APIServer) ListCapabilityCenters(c *gin.Context) {
capabilityCenterList, err := oam.ListCapabilityCenters()
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
@@ -31,7 +30,7 @@ func ListCapabilityCenters(c *gin.Context) {
util.AssembleResponse(c, capabilityCenterList, nil)
}
func SyncCapabilityCenter(c *gin.Context) {
func (s *APIServer) SyncCapabilityCenter(c *gin.Context) {
capabilityCenterName := c.Param("capabilityCenterName")
if err := oam.SyncCapabilityCenter(capabilityCenterName); err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
@@ -40,10 +39,9 @@ func SyncCapabilityCenter(c *gin.Context) {
util.AssembleResponse(c, "sync finished", nil)
}
func AddCapabilityIntoCluster(c *gin.Context) {
func (s *APIServer) AddCapabilityIntoCluster(c *gin.Context) {
cap := c.Param("capabilityCenterName") + "/" + c.Param("capabilityName")
kubeClient := c.MustGet("KubeClient")
msg, err := oam.AddCapabilityIntoCluster(kubeClient.(client.Client), cap)
msg, err := oam.AddCapabilityIntoCluster(s.KubeClient, s.dm, cap)
if err != nil {
util.HandleError(c, util.StatusInternalServerError)
return
@@ -51,16 +49,15 @@ func AddCapabilityIntoCluster(c *gin.Context) {
util.AssembleResponse(c, msg, nil)
}
func DeleteCapabilityCenter(c *gin.Context) {
func (s *APIServer) DeleteCapabilityCenter(c *gin.Context) {
capabilityCenterName := c.Param("capabilityCenterName")
msg, err := oam.RemoveCapabilityCenter(capabilityCenterName)
util.AssembleResponse(c, msg, err)
}
func RemoveCapabilityFromCluster(c *gin.Context) {
func (s *APIServer) RemoveCapabilityFromCluster(c *gin.Context) {
capabilityCenterName := c.Param("capabilityName")
kubeClient := c.MustGet("KubeClient")
msg, err := oam.RemoveCapabilityFromCluster(kubeClient.(client.Client), capabilityCenterName)
msg, err := oam.RemoveCapabilityFromCluster(s.KubeClient, capabilityCenterName)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
@@ -68,7 +65,7 @@ func RemoveCapabilityFromCluster(c *gin.Context) {
util.AssembleResponse(c, msg, nil)
}
func ListCapabilities(c *gin.Context) {
func (s *APIServer) ListCapabilities(c *gin.Context) {
capabilityCenterName := c.Param("capabilityName")
capabilityList, err := oam.ListCapabilities(capabilityCenterName)
if err != nil {
@@ -1,10 +1,9 @@
package handler
package server
import (
"os"
"github.com/gin-gonic/gin"
"sigs.k8s.io/controller-runtime/pkg/client"
cmdutil "github.com/oam-dev/kubevela/pkg/commands/util"
"github.com/oam-dev/kubevela/pkg/oam"
@@ -12,8 +11,7 @@ import (
"github.com/oam-dev/kubevela/pkg/utils/env"
)
func GetComponent(c *gin.Context) {
kubeClient := c.MustGet("KubeClient")
func (s *APIServer) GetComponent(c *gin.Context) {
envName := c.Param("envName")
envMeta, err := env.GetEnvByName(envName)
if err != nil {
@@ -24,7 +22,7 @@ func GetComponent(c *gin.Context) {
applicationName := c.Param("appName")
componentName := c.Param("compName")
ctx := util.GetContext(c)
componentMeta, err := oam.RetrieveComponent(ctx, kubeClient.(client.Client), applicationName, componentName, namespace)
componentMeta, err := oam.RetrieveComponent(ctx, s.KubeClient, applicationName, componentName, namespace)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err)
return
@@ -32,8 +30,7 @@ func GetComponent(c *gin.Context) {
util.AssembleResponse(c, componentMeta, nil)
}
func DeleteComponent(c *gin.Context) {
kubeClient := c.MustGet("KubeClient")
func (s *APIServer) DeleteComponent(c *gin.Context) {
envName := c.Param("envName")
envMeta, err := env.GetEnvByName(envName)
if err != nil {
@@ -44,7 +41,7 @@ func DeleteComponent(c *gin.Context) {
componentName := c.Param("compName")
o := oam.DeleteOptions{
Client: kubeClient.(client.Client),
Client: s.KubeClient,
Env: envMeta,
AppName: appName,
CompName: componentName}
@@ -1,20 +1,17 @@
package handler
package server
import (
"github.com/gin-gonic/gin"
ctrl "sigs.k8s.io/controller-runtime"
"github.com/oam-dev/kubevela/api/types"
"github.com/oam-dev/kubevela/pkg/utils/env"
ctrl "sigs.k8s.io/controller-runtime"
"sigs.k8s.io/controller-runtime/pkg/client"
"github.com/oam-dev/kubevela/pkg/server/apis"
"github.com/oam-dev/kubevela/pkg/server/util"
"github.com/oam-dev/kubevela/pkg/utils/env"
)
// environment related handlers
func CreateEnv(c *gin.Context) {
func (s *APIServer) CreateEnv(c *gin.Context) {
var environment apis.Environment
if err := c.ShouldBindJSON(&environment); err != nil {
util.HandleError(c, util.InvalidArgument, "the create environment request body is invalid")
@@ -28,8 +25,7 @@ func CreateEnv(c *gin.Context) {
}
ctx := util.GetContext(c)
kubeClient := c.MustGet("KubeClient")
message, err := env.CreateEnv(ctx, kubeClient.(client.Client), name, &types.EnvMeta{
message, err := env.CreateEnv(ctx, s.KubeClient, name, &types.EnvMeta{
Name: name,
Current: environment.Current,
Namespace: namespace,
@@ -39,7 +35,7 @@ func CreateEnv(c *gin.Context) {
util.AssembleResponse(c, message, err)
}
func UpdateEnv(c *gin.Context) {
func (s *APIServer) UpdateEnv(c *gin.Context) {
envName := c.Param("envName")
ctrl.Log.Info("Put a update environment request", "envName", envName)
var environmentBody apis.EnvironmentBody
@@ -48,12 +44,11 @@ func UpdateEnv(c *gin.Context) {
return
}
ctx := util.GetContext(c)
kubeClient := c.MustGet("KubeClient")
message, err := env.UpdateEnv(ctx, kubeClient.(client.Client), envName, environmentBody.Namespace)
message, err := env.UpdateEnv(ctx, s.KubeClient, envName, environmentBody.Namespace)
util.AssembleResponse(c, message, err)
}
func GetEnv(c *gin.Context) {
func (s *APIServer) GetEnv(c *gin.Context) {
envName := c.Param("envName")
ctrl.Log.Info("Get a get environment request", "envName", envName)
envList, err := env.ListEnvs(envName)
@@ -69,18 +64,18 @@ func GetEnv(c *gin.Context) {
util.AssembleResponse(c, environmentList, err)
}
func ListEnv(c *gin.Context) {
GetEnv(c)
func (s *APIServer) ListEnv(c *gin.Context) {
s.GetEnv(c)
}
func DeleteEnv(c *gin.Context) {
func (s *APIServer) DeleteEnv(c *gin.Context) {
envName := c.Param("envName")
ctrl.Log.Info("Delete a delete environment request", "envName", envName)
msg, err := env.DeleteEnv(envName)
util.AssembleResponse(c, msg, err)
}
func SetEnv(c *gin.Context) {
func (s *APIServer) SetEnv(c *gin.Context) {
envName := c.Param("envName")
ctrl.Log.Info("Patch a set environment request", "envName", envName)
msg, err := env.SetEnv(envName)
-19
View File
@@ -1,19 +0,0 @@
package handler
import "github.com/gin-gonic/gin"
// Scope related handlers
func CreateScope(c *gin.Context) {
}
func UpdateScope(c *gin.Context) {
}
func GetScope(c *gin.Context) {
}
func ListScope(c *gin.Context) {
}
func DeleteScope(c *gin.Context) {
}
-79
View File
@@ -1,79 +0,0 @@
package handler
import (
"strconv"
"github.com/gin-gonic/gin"
ctrl "sigs.k8s.io/controller-runtime"
"github.com/oam-dev/kubevela/api/types"
"github.com/oam-dev/kubevela/pkg/oam"
"github.com/oam-dev/kubevela/pkg/server/apis"
"github.com/oam-dev/kubevela/pkg/server/util"
)
// Trait related handlers
func AttachTrait(c *gin.Context) {
var body apis.TraitBody
body.EnvName = c.Param("envName")
body.AppName = c.Param("appName")
body.ComponentName = c.Param("compName")
if err := c.ShouldBindJSON(&body); err != nil {
util.HandleError(c, util.InvalidArgument, "the trait attach request body is invalid")
return
}
ctrl.Log.Info("request parameters body:", "body", body)
msg, err := oam.AttachTrait(c, body)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
}
util.AssembleResponse(c, msg, nil)
}
func GetTrait(c *gin.Context) {
var traitType = c.Param("traitName")
var workloadType string
var capability types.Capability
var err error
if capability, err = oam.GetTraitDefinition(&workloadType, traitType); err != nil {
util.HandleError(c, util.StatusInternalServerError, err)
return
}
util.AssembleResponse(c, capability, err)
}
func ListTrait(c *gin.Context) {
var traitList []types.Capability
var workloadName string
var err error
if traitList, err = oam.ListTraitDefinitions(&workloadName); err != nil {
util.HandleError(c, util.StatusInternalServerError, err)
return
}
util.AssembleResponse(c, traitList, err)
}
func DetachTrait(c *gin.Context) {
envName := c.Param("envName")
traitType := c.Param("traitName")
componentName := c.Param("compName")
applicationName := c.Param("appName")
var staging = false
var err error
if stagingStr := c.Param("staging"); stagingStr != "" {
if staging, err = strconv.ParseBool(stagingStr); err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
}
}
msg, err := oam.DetachTrait(c, envName, traitType, componentName, applicationName, staging)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
}
util.AssembleResponse(c, msg, nil)
}
+10 -4
View File
@@ -26,14 +26,20 @@ func main() {
o.Development = development
o.DestWritter = w
}))
apiServer := server.APIServer{}
kubeClient, err := oam.InitKubeClient()
c, err := oam.InitArgs()
if err != nil {
ctrl.Log.Error(err, "failed to init an Kubernetes client")
ctrl.Log.Error(err, "failed to init Kubernetes Config")
os.Exit(1)
}
apiServer, err := server.New(c, util.DefaultAPIServerPort, "")
if err != nil {
ctrl.Log.Error(err, "failed to init dashboard server")
os.Exit(1)
}
errCh := make(chan error, 1)
apiServer.Launch(kubeClient, util.DefaultAPIServerPort, "", errCh)
apiServer.Launch(errCh)
err = <-errCh
if err != nil {
ctrl.Log.Error(err, "failed to launch API server")
@@ -1,4 +1,4 @@
package handler
package server
import (
"net/http"
@@ -9,7 +9,7 @@ import (
"github.com/oam-dev/kubevela/version"
)
func GetVersion(c *gin.Context) {
func (s *APIServer) GetVersion(c *gin.Context) {
c.JSON(http.StatusOK, apis.Response{
Code: http.StatusOK,
Data: map[string]string{"version": version.VelaVersion},
+45 -50
View File
@@ -7,15 +7,13 @@ import (
"github.com/gin-contrib/static"
"github.com/gin-gonic/gin"
"sigs.k8s.io/controller-runtime/pkg/client"
"github.com/oam-dev/kubevela/pkg/server/handler"
"github.com/oam-dev/kubevela/pkg/server/util"
)
// setup the gin http server handler
func setupRoute(kubeClient client.Client, staticPath string) http.Handler {
func (s *APIServer) setupRoute(staticPath string) http.Handler {
// if deploying static Dashboard, set the mode to `release`, or to `debug`
if staticPath != "" {
gin.SetMode(gin.ReleaseMode)
@@ -46,44 +44,41 @@ func setupRoute(kubeClient client.Client, staticPath string) http.Handler {
router.Use(util.SetContext())
router.Use(gin.Recovery())
router.Use(util.ValidateHeaders())
//Store kubernetes client which could be retrieved by handlers
router.Use(util.StoreClient(kubeClient))
// all requests start with /api
api := router.Group(util.RootPath)
// env related operation
envs := api.Group(util.EnvironmentPath)
{
envs.POST("/", handler.CreateEnv)
envs.PUT("/:envName", handler.UpdateEnv)
envs.GET("/:envName", handler.GetEnv)
envs.GET("/", handler.ListEnv)
envs.POST("/", s.CreateEnv)
envs.PUT("/:envName", s.UpdateEnv)
envs.GET("/:envName", s.GetEnv)
envs.GET("/", s.ListEnv)
// Allow levaing out `/` to make API more friendly
envs.GET("", handler.ListEnv)
envs.DELETE("/:envName", handler.DeleteEnv)
envs.PATCH("/:envName", handler.SetEnv)
envs.GET("", s.ListEnv)
envs.DELETE("/:envName", s.DeleteEnv)
envs.PATCH("/:envName", s.SetEnv)
// app related operation
apps := envs.Group("/:envName/apps")
{
//apps.POST("/", handler.CreateApps)
apps.GET("/:appName", handler.GetApp)
apps.PUT("/:appName", handler.UpdateApps)
apps.GET("/", handler.ListApps)
apps.GET("", handler.ListApps)
apps.DELETE("/:appName", handler.DeleteApps)
apps.GET("/:appName", s.GetApp)
apps.PUT("/:appName", s.UpdateApps)
apps.GET("/", s.ListApps)
apps.GET("", s.ListApps)
apps.DELETE("/:appName", s.DeleteApps)
// component related operation
components := apps.Group("/:appName/components")
{
components.GET("/:compName", handler.GetComponent)
components.PUT("/:compName", handler.GetComponent)
components.GET("/", handler.GetApp)
components.GET("", handler.GetApp)
components.DELETE("/:compName", handler.DeleteComponent)
components.GET("/:compName", s.GetComponent)
components.PUT("/:compName", s.GetComponent)
components.GET("/", s.GetApp)
components.GET("", s.GetApp)
components.DELETE("/:compName", s.DeleteComponent)
traitWorkload := components.Group("/:compName/" + util.TraitDefinitionPath)
{
traitWorkload.POST("/", handler.AttachTrait)
traitWorkload.DELETE("/:traitName", handler.DetachTrait)
traitWorkload.POST("/", s.AttachTrait)
traitWorkload.DELETE("/:traitName", s.DetachTrait)
}
}
}
@@ -91,56 +86,56 @@ func setupRoute(kubeClient client.Client, staticPath string) http.Handler {
// workload related api
workload := api.Group(util.WorkloadDefinitionPath)
{
workload.POST("/", handler.CreateWorkload)
workload.GET("/:workloadName", handler.GetWorkload)
workload.PUT("/:workloadName", handler.UpdateWorkload)
workload.GET("/", handler.ListWorkload)
workload.GET("", handler.ListWorkload)
workload.POST("/", s.CreateWorkload)
workload.GET("/:workloadName", s.GetWorkload)
workload.PUT("/:workloadName", s.UpdateWorkload)
workload.GET("/", s.ListWorkload)
workload.GET("", s.ListWorkload)
}
// trait related api
trait := api.Group(util.TraitDefinitionPath)
{
trait.GET("/:traitName", handler.GetTrait)
trait.GET("/", handler.ListTrait)
trait.GET("", handler.ListTrait)
trait.GET("/:traitName", s.GetTrait)
trait.GET("/", s.ListTrait)
trait.GET("", s.ListTrait)
}
// scope related api
scopes := api.Group(util.ScopeDefinitionPath)
{
scopes.POST("/", handler.CreateScope)
scopes.GET("/:scopeName", handler.GetScope)
scopes.PUT("/:scopeName", handler.UpdateScope)
scopes.GET("/", handler.ListScope)
scopes.GET("", handler.ListScope)
scopes.DELETE("/:scopeName", handler.DeleteScope)
scopes.POST("/", s.CreateScope)
scopes.GET("/:scopeName", s.GetScope)
scopes.PUT("/:scopeName", s.UpdateScope)
scopes.GET("/", s.ListScope)
scopes.GET("", s.ListScope)
scopes.DELETE("/:scopeName", s.DeleteScope)
}
// capability center related api
capCenters := api.Group(util.CapabilityCenterPath)
{
capCenters.PUT("/", handler.AddCapabilityCenter)
capCenters.GET("/", handler.ListCapabilityCenters)
capCenters.GET("", handler.ListCapabilityCenters)
capCenters.DELETE("/:capabilityCenterName", handler.DeleteCapabilityCenter)
capCenters.PUT("/", s.AddCapabilityCenter)
capCenters.GET("/", s.ListCapabilityCenters)
capCenters.GET("", s.ListCapabilityCenters)
capCenters.DELETE("/:capabilityCenterName", s.DeleteCapabilityCenter)
caps := capCenters.Group("/:capabilityCenterName" + util.CapabilityPath)
{
caps.PUT("/", handler.SyncCapabilityCenter)
caps.PUT("/:capabilityName", handler.AddCapabilityIntoCluster)
caps.PUT("/", s.SyncCapabilityCenter)
caps.PUT("/:capabilityName", s.AddCapabilityIntoCluster)
}
}
// capability related api
caps := api.Group(util.CapabilityPath)
{
caps.DELETE("/:capabilityName", handler.RemoveCapabilityFromCluster)
caps.DELETE("/", handler.RemoveCapabilityFromCluster)
caps.GET("/", handler.ListCapabilities)
caps.GET("", handler.ListCapabilities)
caps.DELETE("/:capabilityName", s.RemoveCapabilityFromCluster)
caps.DELETE("/", s.RemoveCapabilityFromCluster)
caps.GET("/", s.ListCapabilities)
caps.GET("", s.ListCapabilities)
}
// version
api.GET(util.VersionPath, handler.GetVersion)
api.GET(util.VersionPath, s.GetVersion)
// default
router.NoRoute(util.NoRoute())
+19
View File
@@ -0,0 +1,19 @@
package server
import "github.com/gin-gonic/gin"
// Scope related handlers
func (s *APIServer) CreateScope(c *gin.Context) {
}
func (s *APIServer) UpdateScope(c *gin.Context) {
}
func (s *APIServer) GetScope(c *gin.Context) {
}
func (s *APIServer) ListScope(c *gin.Context) {
}
func (s *APIServer) DeleteScope(c *gin.Context) {
}
+138
View File
@@ -0,0 +1,138 @@
package server
import (
"os"
"strconv"
"github.com/oam-dev/kubevela/pkg/application"
util2 "github.com/oam-dev/kubevela/pkg/commands/util"
"github.com/oam-dev/kubevela/pkg/plugins"
env2 "github.com/oam-dev/kubevela/pkg/utils/env"
"github.com/spf13/pflag"
"github.com/gin-gonic/gin"
ctrl "sigs.k8s.io/controller-runtime"
"github.com/oam-dev/kubevela/api/types"
"github.com/oam-dev/kubevela/pkg/oam"
"github.com/oam-dev/kubevela/pkg/server/apis"
"github.com/oam-dev/kubevela/pkg/server/util"
)
// Trait related handlers
func (s *APIServer) AttachTrait(c *gin.Context) {
var body apis.TraitBody
body.EnvName = c.Param("envName")
body.AppName = c.Param("appName")
body.ComponentName = c.Param("compName")
if err := c.ShouldBindJSON(&body); err != nil {
util.HandleError(c, util.InvalidArgument, "the trait attach request body is invalid")
return
}
ctrl.Log.Info("request parameters body:", "body", body)
msg, err := s.DoAttachTrait(c, body)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
}
util.AssembleResponse(c, msg, nil)
}
func (s *APIServer) GetTrait(c *gin.Context) {
var traitType = c.Param("traitName")
var workloadType string
var capability types.Capability
var err error
if capability, err = oam.GetTraitDefinition(&workloadType, traitType); err != nil {
util.HandleError(c, util.StatusInternalServerError, err)
return
}
util.AssembleResponse(c, capability, err)
}
func (s *APIServer) ListTrait(c *gin.Context) {
var traitList []types.Capability
var workloadName string
var err error
if traitList, err = oam.ListTraitDefinitions(&workloadName); err != nil {
util.HandleError(c, util.StatusInternalServerError, err)
return
}
util.AssembleResponse(c, traitList, err)
}
func (s *APIServer) DetachTrait(c *gin.Context) {
envName := c.Param("envName")
traitType := c.Param("traitName")
componentName := c.Param("compName")
applicationName := c.Param("appName")
var staging = false
var err error
if stagingStr := c.Param("staging"); stagingStr != "" {
if staging, err = strconv.ParseBool(stagingStr); err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
}
}
msg, err := s.DoDetachTrait(c, envName, traitType, componentName, applicationName, staging)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
}
util.AssembleResponse(c, msg, nil)
}
func (s *APIServer) DoAttachTrait(c *gin.Context, body apis.TraitBody) (string, error) {
// Prepare
var appObj *application.Application
fs := pflag.NewFlagSet("trait", pflag.ContinueOnError)
for _, f := range body.Flags {
fs.String(f.Name, f.Value, "")
}
var staging = false
var err error
if body.Staging != "" {
staging, err = strconv.ParseBool(body.Staging)
if err != nil {
return "", err
}
}
traitAlias := body.Name
template, err := plugins.GetInstalledCapabilityWithCapAlias(types.TypeTrait, traitAlias)
if err != nil {
return "", err
}
// Run step
env, err := env2.GetEnvByName(body.EnvName)
if err != nil {
return "", err
}
appObj, err = oam.AddOrUpdateTrait(env, body.AppName, body.ComponentName, fs, template)
if err != nil {
return "", err
}
io := util2.IOStreams{In: os.Stdin, Out: os.Stdout, ErrOut: os.Stderr}
return oam.TraitOperationRun(c, s.KubeClient, env, appObj, staging, io)
}
func (s *APIServer) DoDetachTrait(c *gin.Context, envName string, traitType string, componentName string, appName string, staging bool) (string, error) {
var appObj *application.Application
var err error
if appName == "" {
appName = componentName
}
if appObj, err = oam.PrepareDetachTrait(envName, traitType, componentName, appName); err != nil {
return "", err
}
// Run
env, err := env2.GetEnvByName(envName)
if err != nil {
return "", err
}
io := util2.IOStreams{In: os.Stdin, Out: os.Stdout, ErrOut: os.Stderr}
return oam.TraitOperationRun(c, s.KubeClient, env, appObj, staging, io)
}
@@ -1,11 +1,10 @@
package handler
package server
import (
"os"
"github.com/gin-gonic/gin"
"github.com/spf13/pflag"
"sigs.k8s.io/controller-runtime/pkg/client"
"github.com/oam-dev/kubevela/api/types"
cmdutil "github.com/oam-dev/kubevela/pkg/commands/util"
@@ -17,8 +16,7 @@ import (
)
// Workload related handlers
func CreateWorkload(c *gin.Context) {
kubeClient := c.MustGet("KubeClient")
func (s *APIServer) CreateWorkload(c *gin.Context) {
var body apis.WorkloadRunBody
if err := c.ShouldBindJSON(&body); err != nil {
util.HandleError(c, util.InvalidArgument, "the workload run request body is invalid")
@@ -41,7 +39,7 @@ func CreateWorkload(c *gin.Context) {
return
}
io := cmdutil.IOStreams{In: os.Stdin, Out: os.Stdout, ErrOut: os.Stderr}
msg, err := oam.BaseRun(body.Staging, appObj, kubeClient.(client.Client), env, io)
msg, err := oam.BaseRun(body.Staging, appObj, s.KubeClient, env, io)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
@@ -52,7 +50,7 @@ func CreateWorkload(c *gin.Context) {
for _, t := range body.Traits {
t.AppName = body.AppName
t.ComponentName = body.WorkloadName
msg, err = oam.AttachTrait(c, t)
msg, err = s.DoAttachTrait(c, t)
if err != nil {
util.HandleError(c, util.StatusInternalServerError, err.Error())
return
@@ -62,10 +60,10 @@ func CreateWorkload(c *gin.Context) {
}
}
func UpdateWorkload(c *gin.Context) {
func (s *APIServer) UpdateWorkload(c *gin.Context) {
}
func GetWorkload(c *gin.Context) {
func (s *APIServer) GetWorkload(c *gin.Context) {
var workloadType = c.Param("workloadName")
var capability types.Capability
var err error
@@ -77,7 +75,7 @@ func GetWorkload(c *gin.Context) {
util.AssembleResponse(c, capability, err)
}
func ListWorkload(c *gin.Context) {
func (s *APIServer) ListWorkload(c *gin.Context) {
var workloadDefinitionList []apis.WorkloadMeta
workloads, err := plugins.LoadInstalledCapabilityWithType(types.TypeWorkload)
if err != nil {