From 6995e13259e826f7760e9e606252ff0a66d892f1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Andr=C3=A9=20Sterba?= Date: Mon, 20 Jun 2022 17:15:07 +0200 Subject: [PATCH] Add mode to run for a single service in repo root --- README.md | 25 ++++ cmd/main.go | 109 ++++++++++++------ internal/config/config.go | 5 +- internal/config/config_test.go | 19 ++- .../config/testdata/.upstream-watch-1.yaml | 3 + ...ream-watch.yaml => .upstream-watch-2.yaml} | 1 + 6 files changed, 123 insertions(+), 39 deletions(-) create mode 100644 internal/config/testdata/.upstream-watch-1.yaml rename internal/config/testdata/{.upstream-watch.yaml => .upstream-watch-2.yaml} (66%) diff --git a/README.md b/README.md index 885847c..2badb2e 100644 --- a/README.md +++ b/README.md @@ -5,6 +5,30 @@ It only supports `git`. I wrote this tool to support my personal container infrastructure, which is completely managed via a single git repository. +There are two different modes: + +- single directory +- Subdiretorie per service + +## Single directory + +The target repository could look like this: + +```sh + . + ├── .upstream-watch.yaml + ├── README.md + ├── .update-hooks.yaml + ├── docker-compose.yml + └── upstream-watch +``` + +All configuration files are in a single directory, which must be the root of the git directory. +Use this mode by setting `single_directory_mode: true`. +The rest of the needed configuration is identical to the subdirectory documentation. + +## Use subdirectories for different services + The target repository could look like this: ```sh @@ -26,6 +50,7 @@ The `config.yaml` is the main configuration file for this instance of `upstream- You can set the retry interval (in seconds) and folders that should be ignored. ```sh + single_directory_mode: false retry_intervall: 10 ignore_folders: [".git", ".test"] ``` diff --git a/cmd/main.go b/cmd/main.go index 92be6b2..f9e0860 100644 --- a/cmd/main.go +++ b/cmd/main.go @@ -10,50 +10,91 @@ import ( "github.com/andresterba/upstream-watch/internal/updater" ) -func main() { - for { - loadedConfig, err := config.GetConfig(".upstream-watch.yaml") +func pullUpstreamRepository() { + runCommand := exec.Command("git", "pull") + output, err := runCommand.CombinedOutput() + if err != nil { + log.Fatalf("Failed to pull upstream repository\n%s\n", output) + } + + log.Print("Successfully pulled upstream repository") +} + +func updateSubdirectories(loadedConfig *config.Config, db updater.Database) { + pullUpstreamRepository() + + ds := files.NewDirectoryScanner(loadedConfig.IgnoreFolders) + directories, err := ds.ListDirectories() + if err != nil { + log.Fatalf("failed to list directories\n%s\n", err) + } + + for _, subdirectory := range directories { + updateConfig, err := config.GetUpdateConfig(subdirectory + "/.update-hooks.yaml") if err != nil { - log.Fatal(err) + log.Printf("Failed to update submodule %s: %+v", subdirectory, err) } - runCommand := exec.Command("git", "pull") - output, err := runCommand.CombinedOutput() + updater := updater.NewUpdater( + subdirectory, + updateConfig.PreUpdateCommands, + updateConfig.PostUpdateCommands, + db, + ) + err = updater.Update() if err != nil { - log.Fatalf("Failed to pull upstream repository\n%s\n", output) + log.Printf("Failed to update submodule %s: %+v", subdirectory, err) + continue } - log.Print("Successfully pulled upstream repository") + log.Printf("Successfully updated submodule %s", subdirectory) + } + + <-time.After(loadedConfig.RetryIntervall * time.Second) +} + +func updateRootRepository(loadedConfig *config.Config, db updater.Database) { + pullUpstreamRepository() - ds := files.NewDirectoryScanner(loadedConfig.IgnoreFolders) - directories, err := ds.ListDirectories() + subdirectory := "." + updateConfig, err := config.GetUpdateConfig(subdirectory + "/.update-hooks.yaml") + if err != nil { + log.Printf("Failed to update root: %+v", err) + } + + updater := updater.NewUpdater( + subdirectory, + updateConfig.PreUpdateCommands, + updateConfig.PostUpdateCommands, + db, + ) + err = updater.Update() + if err != nil { + log.Printf("Failed to update root: %+v", err) + } else { + log.Printf("Successfully updated root") + } + + <-time.After(loadedConfig.RetryIntervall * time.Second) +} + +func main() { + for { + loadedConfig, err := config.GetConfig(".upstream-watch.yaml") if err != nil { - log.Fatalf("failed to list directories\n%s\n", output) + log.Fatal(err) } - db := updater.NewDatabase() - - for _, subdirectory := range directories { - updateConfig, err := config.GetUpdateConfig(subdirectory + "/.update-hooks.yaml") - if err != nil { - log.Printf("Failed to update submodule %s: %+v", subdirectory, err) - } - - updater := updater.NewUpdater( - subdirectory, - updateConfig.PreUpdateCommands, - updateConfig.PostUpdateCommands, - db, - ) - err = updater.Update() - if err != nil { - log.Printf("Failed to update submodule %s: %+v", subdirectory, err) - continue - } - - log.Printf("Successfully updated submodule %s", subdirectory) - } + updateDb := updater.NewDatabase() - <-time.After(loadedConfig.RetryIntervall * time.Second) + rootDirectoryeMode := loadedConfig.SingleDirectoryMode + + switch rootDirectoryeMode { + case true: + updateRootRepository(loadedConfig, updateDb) + + case false: + updateSubdirectories(loadedConfig, updateDb) + } } } diff --git a/internal/config/config.go b/internal/config/config.go index ba9fbba..a5bba2b 100644 --- a/internal/config/config.go +++ b/internal/config/config.go @@ -9,8 +9,9 @@ import ( ) type Config struct { - RetryIntervall time.Duration `yaml:"retry_intervall,omitempty"` - IgnoreFolders []string `yaml:"ignore_folders,omitempty"` + SingleDirectoryMode bool `yaml:"single_directory_mode,omitempty"` + RetryIntervall time.Duration `yaml:"retry_intervall,omitempty"` + IgnoreFolders []string `yaml:"ignore_folders,omitempty"` } func GetConfig(path string) (*Config, error) { diff --git a/internal/config/config_test.go b/internal/config/config_test.go index 140e3f2..9ff4186 100644 --- a/internal/config/config_test.go +++ b/internal/config/config_test.go @@ -18,11 +18,12 @@ func TestGetConfig(t *testing.T) { { name: "should parse config", args: args{ - path: "testdata/.upstream-watch.yaml", + path: "testdata/.upstream-watch-1.yaml", }, want: &Config{ - RetryIntervall: 1337, - IgnoreFolders: []string{".git", ".test"}, + SingleDirectoryMode: false, + RetryIntervall: 1337, + IgnoreFolders: []string{".git", ".test"}, }, wantErr: false, }, @@ -34,6 +35,18 @@ func TestGetConfig(t *testing.T) { want: nil, wantErr: true, }, + { + name: "should parse config", + args: args{ + path: "testdata/.upstream-watch-2.yaml", + }, + want: &Config{ + SingleDirectoryMode: true, + RetryIntervall: 1337, + IgnoreFolders: []string{".git", ".test"}, + }, + wantErr: false, + }, } for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { diff --git a/internal/config/testdata/.upstream-watch-1.yaml b/internal/config/testdata/.upstream-watch-1.yaml new file mode 100644 index 0000000..aaa9b3d --- /dev/null +++ b/internal/config/testdata/.upstream-watch-1.yaml @@ -0,0 +1,3 @@ +single_directory_mode: false +retry_intervall: 1337 +ignore_folders: [".git", ".test"] diff --git a/internal/config/testdata/.upstream-watch.yaml b/internal/config/testdata/.upstream-watch-2.yaml similarity index 66% rename from internal/config/testdata/.upstream-watch.yaml rename to internal/config/testdata/.upstream-watch-2.yaml index 8619fbc..8917b9b 100644 --- a/internal/config/testdata/.upstream-watch.yaml +++ b/internal/config/testdata/.upstream-watch-2.yaml @@ -1,2 +1,3 @@ +single_directory_mode: true retry_intervall: 1337 ignore_folders: [".git", ".test"]