6 Commits

Author SHA1 Message Date
Bo-Yi Wu
cf92a979e2 refactor(register): refactor registration functions and improve logging (#288)
- Remove the else clause in the `registerInteractive` function, and unconditionally log "Runner registered successfully."
- Change the return value in the `doRegister` function from `nil` to `ctx.Err()`.

Signed-off-by: Bo-Yi Wu <appleboy.tw@gmail.com>

Reviewed-on: https://gitea.com/gitea/act_runner/pulls/288
Co-authored-by: Bo-Yi Wu <appleboy.tw@gmail.com>
Co-committed-by: Bo-Yi Wu <appleboy.tw@gmail.com>
2023-07-12 14:12:16 +00:00
Bo-Yi Wu
87058716fb fix(register): refactor context usage in registration functions (#286)
- Add context parameter to `registerNoInteractive`, `registerInteractive`, and `doRegister` functions
- Remove the creation of a new context in `doRegister`, now using the passed context instead

Signed-off-by: Bo-Yi Wu <appleboy.tw@gmail.com>

Reviewed-on: https://gitea.com/gitea/act_runner/pulls/286
Co-authored-by: Bo-Yi Wu <appleboy.tw@gmail.com>
Co-committed-by: Bo-Yi Wu <appleboy.tw@gmail.com>
2023-07-12 13:11:55 +00:00
Lunny Xiao
c701ba4787 Add a quick start runner method in README (#282)
Reviewed-on: https://gitea.com/gitea/act_runner/pulls/282
Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
Co-committed-by: Lunny Xiao <xiaolunwen@gmail.com>
2023-07-12 01:43:26 +00:00
Michael Santos
57ff1df6e0 config: default container workspace set to host path (#279)
The container workspace path is overwritten by the default host workspace path ($HOME/.cache/act).

Workaround:
```yaml
host:
  workdir_parent: workspace
```

Ref: 34d15f21c2
Reviewed-on: https://gitea.com/gitea/act_runner/pulls/279
Co-authored-by: Michael Santos <michael.santos@gmail.com>
Co-committed-by: Michael Santos <michael.santos@gmail.com>
2023-07-10 08:57:55 +00:00
Zettat123
3dcfd6ea3d Run as cache server (#275)
This PR
- adds the `cache-server` command so act_runner can run as a cache server. When running as a cache server, act_runner only processes the requests related to cache and does not run jobs.
- adds the `external_server` configuration for cache. If specified, act_runner will use this URL as the ACTIONS_CACHE_URL instead of starting a cache server itself.

Reviewed-on: https://gitea.com/gitea/act_runner/pulls/275
Co-authored-by: Zettat123 <zettat123@gmail.com>
Co-committed-by: Zettat123 <zettat123@gmail.com>
2023-07-07 08:28:54 +00:00
Zettat123
c6006ee699 Upgrade act (#269)
Follow https://gitea.com/gitea/act/pulls/71.
Fix https://gitea.com/gitea/act_runner/issues/266

Reviewed-on: https://gitea.com/gitea/act_runner/pulls/269
Co-authored-by: Zettat123 <zettat123@gmail.com>
Co-committed-by: Zettat123 <zettat123@gmail.com>
2023-07-03 04:15:46 +00:00
9 changed files with 124 additions and 30 deletions

View File

@@ -72,6 +72,12 @@ If the registry succeed, it will run immediately. Next time, you could run the r
./act_runner daemon ./act_runner daemon
``` ```
### Run with docker
```bash
docker run -e GITEA_INSTANCE_URL=https://your_gitea.com -e GITEA_RUNNER_REGISTRATION_TOKEN=<your_token> -v /var/run/docker.sock:/var/run/docker.sock --name my_runner gitea/act_runner:nightly
```
### Configuration ### Configuration
You can also configure the runner with a configuration file. You can also configure the runner with a configuration file.

2
go.mod
View File

@@ -89,4 +89,4 @@ require (
gopkg.in/yaml.v2 v2.4.0 // indirect gopkg.in/yaml.v2 v2.4.0 // indirect
) )
replace github.com/nektos/act => gitea.com/gitea/act v0.246.1 replace github.com/nektos/act => gitea.com/gitea/act v0.246.2-0.20230703034344-3813f40cba18

4
go.sum
View File

@@ -2,8 +2,8 @@ code.gitea.io/actions-proto-go v0.3.0 h1:9Tvg8+TaaCXPKi6EnWl9vVgs2VZsj1Cs5afnsHa
code.gitea.io/actions-proto-go v0.3.0/go.mod h1:00ys5QDo1iHN1tHNvvddAcy2W/g+425hQya1cCSvq9A= code.gitea.io/actions-proto-go v0.3.0/go.mod h1:00ys5QDo1iHN1tHNvvddAcy2W/g+425hQya1cCSvq9A=
code.gitea.io/gitea-vet v0.2.3-0.20230113022436-2b1561217fa5 h1:daBEK2GQeqGikJESctP5Cu1i33z5ztAD4kyQWiw185M= code.gitea.io/gitea-vet v0.2.3-0.20230113022436-2b1561217fa5 h1:daBEK2GQeqGikJESctP5Cu1i33z5ztAD4kyQWiw185M=
code.gitea.io/gitea-vet v0.2.3-0.20230113022436-2b1561217fa5/go.mod h1:zcNbT/aJEmivCAhfmkHOlT645KNOf9W2KnkLgFjGGfE= code.gitea.io/gitea-vet v0.2.3-0.20230113022436-2b1561217fa5/go.mod h1:zcNbT/aJEmivCAhfmkHOlT645KNOf9W2KnkLgFjGGfE=
gitea.com/gitea/act v0.246.1 h1:/HGPW/VqpvlDYgnCQNp1/cIPKwEhiwpYxx4r+xrUwIk= gitea.com/gitea/act v0.246.2-0.20230703034344-3813f40cba18 h1:UN4x0o3LKZCsNLPtbk2E1e38XQKsL7XI/XaRh7ckw1g=
gitea.com/gitea/act v0.246.1/go.mod h1:oU/5klyP5O+J2psPS3t50t09+SNVg+fZ/jN4lDZAq1U= gitea.com/gitea/act v0.246.2-0.20230703034344-3813f40cba18/go.mod h1:oU/5klyP5O+J2psPS3t50t09+SNVg+fZ/jN4lDZAq1U=
github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78 h1:w+iIsaOQNcT7OZ575w+acHgRric5iCyQh+xv+KJ4HB8= github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78 h1:w+iIsaOQNcT7OZ575w+acHgRric5iCyQh+xv+KJ4HB8=
github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78/go.mod h1:LmzpDX56iTiv29bbRTIsUNlaFfuhWRQBWjQdVyAevI8= github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78/go.mod h1:LmzpDX56iTiv29bbRTIsUNlaFfuhWRQBWjQdVyAevI8=
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=

View File

@@ -0,0 +1,69 @@
// Copyright 2023 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package cmd
import (
"context"
"fmt"
"os"
"os/signal"
"gitea.com/gitea/act_runner/internal/pkg/config"
"github.com/nektos/act/pkg/artifactcache"
log "github.com/sirupsen/logrus"
"github.com/spf13/cobra"
)
type cacheServerArgs struct {
Dir string
Host string
Port uint16
}
func runCacheServer(ctx context.Context, configFile *string, cacheArgs *cacheServerArgs) func(cmd *cobra.Command, args []string) error {
return func(cmd *cobra.Command, args []string) error {
cfg, err := config.LoadDefault(*configFile)
if err != nil {
return fmt.Errorf("invalid configuration: %w", err)
}
initLogging(cfg)
var (
dir = cfg.Cache.Dir
host = cfg.Cache.Host
port = cfg.Cache.Port
)
// cacheArgs has higher priority
if cacheArgs.Dir != "" {
dir = cacheArgs.Dir
}
if cacheArgs.Host != "" {
host = cacheArgs.Host
}
if cacheArgs.Port != 0 {
port = cacheArgs.Port
}
cacheHandler, err := artifactcache.StartHandler(
dir,
host,
port,
log.StandardLogger().WithField("module", "cache_request"),
)
if err != nil {
return err
}
log.Infof("cache server is listening on %v", cacheHandler.ExternalURL())
c := make(chan os.Signal, 1)
signal.Notify(c, os.Interrupt)
<-c
return nil
}
}

View File

@@ -63,6 +63,19 @@ func Execute(ctx context.Context) {
}, },
}) })
// ./act_runner cache-server
var cacheArgs cacheServerArgs
cacheCmd := &cobra.Command{
Use: "cache-server",
Short: "Start a cache server for the cache action",
Args: cobra.MaximumNArgs(0),
RunE: runCacheServer(ctx, &configFile, &cacheArgs),
}
cacheCmd.Flags().StringVarP(&cacheArgs.Dir, "dir", "d", "", "Cache directory")
cacheCmd.Flags().StringVarP(&cacheArgs.Host, "host", "s", "", "Host of the cache server")
cacheCmd.Flags().Uint16VarP(&cacheArgs.Port, "port", "p", 0, "Port of the cache server")
rootCmd.AddCommand(cacheCmd)
// hide completion command // hide completion command
rootCmd.CompletionOptions.HiddenDefaultCmd = true rootCmd.CompletionOptions.HiddenDefaultCmd = true

