91 lines
		
	
	
		
			2.7 KiB
		
	
	
	
		
			Go
		
	
	
	
			
		
		
	
	
			91 lines
		
	
	
		
			2.7 KiB
		
	
	
	
		
			Go
		
	
	
	
| package actionsgithubcom
 | |
| 
 | |
| import (
 | |
| 	"fmt"
 | |
| 	"os"
 | |
| 	"strconv"
 | |
| 
 | |
| 	"sigs.k8s.io/controller-runtime/pkg/builder"
 | |
| 	"sigs.k8s.io/controller-runtime/pkg/controller"
 | |
| )
 | |
| 
 | |
| // Options is the optional configuration for the controllers, which can be
 | |
| // set via command-line flags or environment variables.
 | |
| type Options struct {
 | |
| 	// RunnerMaxConcuncurrentReconciles is the maximum number of concurrent Reconciles which can be run
 | |
| 	// by the EphemeralRunnerController.
 | |
| 	RunnerMaxConcuncurrentReconciles int
 | |
| }
 | |
| 
 | |
| // OptionsWithDefault returns the default options.
 | |
| // This is here to maintain the options and their default values in one place,
 | |
| // rather than having to correlate those in multiple places.
 | |
| func OptionsWithDefault() Options {
 | |
| 	return Options{
 | |
| 		RunnerMaxConcuncurrentReconciles: 1,
 | |
| 	}
 | |
| }
 | |
| 
 | |
| // LoadEnv loads the options from the environment variables.
 | |
| // This updates the option value only if the environment variable is set.
 | |
| // If the option is already set (via a command-line flag), the value from the environment variable takes precedence.
 | |
| func (o *Options) LoadEnv() error {
 | |
| 	v, err := o.getEnvInt("RUNNER_MAX_CONCURRENT_RECONCILES")
 | |
| 	if err != nil {
 | |
| 		return err
 | |
| 	}
 | |
| 
 | |
| 	if v != nil {
 | |
| 		o.RunnerMaxConcuncurrentReconciles = *v
 | |
| 	}
 | |
| 
 | |
| 	return nil
 | |
| }
 | |
| 
 | |
| func (o *Options) getEnvInt(name string) (*int, error) {
 | |
| 	s := os.Getenv(name)
 | |
| 	if s == "" {
 | |
| 		return nil, nil
 | |
| 	}
 | |
| 
 | |
| 	v, err := strconv.Atoi(s)
 | |
| 	if err != nil {
 | |
| 		return nil, fmt.Errorf("failed to convert %s=%s to int: %w", name, s, err)
 | |
| 	}
 | |
| 
 | |
| 	return &v, nil
 | |
| }
 | |
| 
 | |
| type Option func(*controller.Options)
 | |
| 
 | |
| // WithMaxConcurrentReconciles sets the maximum number of concurrent Reconciles which can be run.
 | |
| //
 | |
| // This is useful to improve the throughput of the controller, but it may also increase the load on the API server and
 | |
| // the external service (e.g. GitHub API). The default value is 1, as defined by the controller-runtime.
 | |
| //
 | |
| // See https://github.com/actions/actions-runner-controller/issues/3021 for more information
 | |
| // on real-world use cases and the potential impact of this option.
 | |
| func WithMaxConcurrentReconciles(n int) Option {
 | |
| 	return func(b *controller.Options) {
 | |
| 		b.MaxConcurrentReconciles = n
 | |
| 	}
 | |
| }
 | |
| 
 | |
| // builderWithOptions applies the given options to the provided builder, if any.
 | |
| // This is a helper function to avoid the need to import the controller-runtime package in every reconciler source file
 | |
| // and the command package that creates the controller.
 | |
| // This is also useful for reducing code duplication around setting controller options in
 | |
| // multiple reconcilers.
 | |
| func builderWithOptions(b *builder.Builder, opts []Option) *builder.Builder {
 | |
| 	if len(opts) == 0 {
 | |
| 		return b
 | |
| 	}
 | |
| 
 | |
| 	var controllerOpts controller.Options
 | |
| 	for _, opt := range opts {
 | |
| 		opt(&controllerOpts)
 | |
| 	}
 | |
| 
 | |
| 	return b.WithOptions(controllerOpts)
 | |
| }
 |