You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by as...@apache.org on 2021/12/07 13:23:50 UTC

[camel-k] 01/04: chore: Parallel Kamelets install

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

astefanutti pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel-k.git

commit 03bb989d9ad9753f3b2354e0d35d418e853d1cdd
Author: Antonin Stefanutti <an...@stefanutti.fr>
AuthorDate: Mon Dec 6 15:09:04 2021 +0100

    chore: Parallel Kamelets install
---
 go.mod                  |   1 +
 pkg/install/kamelets.go | 106 ++++++++++++++++++++++++++++--------------------
 2 files changed, 63 insertions(+), 44 deletions(-)

diff --git a/go.mod b/go.mod
index 34497e8..e11b03b 100644
--- a/go.mod
+++ b/go.mod
@@ -43,6 +43,7 @@ require (
 	go.uber.org/multierr v1.6.0
 	go.uber.org/zap v1.19.1
 	golang.org/x/oauth2 v0.0.0-20211104180415-d3ed0bb246c8
+	golang.org/x/sync v0.0.0-20210220032951-036812b2e83c
 	gopkg.in/inf.v0 v0.9.1
 	gopkg.in/yaml.v2 v2.4.0
 	k8s.io/api v0.21.4
diff --git a/pkg/install/kamelets.go b/pkg/install/kamelets.go
index 91bebee..b2ad752 100644
--- a/pkg/install/kamelets.go
+++ b/pkg/install/kamelets.go
@@ -1,12 +1,12 @@
 /*
 Licensed to the Apache Software Foundation (ASF) under one or more
-contributor license agreements.  See the NOTICE file distributed with
+contributor license agreements. See the NOTICE file distributed with
 this work for additional information regarding copyright ownership.
 The ASF licenses this file to You under the Apache License, Version 2.0
 (the "License"); you may not use this file except in compliance with
-the License.  You may obtain a copy of the License at
+the License. You may obtain a copy of the License at
 
-   http://www.apache.org/licenses/LICENSE-2.0
+http://www.apache.org/licenses/LICENSE-2.0
 
 Unless required by applicable law or agreed to in writing, software
 distributed under the License is distributed on an "AS IS" BASIS,
@@ -20,19 +20,22 @@ package install
 import (
 	"context"
 	"fmt"
-	"io/ioutil"
+	"io/fs"
 	"os"
 	"path"
+	"path/filepath"
 	"strings"
 
-	"github.com/apache/camel-k/pkg/util"
+	"golang.org/x/sync/errgroup"
 
-	"github.com/pkg/errors"
 	k8serrors "k8s.io/apimachinery/pkg/api/errors"
 	"k8s.io/apimachinery/pkg/types"
 
+	"github.com/pkg/errors"
+
 	"github.com/apache/camel-k/pkg/apis/camel/v1alpha1"
 	"github.com/apache/camel-k/pkg/client"
+	"github.com/apache/camel-k/pkg/util"
 	"github.com/apache/camel-k/pkg/util/defaults"
 	"github.com/apache/camel-k/pkg/util/kubernetes"
 )
@@ -42,7 +45,7 @@ const (
 	defaultKameletDir = "/kamelets/"
 )
 
-// KameletCatalog installs the bundled KameletCatalog into one namespace.
+// KameletCatalog installs the bundled Kamelets into the specified namespace.
 func KameletCatalog(ctx context.Context, c client.Client, namespace string) error {
 	kameletDir := os.Getenv(kameletDirEnv)
 	if kameletDir == "" {
@@ -58,57 +61,72 @@ func KameletCatalog(ctx context.Context, c client.Client, namespace string) erro
 		return fmt.Errorf("kamelet directory %q is a file", kameletDir)
 	}
 
-	files, err := ioutil.ReadDir(kameletDir)
+	g, gCtx := errgroup.WithContext(ctx)
+
+	err = filepath.WalkDir(kameletDir, func(p string, f fs.DirEntry, err error) error {
+		if err != nil {
+			return err
+		}
+		if f.IsDir() && f.Name() != d.Name() {
+			return fs.SkipDir
+		}
+		if !(strings.HasSuffix(f.Name(), ".yaml") || strings.HasSuffix(f.Name(), ".yml")) {
+			return nil
+		}
+		// We may want to throttle the creation of Go routines if the number of bundled Kamelets increases.
+		g.Go(func() error {
+			return createOrReplaceKamelet(gCtx, c, path.Join(kameletDir, f.Name()), namespace)
+		})
+		return nil
+	})
 	if err != nil {
 		return err
 	}
 
-	for _, file := range files {
-		if file.IsDir() || !(strings.HasSuffix(file.Name(), ".yaml") || strings.HasSuffix(file.Name(), ".yml")) {
-			continue
-		}
+	return g.Wait()
+}
 
-		content, err := util.ReadFile(path.Join(kameletDir, file.Name()))
-		if err != nil {
-			return err
-		}
+func createOrReplaceKamelet(ctx context.Context, c client.Client, path string, namespace string) error {
+	fmt.Printf("Install file: %s in %s", path, namespace)
+
+	content, err := util.ReadFile(path)
+	if err != nil {
+		return err
+	}
 
-		obj, err := kubernetes.LoadResourceFromYaml(c.GetScheme(), string(content))
+	obj, err := kubernetes.LoadResourceFromYaml(c.GetScheme(), string(content))
+	if err != nil {
+		return err
+	}
+	if k, ok := obj.(*v1alpha1.Kamelet); ok {
+		existing := &v1alpha1.Kamelet{}
+		err = c.Get(ctx, types.NamespacedName{Namespace: namespace, Name: k.Name}, existing)
 		if err != nil {
-			return err
+			if k8serrors.IsNotFound(err) {
+				existing = nil
+			} else {
+				return err
+			}
 		}
-		if k, ok := obj.(*v1alpha1.Kamelet); ok {
-			existing := &v1alpha1.Kamelet{}
-			err = c.Get(ctx, types.NamespacedName{Namespace: namespace, Name: k.Name}, existing)
-			if err != nil {
-				if k8serrors.IsNotFound(err) {
-					existing = nil
-				} else {
-					return err
-				}
+
+		if existing == nil || existing.Labels[v1alpha1.KameletBundledLabel] == "true" {
+			if k.GetAnnotations() == nil {
+				k.SetAnnotations(make(map[string]string))
 			}
+			k.GetAnnotations()[kamelVersionAnnotation] = defaults.Version
 
-			if existing == nil || existing.Labels[v1alpha1.KameletBundledLabel] == "true" {
-				if k.GetAnnotations() == nil {
-					k.SetAnnotations(make(map[string]string))
-				}
-				k.GetAnnotations()[kamelVersionAnnotation] = defaults.Version
-
-				if k.GetLabels() == nil {
-					k.SetLabels(make(map[string]string))
-				}
-				k.GetLabels()[v1alpha1.KameletBundledLabel] = "true"
-				k.GetLabels()[v1alpha1.KameletReadOnlyLabel] = "true"
-
-				err := ObjectOrCollect(ctx, c, namespace, nil, true, k)
-				if err != nil {
-					return errors.Wrapf(err, "could not create resource from file %q", path.Join(kameletDir, file.Name()))
-				}
+			if k.GetLabels() == nil {
+				k.SetLabels(make(map[string]string))
 			}
+			k.GetLabels()[v1alpha1.KameletBundledLabel] = "true"
+			k.GetLabels()[v1alpha1.KameletReadOnlyLabel] = "true"
 
+			err := ObjectOrCollect(ctx, c, namespace, nil, true, k)
+			if err != nil {
+				return errors.Wrapf(err, "could not create resource from file %q", path)
+			}
 		}
 	}
-
 	return nil
 }