View File

@@ -47,12 +47,12 @@ func runRegister(ctx context.Context, regArgs *registerArgs, configFile *string)
} }
if regArgs.NoInteractive { if regArgs.NoInteractive {
if err := registerNoInteractive(*configFile, regArgs); err != nil { if err := registerNoInteractive(ctx, *configFile, regArgs); err != nil {
return err return err
} }
} else { } else {
go func() { go func() {
if err := registerInteractive(*configFile); err != nil { if err := registerInteractive(ctx, *configFile); err != nil {
log.Fatal(err) log.Fatal(err)
return return
} }
@@ -187,7 +187,7 @@ func (r *registerInputs) assignToNext(stage registerStage, value string, cfg *co
return StageUnknown return StageUnknown
} }
func registerInteractive(configFile string) error { func registerInteractive(ctx context.Context, configFile string) error {
var ( var (
reader = bufio.NewReader(os.Stdin) reader = bufio.NewReader(os.Stdin)
stage = StageInputInstance stage = StageInputInstance
@@ -213,11 +213,10 @@ func registerInteractive(configFile string) error {
if stage == StageWaitingForRegistration { if stage == StageWaitingForRegistration {
log.Infof("Registering runner, name=%s, instance=%s, labels=%v.", inputs.RunnerName, inputs.InstanceAddr, inputs.Labels) log.Infof("Registering runner, name=%s, instance=%s, labels=%v.", inputs.RunnerName, inputs.InstanceAddr, inputs.Labels)
if err := doRegister(cfg, inputs); err != nil { if err := doRegister(ctx, cfg, inputs); err != nil {
return fmt.Errorf("Failed to register runner: %w", err) return fmt.Errorf("Failed to register runner: %w", err)
} else {
log.Infof("Runner registered successfully.")
} }
log.Infof("Runner registered successfully.")
return nil return nil
} }
@@ -250,7 +249,7 @@ func printStageHelp(stage registerStage) {
} }
} }
func registerNoInteractive(configFile string, regArgs *registerArgs) error { func registerNoInteractive(ctx context.Context, configFile string, regArgs *registerArgs) error {
cfg, err := config.LoadDefault(configFile) cfg, err := config.LoadDefault(configFile)
if err != nil { if err != nil {
return err return err
@@ -282,16 +281,14 @@ func registerNoInteractive(configFile string, regArgs *registerArgs) error {
log.WithError(err).Errorf("Invalid input, please re-run act command.") log.WithError(err).Errorf("Invalid input, please re-run act command.")
return nil return nil
} }
if err := doRegister(cfg, inputs); err != nil { if err := doRegister(ctx, cfg, inputs); err != nil {
return fmt.Errorf("Failed to register runner: %w", err) return fmt.Errorf("Failed to register runner: %w", err)
} }
log.Infof("Runner registered successfully.") log.Infof("Runner registered successfully.")
return nil return nil
} }
func doRegister(cfg *config.Config, inputs *registerInputs) error { func doRegister(ctx context.Context, cfg *config.Config, inputs *registerInputs) error {
ctx := context.Background()
// initial http client // initial http client
cli := client.New( cli := client.New(
inputs.InstanceAddr, inputs.InstanceAddr,
@@ -307,7 +304,7 @@ func doRegister(cfg *config.Config, inputs *registerInputs) error {
})) }))
select { select {
case <-ctx.Done(): case <-ctx.Done():
return nil return ctx.Err()
default: default:
} }
if ctx.Err() != nil { if ctx.Err() != nil {

View File

@@ -53,17 +53,21 @@ func NewRunner(cfg *config.Config, reg *config.Registration, cli client.Client)
envs[k] = v envs[k] = v
} }
if cfg.Cache.Enabled == nil || *cfg.Cache.Enabled { if cfg.Cache.Enabled == nil || *cfg.Cache.Enabled {
cacheHandler, err := artifactcache.StartHandler( if cfg.Cache.ExternalServer != "" {
cfg.Cache.Dir, envs["ACTIONS_CACHE_URL"] = cfg.Cache.ExternalServer
cfg.Cache.Host,
cfg.Cache.Port,
log.StandardLogger().WithField("module", "cache_request"),
)
if err != nil {
log.Errorf("cannot init cache server, it will be disabled: %v", err)
// go on
} else { } else {
envs["ACTIONS_CACHE_URL"] = cacheHandler.ExternalURL() + "/" cacheHandler, err := artifactcache.StartHandler(
cfg.Cache.Dir,
cfg.Cache.Host,
cfg.Cache.Port,
log.StandardLogger().WithField("module", "cache_request"),
)
if err != nil {
log.Errorf("cannot init cache server, it will be disabled: %v", err)
// go on
} else {
envs["ACTIONS_CACHE_URL"] = cacheHandler.ExternalURL() + "/"
}
} }
} }

View File

@@ -45,6 +45,10 @@ cache:
# The port of the cache server. # The port of the cache server.
# 0 means to use a random available port. # 0 means to use a random available port.
port: 0 port: 0
# The external cache server URL. Valid only when enable is true.
# If it's specified, act_runner will use this URL as the ACTIONS_CACHE_URL rather than start a server by itself.
# The URL should generally end with "/".
external_server: ""
container: container:
# Specifies the network to which the container will connect. # Specifies the network to which the container will connect.

View File

@@ -34,10 +34,11 @@ type Runner struct {
// Cache represents the configuration for caching. // Cache represents the configuration for caching.
type Cache struct { type Cache struct {
Enabled *bool `yaml:"enabled"` // Enabled indicates whether caching is enabled. It is a pointer to distinguish between false and not set. If not set, it will be true. Enabled *bool `yaml:"enabled"` // Enabled indicates whether caching is enabled. It is a pointer to distinguish between false and not set. If not set, it will be true.
Dir string `yaml:"dir"` // Dir specifies the directory path for caching. Dir string `yaml:"dir"` // Dir specifies the directory path for caching.
Host string `yaml:"host"` // Host specifies the caching host. Host string `yaml:"host"` // Host specifies the caching host.
Port uint16 `yaml:"port"` // Port specifies the caching port. Port uint16 `yaml:"port"` // Port specifies the caching port.
ExternalServer string `yaml:"external_server"` // ExternalServer specifies the URL of external cache server
} }
// Container represents the configuration for the container. // Container represents the configuration for the container.
@@ -119,7 +120,7 @@ func LoadDefault(file string) (*Config, error) {
} }
if cfg.Host.WorkdirParent == "" { if cfg.Host.WorkdirParent == "" {
home, _ := os.UserHomeDir() home, _ := os.UserHomeDir()
cfg.Container.WorkdirParent = filepath.Join(home, ".cache", "act") cfg.Host.WorkdirParent = filepath.Join(home, ".cache", "act")
} }
if cfg.Runner.FetchTimeout <= 0 { if cfg.Runner.FetchTimeout <= 0 {
cfg.Runner.FetchTimeout = 5 * time.Second cfg.Runner.FetchTimeout = 5 * time.Second