refactor: keep only one struct for package

This commit is contained in:
2025-06-12 16:25:18 +03:00
parent e259184a89
commit 392a522723
34 changed files with 682 additions and 580 deletions

View File

@ -22,11 +22,11 @@ package repos
import (
"context"
"gitea.plemya-x.ru/Plemya-x/ALR/internal/db"
"gitea.plemya-x.ru/Plemya-x/ALR/pkg/alrsh"
)
func (rs *Repos) FindPkgs(ctx context.Context, pkgs []string) (map[string][]db.Package, []string, error) {
found := map[string][]db.Package{}
func (rs *Repos) FindPkgs(ctx context.Context, pkgs []string) (map[string][]alrsh.Package, []string, error) {
found := map[string][]alrsh.Package{}
notFound := []string(nil)
for _, pkgName := range pkgs {

View File

@ -24,8 +24,8 @@ import (
"strings"
"testing"
"gitea.plemya-x.ru/Plemya-x/ALR/internal/db"
"gitea.plemya-x.ru/Plemya-x/ALR/internal/repos"
"gitea.plemya-x.ru/Plemya-x/ALR/pkg/alrsh"
"gitea.plemya-x.ru/Plemya-x/ALR/pkg/types"
)
@ -89,31 +89,31 @@ func TestFindPkgsEmpty(t *testing.T) {
e.Db,
)
err := e.Db.InsertPackage(e.Ctx, db.Package{
err := e.Db.InsertPackage(e.Ctx, alrsh.Package{
Name: "test1",
Repository: "default",
Version: "0.0.1",
Release: 1,
Description: map[string]string{
Provides: []string{""},
Description: alrsh.OverridableFromMap(map[string]string{
"en": "Test package 1",
"ru": "Проверочный пакет 1",
},
Provides: []string{""},
}),
})
if err != nil {
t.Fatalf("Expected no error, got %s", err)
}
err = e.Db.InsertPackage(e.Ctx, db.Package{
err = e.Db.InsertPackage(e.Ctx, alrsh.Package{
Name: "test2",
Repository: "default",
Version: "0.0.1",
Release: 1,
Description: map[string]string{
Provides: []string{"test"},
Description: alrsh.OverridableFromMap(map[string]string{
"en": "Test package 2",
"ru": "Проверочный пакет 2",
},
Provides: []string{"test"},
}),
})
if err != nil {
t.Fatalf("Expected no error, got %s", err)

View File

@ -27,6 +27,7 @@ import (
"gitea.plemya-x.ru/Plemya-x/ALR/internal/config"
"gitea.plemya-x.ru/Plemya-x/ALR/internal/db"
"gitea.plemya-x.ru/Plemya-x/ALR/pkg/alrsh"
"gitea.plemya-x.ru/Plemya-x/ALR/pkg/types"
)
@ -84,10 +85,10 @@ build_deps=('golang')
result, err := database.GetPkgs(ctx, "1 = 1")
assert.NoError(t, err)
pkgCount := 0
for _, dbPkg := range result {
assert.Equal(t, "foo", dbPkg.Name)
assert.Equal(t, map[string]string{"": "main desc"}, dbPkg.Description)
assert.Equal(t, map[string][]string{"": {"sudo"}}, dbPkg.Depends)
for _, pkg := range result {
assert.Equal(t, "foo", pkg.Name)
assert.Equal(t, alrsh.OverridableFromMap(map[string]string{"": "main desc"}), pkg.Description)
assert.Equal(t, alrsh.OverridableFromMap(map[string][]string{"": {"sudo"}}), pkg.Depends)
pkgCount++
}
assert.Equal(t, 1, pkgCount)
@ -119,18 +120,18 @@ meta_buz() {
assert.NoError(t, err)
pkgCount := 0
for _, dbPkg := range result {
for _, pkg := range result {
if err != nil {
t.Errorf("Expected no error, got %s", err)
}
if dbPkg.Name == "bar" {
assert.Equal(t, map[string]string{"": "foo desc"}, dbPkg.Description)
assert.Equal(t, map[string][]string{"": {"sudo"}}, dbPkg.Depends)
if pkg.Name == "bar" {
assert.Equal(t, alrsh.OverridableFromMap(map[string]string{"": "foo desc"}), pkg.Description)
assert.Equal(t, alrsh.OverridableFromMap(map[string][]string{"": {"sudo"}}), pkg.Depends)
}
if dbPkg.Name == "buz" {
assert.Equal(t, map[string]string{"": "main desc"}, dbPkg.Description)
assert.Equal(t, map[string][]string{"": {"sudo", "doas"}}, dbPkg.Depends)
if pkg.Name == "buz" {
assert.Equal(t, alrsh.OverridableFromMap(map[string]string{"": "main desc"}), pkg.Description)
assert.Equal(t, alrsh.OverridableFromMap(map[string][]string{"": {"sudo", "doas"}}), pkg.Depends)
}
pkgCount++
}

View File

@ -18,12 +18,9 @@ package repos
import (
"context"
"errors"
"fmt"
"io"
"path/filepath"
"reflect"
"strings"
"github.com/go-git/go-git/v5"
"github.com/go-git/go-git/v5/plumbing"
@ -34,9 +31,7 @@ import (
"mvdan.cc/sh/v3/interp"
"mvdan.cc/sh/v3/syntax"
"gitea.plemya-x.ru/Plemya-x/ALR/internal/db"
"gitea.plemya-x.ru/Plemya-x/ALR/internal/parser"
"gitea.plemya-x.ru/Plemya-x/ALR/internal/shutils/decoder"
"gitea.plemya-x.ru/Plemya-x/ALR/pkg/alrsh"
"gitea.plemya-x.ru/Plemya-x/ALR/pkg/distro"
"gitea.plemya-x.ru/Plemya-x/ALR/pkg/types"
)
@ -63,151 +58,21 @@ func parseScript(
syntaxParser *syntax.Parser,
runner *interp.Runner,
r io.ReadCloser,
) ([]*db.Package, error) {
fl, err := syntaxParser.Parse(r, "alr.sh")
) ([]*alrsh.Package, error) {
f, err := alrsh.ReadFromIOReader(r, "/tmp")
if err != nil {
return nil, err
}
runner.Reset()
err = runner.Run(ctx, fl)
_, dbPkgs, err := f.ParseBuildVars(ctx, &distro.OSRelease{}, []string{})
if err != nil {
return nil, err
}
d := decoder.New(&distro.OSRelease{}, runner)
d.Overrides = false
d.LikeDistros = false
pkgNames, err := parser.ParseNames(d)
if err != nil {
return nil, fmt.Errorf("failed parsing package names: %w", err)
for _, pkg := range dbPkgs {
pkg.Repository = repo.Name
}
if len(pkgNames.Names) == 0 {
return nil, errors.New("package name is missing")
}
var dbPkgs []*db.Package
if len(pkgNames.Names) > 1 {
if pkgNames.BasePkgName == "" {
pkgNames.BasePkgName = pkgNames.Names[0]
}
for _, pkgName := range pkgNames.Names {
pkgInfo := PackageInfo{}
funcName := fmt.Sprintf("meta_%s", pkgName)
runner.Reset()
err = runner.Run(ctx, fl)
if err != nil {
return nil, err
}
meta, ok := d.GetFuncWithSubshell(funcName)
if !ok {
return nil, fmt.Errorf("func %s is missing", funcName)
}
r, err := meta(ctx)
if err != nil {
return nil, err
}
d := decoder.New(&distro.OSRelease{}, r)
d.Overrides = false
d.LikeDistros = false
err = d.DecodeVars(&pkgInfo)
if err != nil {
return nil, err
}
pkg := pkgInfo.ToPackage(repo.Name)
resolveOverrides(r, pkg)
pkg.Name = pkgName
pkg.BasePkgName = pkgNames.BasePkgName
dbPkgs = append(dbPkgs, pkg)
}
return dbPkgs, nil
}
pkg := EmptyPackage(repo.Name)
err = d.DecodeVars(pkg)
if err != nil {
return nil, err
}
resolveOverrides(runner, pkg)
dbPkgs = append(dbPkgs, pkg)
return dbPkgs, nil
}
type PackageInfo struct {
Version string `sh:"version,required"`
Release int `sh:"release,required"`
Epoch uint `sh:"epoch"`
Architectures []string `sh:"architectures"`
Licenses []string `sh:"license"`
Provides []string `sh:"provides"`
Conflicts []string `sh:"conflicts"`
Replaces []string `sh:"replaces"`
}
func (inf *PackageInfo) ToPackage(repoName string) *db.Package {
pkg := EmptyPackage(repoName)
pkg.Version = inf.Version
pkg.Release = inf.Release
pkg.Epoch = inf.Epoch
pkg.Architectures = inf.Architectures
pkg.Licenses = inf.Licenses
pkg.Provides = inf.Provides
pkg.Conflicts = inf.Conflicts
pkg.Replaces = inf.Replaces
return pkg
}
func EmptyPackage(repoName string) *db.Package {
return &db.Package{
Group: map[string]string{},
Summary: map[string]string{},
Description: map[string]string{},
Homepage: map[string]string{},
Maintainer: map[string]string{},
Depends: map[string][]string{},
BuildDepends: map[string][]string{},
Repository: repoName,
}
}
var overridable = map[string]string{
"deps": "Depends",
"build_deps": "BuildDepends",
"desc": "Description",
"homepage": "Homepage",
"maintainer": "Maintainer",
"group": "Group",
"summary": "Summary",
}
func resolveOverrides(runner *interp.Runner, pkg *db.Package) {
pkgVal := reflect.ValueOf(pkg).Elem()
for name, val := range runner.Vars {
for prefix, field := range overridable {
if strings.HasPrefix(name, prefix) {
override := strings.TrimPrefix(name, prefix)
override = strings.TrimPrefix(override, "_")
varVal := pkgVal.FieldByName(field)
varType := varVal.Type()
switch varType.Elem().String() {
case "[]string":
varVal.SetMapIndex(reflect.ValueOf(override), reflect.ValueOf(val.List))
case "string":
varVal.SetMapIndex(reflect.ValueOf(override), reflect.ValueOf(val.Str))
}
break
}
}
}
}
func getHeadReference(r *git.Repository) (plumbing.ReferenceName, error) {
remote, err := r.Remote(git.DefaultRemoteName)
if err != nil {