github.com/redhat-appstudio/release-service@v0.0.0-20240507045911-a8558ef3422a/main.go (about)

     1  /*
     2  Copyright 2022.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8      http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package main
    18  
    19  import (
    20  	"crypto/tls"
    21  	"flag"
    22  	"os"
    23  
    24  	"sigs.k8s.io/controller-runtime/pkg/metrics/server"
    25  	crwebhook "sigs.k8s.io/controller-runtime/pkg/webhook"
    26  
    27  	"github.com/konflux-ci/operator-toolkit/controller"
    28  	"github.com/konflux-ci/operator-toolkit/webhook"
    29  	"github.com/redhat-appstudio/release-service/api/v1alpha1/webhooks"
    30  
    31  	"go.uber.org/zap/zapcore"
    32  
    33  	// Import all Kubernetes client auth plugins (e.g. Azure, GCP, OIDC, etc.)
    34  	// to ensure that exec-entrypoint and run can make use of them.
    35  	_ "k8s.io/client-go/plugin/pkg/client/auth"
    36  
    37  	ecapiv1alpha1 "github.com/enterprise-contract/enterprise-contract-controller/api/v1alpha1"
    38  	applicationapiv1alpha1 "github.com/redhat-appstudio/application-api/api/v1alpha1"
    39  
    40  	"k8s.io/apimachinery/pkg/runtime"
    41  	utilruntime "k8s.io/apimachinery/pkg/util/runtime"
    42  	clientgoscheme "k8s.io/client-go/kubernetes/scheme"
    43  	ctrl "sigs.k8s.io/controller-runtime"
    44  	"sigs.k8s.io/controller-runtime/pkg/healthz"
    45  	"sigs.k8s.io/controller-runtime/pkg/log/zap"
    46  
    47  	tektonv1 "github.com/tektoncd/pipeline/pkg/apis/pipeline/v1"
    48  
    49  	appstudiov1alpha1 "github.com/redhat-appstudio/release-service/api/v1alpha1"
    50  	"github.com/redhat-appstudio/release-service/controllers"
    51  	//+kubebuilder:scaffold:imports
    52  )
    53  
    54  var (
    55  	scheme   = runtime.NewScheme()
    56  	setupLog = ctrl.Log.WithName("setup")
    57  )
    58  
    59  func init() {
    60  	utilruntime.Must(clientgoscheme.AddToScheme(scheme))
    61  	utilruntime.Must(appstudiov1alpha1.AddToScheme(scheme))
    62  	utilruntime.Must(applicationapiv1alpha1.AddToScheme(scheme))
    63  	utilruntime.Must(ecapiv1alpha1.AddToScheme(scheme))
    64  	utilruntime.Must(tektonv1.AddToScheme(scheme))
    65  
    66  	//+kubebuilder:scaffold:scheme
    67  }
    68  
    69  func main() {
    70  	var metricsAddr string
    71  	var enableHttp2 bool
    72  	var enableLeaderElection bool
    73  	var probeAddr string
    74  	flag.StringVar(&metricsAddr, "metrics-bind-address", ":8080", "The address the metric endpoint binds to.")
    75  	flag.StringVar(&probeAddr, "health-probe-bind-address", ":8081", "The address the probe endpoint binds to.")
    76  	flag.BoolVar(&enableHttp2, "enable-http2", false, "Enable HTTP/2 for the metrics and webhook servers.")
    77  	flag.BoolVar(&enableLeaderElection, "leader-elect", false,
    78  		"Enable leader election for controller manager. "+
    79  			"Enabling this will ensure there is only one active controller manager.")
    80  	opts := zap.Options{
    81  		Development: true,
    82  		TimeEncoder: zapcore.ISO8601TimeEncoder,
    83  	}
    84  	opts.BindFlags(flag.CommandLine)
    85  	flag.Parse()
    86  
    87  	ctrl.SetLogger(zap.New(zap.UseFlagOptions(&opts)))
    88  
    89  	mgr, err := ctrl.NewManager(ctrl.GetConfigOrDie(), ctrl.Options{
    90  		HealthProbeBindAddress: probeAddr,
    91  		LeaderElection:         enableLeaderElection,
    92  		LeaderElectionID:       "f3d4c01a.redhat.com",
    93  		Metrics: server.Options{
    94  			BindAddress: metricsAddr,
    95  		},
    96  		WebhookServer: crwebhook.NewServer(crwebhook.Options{
    97  			Port: 9443,
    98  			TLSOpts: []func(*tls.Config){
    99  				func(c *tls.Config) {
   100  					if !enableHttp2 {
   101  						c.NextProtos = []string{"http/1.1"}
   102  					}
   103  				},
   104  			},
   105  		}),
   106  		Scheme: scheme,
   107  	})
   108  	if err != nil {
   109  		setupLog.Error(err, "unable to start manager")
   110  		os.Exit(1)
   111  	}
   112  
   113  	// Set a default value for the DEFAULT_RELEASE_PVC environment variable
   114  	if os.Getenv("DEFAULT_RELEASE_PVC") == "" {
   115  		err := os.Setenv("DEFAULT_RELEASE_PVC", "release-pvc")
   116  		if err != nil {
   117  			setupLog.Error(err, "unable to setup DEFAULT_RELEASE_PVC environment variable")
   118  			os.Exit(1)
   119  		}
   120  	}
   121  
   122  	// Set a default value for the DEFAULT_RELEASE_WORKSPACE_NAME environment variable
   123  	if os.Getenv("DEFAULT_RELEASE_WORKSPACE_NAME") == "" {
   124  		err := os.Setenv("DEFAULT_RELEASE_WORKSPACE_NAME", "release-workspace")
   125  		if err != nil {
   126  			setupLog.Error(err, "unable to setup DEFAULT_RELEASE_WORKSPACE_NAME environment variable")
   127  			os.Exit(1)
   128  		}
   129  	}
   130  
   131  	// Set a default value for the DEFAULT_RELEASE_WORKSPACE_SIZE environment variable
   132  	if os.Getenv("DEFAULT_RELEASE_WORKSPACE_SIZE") == "" {
   133  		err := os.Setenv("DEFAULT_RELEASE_WORKSPACE_SIZE", "1Gi")
   134  		if err != nil {
   135  			setupLog.Error(err, "unable to setup DEFAULT_RELEASE_WORKSPACE_SIZE environment variable")
   136  			os.Exit(1)
   137  		}
   138  	}
   139  
   140  	setUpControllers(mgr)
   141  	setUpWebhooks(mgr)
   142  
   143  	err = os.Setenv("ENTERPRISE_CONTRACT_CONFIG_MAP", "enterprise-contract-service/ec-defaults")
   144  	if err != nil {
   145  		setupLog.Error(err, "unable to setup ENTERPRISE_CONTRACT_CONFIG_MAP environment variable")
   146  		os.Exit(1)
   147  	}
   148  
   149  	//+kubebuilder:scaffold:builder
   150  
   151  	if err := mgr.AddHealthzCheck("healthz", healthz.Ping); err != nil {
   152  		setupLog.Error(err, "unable to set up health check")
   153  		os.Exit(1)
   154  	}
   155  	if err := mgr.AddReadyzCheck("readyz", healthz.Ping); err != nil {
   156  		setupLog.Error(err, "unable to set up ready check")
   157  		os.Exit(1)
   158  	}
   159  
   160  	setupLog.Info("starting manager")
   161  	if err := mgr.Start(ctrl.SetupSignalHandler()); err != nil {
   162  		setupLog.Error(err, "problem running manager")
   163  		os.Exit(1)
   164  	}
   165  }
   166  
   167  // setUpControllers sets up controllers.
   168  func setUpControllers(mgr ctrl.Manager) {
   169  	err := controller.SetupControllers(mgr, nil, controllers.EnabledControllers...)
   170  	if err != nil {
   171  		setupLog.Error(err, "unable to setup controllers")
   172  		os.Exit(1)
   173  	}
   174  }
   175  
   176  // setUpWebhooks sets up webhooks.
   177  func setUpWebhooks(mgr ctrl.Manager) {
   178  	if os.Getenv("ENABLE_WEBHOOKS") == "false" {
   179  		return
   180  	}
   181  
   182  	err := webhook.SetupWebhooks(mgr, webhooks.EnabledWebhooks...)
   183  	if err != nil {
   184  		setupLog.Error(err, "unable to setup webhooks")
   185  		os.Exit(1)
   186  	}
   187  }