2022-08-14 05:29:00 +00:00
|
|
|
package runtime
|
|
|
|
|
|
|
|
import (
|
|
|
|
"context"
|
2022-09-04 07:19:07 +00:00
|
|
|
"errors"
|
2022-09-03 12:57:32 +00:00
|
|
|
"fmt"
|
2022-08-14 05:29:00 +00:00
|
|
|
|
|
|
|
"gitea.com/gitea/act_runner/client"
|
2022-08-17 06:26:58 +00:00
|
|
|
runnerv1 "gitea.com/gitea/proto-go/runner/v1"
|
2022-08-14 05:29:00 +00:00
|
|
|
|
2022-09-03 12:57:32 +00:00
|
|
|
log "github.com/sirupsen/logrus"
|
2022-08-14 05:29:00 +00:00
|
|
|
)
|
|
|
|
|
2022-09-04 07:19:07 +00:00
|
|
|
var ErrDataLock = errors.New("Data Lock Error")
|
|
|
|
|
2022-08-28 06:05:56 +00:00
|
|
|
// Defines the Resource Kind and Type.
|
|
|
|
const (
|
|
|
|
Kind = "pipeline"
|
|
|
|
Type = "docker"
|
|
|
|
)
|
|
|
|
|
2022-08-14 05:29:00 +00:00
|
|
|
// Runner runs the pipeline.
|
|
|
|
type Runner struct {
|
|
|
|
Machine string
|
|
|
|
Environ map[string]string
|
|
|
|
Client client.Client
|
|
|
|
}
|
|
|
|
|
|
|
|
// Run runs the pipeline stage.
|
2022-09-01 07:09:22 +00:00
|
|
|
func (s *Runner) Run(ctx context.Context, stage *runnerv1.Stage) error {
|
2022-09-03 12:57:32 +00:00
|
|
|
l := log.
|
|
|
|
WithField("stage.id", stage.Id).
|
|
|
|
WithField("stage.name", stage.Name)
|
2022-08-14 05:29:00 +00:00
|
|
|
|
|
|
|
l.Info("start running pipeline")
|
2022-09-01 07:09:22 +00:00
|
|
|
|
2022-09-03 12:57:32 +00:00
|
|
|
// update machine in stage
|
|
|
|
stage.Machine = s.Machine
|
|
|
|
data, err := s.Client.Detail(ctx, &runnerv1.DetailRequest{
|
|
|
|
Stage: stage,
|
|
|
|
})
|
2022-09-04 07:19:07 +00:00
|
|
|
if err != nil && err == ErrDataLock {
|
|
|
|
l.Info("stage accepted by another runner")
|
2022-09-03 12:57:32 +00:00
|
|
|
return nil
|
|
|
|
}
|
2022-09-04 07:19:07 +00:00
|
|
|
if err != nil {
|
|
|
|
l.WithError(err).Error("cannot accept stage")
|
|
|
|
return err
|
|
|
|
}
|
2022-09-03 12:57:32 +00:00
|
|
|
|
|
|
|
l = log.WithField("repo.id", data.Repo.Id).
|
|
|
|
WithField("repo.name", data.Repo.Name).
|
|
|
|
WithField("build.id", data.Build.Id).
|
|
|
|
WithField("build.name", data.Build.Name)
|
|
|
|
|
|
|
|
l.Info("stage details fetched")
|
|
|
|
|
|
|
|
return s.run(ctx, data)
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Runner) run(ctx context.Context, data *runnerv1.DetailResponse) error {
|
|
|
|
_, exist := globalTaskMap.Load(data.Build.Id)
|
|
|
|
if exist {
|
|
|
|
return fmt.Errorf("task %d already exists", data.Build.Id)
|
|
|
|
}
|
|
|
|
|
|
|
|
task := NewTask(data.Build.Id, s.Client)
|
|
|
|
|
|
|
|
// set task ve to global map
|
|
|
|
// when task is done or canceled, it will be removed from the map
|
|
|
|
globalTaskMap.Store(data.Build.Id, task)
|
|
|
|
|
|
|
|
go task.Run(ctx)
|
|
|
|
|
|
|
|
return nil
|
2022-08-14 05:29:00 +00:00
|
|
|
}
|