From 442c3f368e8592767fa6c713ce745167f40b8ada Mon Sep 17 00:00:00 2001 From: axtloss Date: Fri, 15 Nov 2024 12:59:19 +0100 Subject: [PATCH] feat: Make it easier to configure local includes --- api/download.go | 55 ++++++++++++++++++++++++++++++++---- api/structs.go | 1 + core/build.go | 8 +----- core/loader.go | 8 ++++-- core/shell.go | 2 +- plugins/cmake.go | 2 +- plugins/dpkg-buildpackage.go | 2 +- plugins/go.go | 2 +- plugins/make.go | 2 +- plugins/meson.go | 2 +- 10 files changed, 62 insertions(+), 22 deletions(-) diff --git a/api/download.go b/api/download.go index 89edb23..2b4aef0 100644 --- a/api/download.go +++ b/api/download.go @@ -34,35 +34,40 @@ func GetSourcePath(source Source, moduleName string) string { file := strings.Split(url[len(url)-1], "?")[0] fileParts := strings.Split(file, ".") return filepath.Join(moduleName, strings.Join(fileParts[:len(fileParts)-1], ".")) + case "local": + toplevelDir := strings.Split(source.URL, "/") + return filepath.Join(moduleName, toplevelDir[len(toplevelDir)-1]) } return "" } // Download the source based on its type and validate its checksum -func DownloadSource(downloadPath string, source Source, moduleName string) error { +func DownloadSource(recipe *Recipe, source Source, moduleName string) error { fmt.Printf("Downloading source: %s\n", source.URL) switch source.Type { case "git": - return DownloadGitSource(downloadPath, source, moduleName) + return DownloadGitSource(recipe.DownloadsPath, source, moduleName) case "tar": - err := DownloadTarSource(downloadPath, source, moduleName) + err := DownloadTarSource(recipe.DownloadsPath, source, moduleName) if err != nil { return err } - return checksumValidation(source, filepath.Join(downloadPath, GetSourcePath(source, moduleName), moduleName+".tar")) + return checksumValidation(source, filepath.Join(recipe.DownloadsPath, GetSourcePath(source, moduleName), moduleName+".tar")) case "file": - err := DownloadFileSource(downloadPath, source, moduleName) + err := DownloadFileSource(recipe.DownloadsPath, source, moduleName) if err != nil { return err } extension := filepath.Ext(source.URL) filename := fmt.Sprintf("%s%s", moduleName, extension) - destinationPath := filepath.Join(downloadPath, GetSourcePath(source, moduleName), filename) + destinationPath := filepath.Join(recipe.DownloadsPath, GetSourcePath(source, moduleName), filename) return checksumValidation(source, destinationPath) + case "local": + return DownloadLocalSource(recipe.SourcesPath, source, moduleName) default: return fmt.Errorf("unsupported source type %s", source.Type) } @@ -175,6 +180,42 @@ func DownloadTarSource(downloadPath string, source Source, moduleName string) er return nil } +// Copies a local source for use during the build, skips the Download directory and copies directly into the source path +func DownloadLocalSource(sourcesPath string, source Source, moduleName string) error { + fmt.Printf("Source is local: %s\n", source.URL) + dest := filepath.Join(sourcesPath, GetSourcePath(source, moduleName)) + os.MkdirAll(dest, 0o777) + fileInfo, err := os.Stat(source.URL) + if err != nil { + return err + } + if fileInfo.IsDir() { + fmt.Println("ROOTDIR:: ", source.URL) + root := os.DirFS(source.URL) + return os.CopyFS(dest, root) + } else { + fileName := strings.Split(source.URL, "/") + out, err := os.Create(filepath.Join(dest, fileName[len(fileName)-1])) + if err != nil { + return err + } + defer out.Close() + + in, err := os.Open(source.URL) + if err != nil { + return err + } + defer in.Close() + + _, err = io.Copy(out, in) + if err != nil { + return err + } + return nil + } + +} + // Move downloaded sources from the download path to the sources path func MoveSources(downloadPath string, sourcesPath string, sources []Source, moduleName string) error { fmt.Println("Moving sources for " + moduleName) @@ -224,6 +265,8 @@ func MoveSource(downloadPath string, sourcesPath string, source Source, moduleNa } return os.Remove(filepath.Join(downloadPath, GetSourcePath(source, moduleName), moduleName+".tar")) + case "local": + return nil default: return fmt.Errorf("unsupported source type %s", source.Type) } diff --git a/api/structs.go b/api/structs.go index 425aa3d..126e161 100644 --- a/api/structs.go +++ b/api/structs.go @@ -21,6 +21,7 @@ type Recipe struct { ParentPath string DownloadsPath string SourcesPath string + IncludesPath string PluginPath string Containerfile string Finalize []interface{} diff --git a/core/build.go b/core/build.go index 68cb0b2..9ef577d 100644 --- a/core/build.go +++ b/core/build.go @@ -230,17 +230,11 @@ func BuildContainerfile(recipe *api.Recipe) error { } // INCLUDES.CONTAINER - _, err = containerfile.WriteString("ADD includes.container /\n") + _, err = containerfile.WriteString(fmt.Sprintf("ADD %s /\n", recipe.IncludesPath)) if err != nil { return err } - // SOURCES - /*_, err = containerfile.WriteString("ADD sources /sources\n") - if err != nil { - return err - }*/ - for _, cmd := range cmds { err = ChangeWorkingDirectory(cmd.Workdir, containerfile) if err != nil { diff --git a/core/loader.go b/core/loader.go index dc6b360..d9e5528 100644 --- a/core/loader.go +++ b/core/loader.go @@ -97,10 +97,12 @@ func LoadRecipe(path string) (*api.Recipe, error) { // directory. For example, if you want to include a file in // /etc/nginx/nginx.conf you must place it in includes/etc/nginx/nginx.conf // so it will be copied to the correct location in the container - includesContainerPath := filepath.Join(filepath.Dir(recipePath), "includes.container") - _, err = os.Stat(includesContainerPath) + if len(strings.TrimSpace(recipe.IncludesPath)) == 0 { + recipe.IncludesPath = filepath.Join("includes.container") + } + _, err = os.Stat(recipe.IncludesPath) if os.IsNotExist(err) { - err := os.MkdirAll(includesContainerPath, 0755) + err := os.MkdirAll(recipe.IncludesPath, 0755) if err != nil { return nil, err } diff --git a/core/shell.go b/core/shell.go index ed66566..bf6580d 100644 --- a/core/shell.go +++ b/core/shell.go @@ -28,7 +28,7 @@ func BuildShellModule(moduleInterface interface{}, recipe *api.Recipe) (string, for _, source := range module.Sources { if strings.TrimSpace(source.Type) != "" { - err := api.DownloadSource(recipe.DownloadsPath, source, module.Name) + err := api.DownloadSource(recipe, source, module.Name) if err != nil { return "", err } diff --git a/plugins/cmake.go b/plugins/cmake.go index 677a85b..2e6b9d7 100644 --- a/plugins/cmake.go +++ b/plugins/cmake.go @@ -48,7 +48,7 @@ func BuildModule(moduleInterface *C.char, recipeInterface *C.char) *C.char { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } - err = api.DownloadSource(recipe.DownloadsPath, module.Source, module.Name) + err = api.DownloadSource(recipe, module.Source, module.Name) if err != nil { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } diff --git a/plugins/dpkg-buildpackage.go b/plugins/dpkg-buildpackage.go index 035d604..a7fd8b6 100644 --- a/plugins/dpkg-buildpackage.go +++ b/plugins/dpkg-buildpackage.go @@ -46,7 +46,7 @@ func BuildModule(moduleInterface *C.char, recipeInterface *C.char) *C.char { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } - err = api.DownloadSource(recipe.DownloadsPath, module.Source, module.Name) + err = api.DownloadSource(recipe, module.Source, module.Name) if err != nil { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } diff --git a/plugins/go.go b/plugins/go.go index 9bfa791..ac77c66 100644 --- a/plugins/go.go +++ b/plugins/go.go @@ -48,7 +48,7 @@ func BuildModule(moduleInterface *C.char, recipeInterface *C.char) *C.char { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } - err = api.DownloadSource(recipe.DownloadsPath, module.Source, module.Name) + err = api.DownloadSource(recipe, module.Source, module.Name) if err != nil { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } diff --git a/plugins/make.go b/plugins/make.go index bf441d2..ac926fb 100644 --- a/plugins/make.go +++ b/plugins/make.go @@ -50,7 +50,7 @@ func BuildModule(moduleInterface *C.char, recipeInterface *C.char) *C.char { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } - err = api.DownloadSource(recipe.DownloadsPath, module.Source, module.Name) + err = api.DownloadSource(recipe, module.Source, module.Name) if err != nil { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } diff --git a/plugins/meson.go b/plugins/meson.go index 920d77e..617cfde 100644 --- a/plugins/meson.go +++ b/plugins/meson.go @@ -47,7 +47,7 @@ func BuildModule(moduleInterface *C.char, recipeInterface *C.char) *C.char { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) } - err = api.DownloadSource(recipe.DownloadsPath, module.Source, module.Name) + err = api.DownloadSource(recipe, module.Source, module.Name) if err != nil { return C.CString(fmt.Sprintf("ERROR: %s", err.Error())) }