Skip to content

Commit

Permalink
feat: Move resolver to api/download
Browse files Browse the repository at this point in the history
Makes the resolve functions available in the api to let modules download
their sources themselves
  • Loading branch information
axtloss committed Nov 28, 2023
1 parent f98a719 commit 6eea1f6
Show file tree
Hide file tree
Showing 17 changed files with 201 additions and 133 deletions.
75 changes: 17 additions & 58 deletions core/resolver.go → api/download.go
Original file line number Diff line number Diff line change
@@ -1,9 +1,8 @@
package core
package api

import (
"crypto/sha256"
"fmt"
"github.com/vanilla-os/vib/api"
"io"
"net/http"
"os"
Expand All @@ -12,70 +11,30 @@ import (
"strings"
)

// ResolveSources resolves the sources of a recipe and downloads them
// to the downloads directory. Note that modules in this function are
// returned in the order they should be built.
func ResolveSources(recipe *Recipe) ([]Module, []api.Source, error) {
fmt.Println("Resolving sources")

modules := GetAllModules(recipe.Modules)
//var sources []Source

for _, module := range modules {
fmt.Printf("Resolving source for: %s\n", module.Name)

if module.Source.URL == "" {
continue
}

module.Source.Module = module.Name
err := DownloadSource(recipe, module.Source)
if err != nil {
return nil, nil, err
}

sources = append(sources, module.Source)
}

return modules, sources, nil
}

// GetAllModules returns a list of all modules in an ordered list
func GetAllModules(modules []Module) []Module {
var orderedList []Module

for _, module := range modules {
orderedList = append(orderedList, GetAllModules(module.Modules)...)
orderedList = append(orderedList, module)
}

return orderedList
}

// DownloadSource downloads a source to the downloads directory
// according to its type (git, tar, ...)
func DownloadSource(recipe *Recipe, source Source) error {
func DownloadSource(downloadPath string, source Source) error {
fmt.Printf("Downloading source: %s\n", source.URL)

if source.Type == "git" {
return DownloadGitSource(recipe, source)
return DownloadGitSource(downloadPath, source)
} else if source.Type == "tar" {
err := DownloadTarSource(recipe, source)
err := DownloadTarSource(downloadPath, source)
if err != nil {
return err
}
return checksumValidation(source, filepath.Join(recipe.DownloadsPath, source.Module))
return checksumValidation(source, filepath.Join(downloadPath, source.Module))
} else {
return fmt.Errorf("unsupported source type %s", source.Type)
}
}

// DownloadGitSource downloads a git source to the downloads directory
// and checks out the commit or tag
func DownloadGitSource(recipe *Recipe, source Source) error {
func DownloadGitSource(downloadPath string, source Source) error {
fmt.Printf("Source is git: %s\n", source.URL)

dest := filepath.Join(recipe.DownloadsPath, source.Module)
dest := filepath.Join(downloadPath, source.Module)

if source.Commit == "" && source.Tag == "" && source.Branch == "" {
return fmt.Errorf("missing source commit, tag or branch")
Expand Down Expand Up @@ -157,10 +116,10 @@ func DownloadGitSource(recipe *Recipe, source Source) error {
}

// DownloadTarSource downloads a tar archive to the downloads directory
func DownloadTarSource(recipe *Recipe, source Source) error {
func DownloadTarSource(downloadPath string, source Source) error {
fmt.Printf("Source is tar: %s\n", source.URL)
//Create the destination path
dest := filepath.Join(recipe.DownloadsPath, source.Module)
dest := filepath.Join(downloadPath, source.Module)
//Download the resource
res, err := http.Get(source.URL)
if err != nil {
Expand All @@ -186,11 +145,11 @@ func DownloadTarSource(recipe *Recipe, source Source) error {

// MoveSources moves all sources from the downloads directory to the
// sources directory
func MoveSources(recipe *Recipe, sources []Source) error {
func MoveSources(downloadPath string, sources []Source) error {
fmt.Println("Moving sources")

for _, source := range sources {
err := MoveSource(recipe, source)
err := MoveSource(downloadPath, source)
if err != nil {
return err
}
Expand All @@ -202,26 +161,26 @@ func MoveSources(recipe *Recipe, sources []Source) error {
// MoveSource moves a source from the downloads directory to the
// sources directory, by extracting if a tar archive or moving if a
// git repository
func MoveSource(recipe *Recipe, source Source) error {
func MoveSource(downloadPath string, source Source) error {
fmt.Printf("Moving source: %s\n", source.Module)

if source.Type == "git" {
return os.Rename(
filepath.Join(recipe.DownloadsPath, source.Module),
filepath.Join(recipe.SourcesPath, source.Module),
filepath.Join(downloadPath, source.Module),
filepath.Join(downloadPath, source.Module),
)
} else if source.Type == "tar" {
cmd := exec.Command(
"tar",
"-xf", filepath.Join(recipe.DownloadsPath, source.Module),
"-C", recipe.SourcesPath,
"-xf", filepath.Join(downloadPath, source.Module),
"-C", downloadPath,
)
err := cmd.Run()
if err != nil {
return err
}

return os.Remove(filepath.Join(recipe.DownloadsPath, source.Module))
return os.Remove(filepath.Join(downloadPath, source.Module))
} else {
return fmt.Errorf("unsupported source type %s", source.Type)
}
Expand Down
18 changes: 18 additions & 0 deletions api/structs.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,3 +11,21 @@ type Source struct {
Paths []string `json:"paths"`
Module string
}

type Recipe struct {
Base string `json:"base"`
Name string
Id string
SingleLayer bool `json:"singlelayer"`
Labels map[string]string `json:"labels"`
Adds map[string]string `json:"adds"`
Args map[string]string `json:"args"`
Runs []string `json:"runs"`
Cmd string `json:"cmd"`
Modules []interface{} `json:"modules"`
Path string
ParentPath string
DownloadsPath string
SourcesPath string
Containerfile string
}
5 changes: 3 additions & 2 deletions core/apt.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,14 @@ import (

type AptModule struct {
Name string `json:"name"`
Type string `json:"name"`
Type string `json:"type"`
Source api.Source `json:"source"`
}

// BuildAptModule builds a module that installs packages
// using the apt package manager
func BuildAptModule(recipe *Recipe, module AptModule) (string, error) {
func BuildAptModule(moduleInterface interface{}, recipe *api.Recipe) (string, error) {
module := moduleInterface.(AptModule)
if len(module.Source.Packages) > 0 {
packages := ""
for _, pkg := range module.Source.Packages {
Expand Down
59 changes: 37 additions & 22 deletions core/build.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,17 @@ package core

import (
"fmt"
"github.com/mitchellh/mapstructure"
"github.com/vanilla-os/vib/api"
"os"
)

// BuildRecipe builds a Containerfile from a recipe path
func BuildRecipe(recipePath string) (Recipe, error) {
func BuildRecipe(recipePath string) (api.Recipe, error) {
// load the recipe
recipe, err := LoadRecipe(recipePath)
if err != nil {
return Recipe{}, err
return api.Recipe{}, err
}

fmt.Printf("Building recipe %s\n", recipe.Name)
Expand All @@ -33,21 +35,21 @@ func BuildRecipe(recipePath string) (Recipe, error) {
// in the Containerfile to build the modules
cmds, err := BuildModules(recipe, recipe.Modules)
if err != nil {
return Recipe{}, err
return api.Recipe{}, err
}

// build the Containerfile
err = BuildContainerfile(recipe, cmds)
if err != nil {
return Recipe{}, err
return api.Recipe{}, err
}

return *recipe, nil
}

// BuildContainerfile builds a Containerfile from a recipe
// and a list of modules commands
func BuildContainerfile(recipe *Recipe, cmds []ModuleCommand) error {
func BuildContainerfile(recipe *api.Recipe, cmds []ModuleCommand) error {
containerfile, err := os.Create(recipe.Containerfile)
if err != nil {
return err
Expand Down Expand Up @@ -172,19 +174,23 @@ func BuildContainerfile(recipe *Recipe, cmds []ModuleCommand) error {
}

// BuildModules builds a list of modules commands from a list of modules
func BuildModules(recipe *Recipe, modules map[string]interface{}) ([]ModuleCommand, error) {
func BuildModules(recipe *api.Recipe, modules []interface{}) ([]ModuleCommand, error) {
cmds := []ModuleCommand{}
for _, moduleInterface := range modules {
var module Module
err := mapstructure.Decode(moduleInterface, &module)
if err != nil {
return nil, err
}
fmt.Printf("Creating build command for %s\n", module)

for _, module := range modules {
fmt.Printf("Creating build command for %s\n", module.(Module).Name)

cmd, err := BuildModule(recipe, module)
cmd, err := BuildModule(recipe, moduleInterface)
if err != nil {
return nil, err
}

cmds = append(cmds, ModuleCommand{
Name: module.(Module).Name,
Name: module.Name,
Command: cmd,
})
}
Expand All @@ -195,25 +201,34 @@ func BuildModules(recipe *Recipe, modules map[string]interface{}) ([]ModuleComma
// BuildModule builds a module command from a module
// this is done by calling the appropriate module builder
// function based on the module type
func BuildModule(recipe *Recipe, module interface{}) (string, error) {
switch module.(Module).Type {
func BuildModule(recipe *api.Recipe, moduleInterface interface{}) (string, error) {
var module Module
err := mapstructure.Decode(moduleInterface, &module)
if err != nil {
return "", err
}
fmt.Printf("Processing module: %s\n", module.Type)
fmt.Println(moduleInterface)
switch module.Type {
case "apt":
return BuildAptModule(recipe, module.(AptModule))
return BuildAptModule(moduleInterface, recipe)
case "cmake":
return BuildCMakeModule(module.(CMakeModule))
return BuildCMakeModule(moduleInterface, recipe)
case "dpkg":
return BuildDpkgModule(module.(DpkgModule))
return BuildDpkgModule(moduleInterface, recipe)
case "dpkg-buildpackage":
return BuildDpkgBuildPkgModule(module.(DpkgBuildModule))
return BuildDpkgBuildPkgModule(moduleInterface, recipe)
case "go":
return BuildGoModule(module.(GoModule))
return BuildGoModule(moduleInterface, recipe)
case "make":
return BuildMakeModule(module.(Module))
return BuildMakeModule(moduleInterface, recipe)
case "meson":
return BuildMesonModule(module.(Module))
return BuildMesonModule(moduleInterface, recipe)
case "shell":
return BuildShellModule(module.(ShellModule))
return BuildShellModule(moduleInterface, recipe)
case "includes":
return "", nil
default:
return LoadPlugin(module.(Module).Type, module)
return LoadPlugin(module.Type, moduleInterface, recipe)
}
}
24 changes: 19 additions & 5 deletions core/cmake.go
Original file line number Diff line number Diff line change
@@ -1,16 +1,30 @@
package core

import "fmt"
import (
"fmt"

"github.com/vanilla-os/vib/api"
)

type CMakeModule struct {
Name string `json:"name"`
Type string `json:"name"`
BuildVars map[string]string `json:"name"`
BuildFlags string `json:"name"`
Type string `json:"type"`
BuildVars map[string]string `json:"buildvars"`
BuildFlags string `json:"buildflags"`
Source api.Source
}

// BuildCMakeModule builds a module that builds a CMake project
func BuildCMakeModule(module CMakeModule) (string, error) {
func BuildCMakeModule(moduleInterface interface{}, recipe *api.Recipe) (string, error) {
module := moduleInterface.(CMakeModule)
err := api.DownloadSource(recipe.DownloadsPath, module.Source)
if err != nil {
return "", err
}
err = api.MoveSource(recipe.DownloadsPath, module.Source)
if err != nil {
return "", err
}
buildVars := map[string]string{}
for k, v := range module.BuildVars {
buildVars[k] = v
Expand Down
5 changes: 3 additions & 2 deletions core/compile.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package core

import (
"fmt"
"github.com/vanilla-os/vib/api"
"os"
"os/exec"
)
Expand Down Expand Up @@ -44,7 +45,7 @@ func CompileRecipe(recipePath string, runtime string) error {
return nil
}

func compileDocker(recipe Recipe, storePath string) error {
func compileDocker(recipe api.Recipe, storePath string) error {
docker, err := exec.LookPath("docker")
if err != nil {
return err
Expand All @@ -64,7 +65,7 @@ func compileDocker(recipe Recipe, storePath string) error {
return cmd.Run()
}

func compilePodman(recipe Recipe, storePath string) error {
func compilePodman(recipe api.Recipe, storePath string) error {
podman, err := exec.LookPath("podman")
if err != nil {
return err
Expand Down
3 changes: 2 additions & 1 deletion core/dpkg-buildpackage.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@ type DpkgBuildModule struct {

// BuildDpkgModule builds a module that builds a dpkg project
// and installs the resulting .deb package
func BuildDpkgBuildPkgModule(module DpkgBuildModule) (string, error) {
func BuildDpkgBuildPkgModule(moduleInterface interface{}, _ *api.Recipe) (string, error) {
module := moduleInterface.(DpkgBuildModule)
cmd := fmt.Sprintf(
"cd /sources/%s && dpkg-buildpackage -d -us -uc -b",
module.Name,
Expand Down
3 changes: 2 additions & 1 deletion core/dpkg.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,8 @@ type DpkgModule struct {
}

// BuildDpkgModule builds a module that installs a .deb package
func BuildDpkgModule(module DpkgModule) (string, error) {
func BuildDpkgModule(moduleInterface interface{}, _ *api.Recipe) (string, error) {
module := moduleInterface.(DpkgModule)
cmd := ""
for _, path := range module.Source.Paths {
cmd += fmt.Sprintf(" dpkg -i /sources/%s && apt install -f && ", path)
Expand Down
Loading

0 comments on commit 6eea1f6

Please sign in to comment.