Add pool balancing strategy

This change adds the ability to specify the pool balancing strategy to
use when processing queued jobs. Before this change, GARM would round-robin
through all pools that matched the set of tags requested by queued jobs.

When round-robin (default) is used for an entity (repo, org or enterprise)
and you have 2 pools defined for that entity with a common set of tags that
match 10 jobs (for example), then those jobs would trigger the creation of
a new runner in each of the two pools in turn. Job 1 would go to pool 1,
job 2 would go to pool 2, job 3 to pool 1, job 4 to pool 2 and so on.

When "stack" is used, those same 10 jobs would trigger the creation of a
new runner in the pool with the highest priority, every time.

In both cases, if a pool is full, the next one would be tried automatically.

For the stack case, this would mean that if pool 2 had a priority of 10 and
pool 1 would have a priority of 5, pool 2 would be saturated first, then
pool 1.

Signed-off-by: Gabriel Adrian Samfira <gsamfira@cloudbasesolutions.com>
This commit is contained in:
Gabriel Adrian Samfira 2024-03-14 20:04:34 +00:00
parent 569d512819
commit ce3c917ae5
34 changed files with 362 additions and 137 deletions

View file

@ -31,10 +31,11 @@ type InstanceRequest struct {
}
type CreateRepoParams struct {
Owner string `json:"owner"`
Name string `json:"name"`
CredentialsName string `json:"credentials_name"`
WebhookSecret string `json:"webhook_secret"`
Owner string `json:"owner"`
Name string `json:"name"`
CredentialsName string `json:"credentials_name"`
WebhookSecret string `json:"webhook_secret"`
PoolBalancerType PoolBalancerType `json:"pool_balancer_type"`
}
func (c *CreateRepoParams) Validate() error {
@ -52,13 +53,21 @@ func (c *CreateRepoParams) Validate() error {
if c.WebhookSecret == "" {
return errors.NewMissingSecretError("missing secret")
}
switch c.PoolBalancerType {
case PoolBalancerTypeRoundRobin, PoolBalancerTypeStack:
default:
return errors.NewBadRequestError("invalid pool balancer type")
}
return nil
}
type CreateOrgParams struct {
Name string `json:"name"`
CredentialsName string `json:"credentials_name"`
WebhookSecret string `json:"webhook_secret"`
Name string `json:"name"`
CredentialsName string `json:"credentials_name"`
WebhookSecret string `json:"webhook_secret"`
PoolBalancerType PoolBalancerType `json:"pool_balancer_type"`
}
func (c *CreateOrgParams) Validate() error {
@ -72,13 +81,20 @@ func (c *CreateOrgParams) Validate() error {
if c.WebhookSecret == "" {
return errors.NewMissingSecretError("missing secret")
}
switch c.PoolBalancerType {
case PoolBalancerTypeRoundRobin, PoolBalancerTypeStack:
default:
return errors.NewBadRequestError("invalid pool balancer type")
}
return nil
}
type CreateEnterpriseParams struct {
Name string `json:"name"`
CredentialsName string `json:"credentials_name"`
WebhookSecret string `json:"webhook_secret"`
Name string `json:"name"`
CredentialsName string `json:"credentials_name"`
WebhookSecret string `json:"webhook_secret"`
PoolBalancerType PoolBalancerType `json:"pool_balancer_type"`
}
func (c *CreateEnterpriseParams) Validate() error {
@ -91,6 +107,12 @@ func (c *CreateEnterpriseParams) Validate() error {
if c.WebhookSecret == "" {
return errors.NewMissingSecretError("missing secret")
}
switch c.PoolBalancerType {
case PoolBalancerTypeRoundRobin, PoolBalancerTypeStack:
default:
return errors.NewBadRequestError("invalid pool balancer type")
}
return nil
}
@ -122,6 +144,7 @@ type UpdatePoolParams struct {
// pool will be added to.
// The runner group must be created by someone with access to the enterprise.
GitHubRunnerGroup *string `json:"github-runner-group,omitempty"`
Priority *uint `json:"priority,omitempty"`
}
type CreateInstanceParams struct {
@ -159,6 +182,7 @@ type CreatePoolParams struct {
// pool will be added to.
// The runner group must be created by someone with access to the enterprise.
GitHubRunnerGroup string `json:"github-runner-group"`
Priority uint `json:"priority"`
}
func (p *CreatePoolParams) Validate() error {
@ -231,8 +255,9 @@ func (p PasswordLoginParams) Validate() error {
}
type UpdateEntityParams struct {
CredentialsName string `json:"credentials_name"`
WebhookSecret string `json:"webhook_secret"`
CredentialsName string `json:"credentials_name"`
WebhookSecret string `json:"webhook_secret"`
PoolBalancerType PoolBalancerType `json:"pool_balancer_type"`
}
type InstanceUpdateMessage struct {