staging: assume changed directories are packages

Ignore any non-top level direcotries here. This should be fixed
to handle _manifest files
This commit is contained in:
2025-09-11 14:56:27 +02:00
parent 1a19873f77
commit ff7df44d37
2 changed files with 114 additions and 18 deletions

View File

@@ -40,6 +40,10 @@ type GitSubmoduleLister interface {
GitSubmoduleCommitId(cwd, packageName, commitId string) (subCommitId string, valid bool) GitSubmoduleCommitId(cwd, packageName, commitId string) (subCommitId string, valid bool)
} }
type GitDirectoryLister interface {
GitDirectoryList(gitPath, commitId string) (dirlist map[string]string, err error)
}
type GitStatusLister interface { type GitStatusLister interface {
GitStatus(cwd string) ([]GitStatusData, error) GitStatus(cwd string) ([]GitStatusData, error)
} }
@@ -61,6 +65,7 @@ type Git interface {
io.Closer io.Closer
GitSubmoduleLister GitSubmoduleLister
GitDirectoryLister
GitStatusLister GitStatusLister
GitExecWithOutputOrPanic(cwd string, params ...string) string GitExecWithOutputOrPanic(cwd string, params ...string) string
@@ -247,26 +252,26 @@ func (e *GitHandlerImpl) GitClone(repo, branch, remoteUrl string) (string, error
e.GitExecOrPanic(repo, "fetch", "--prune", remoteName, remoteBranch) e.GitExecOrPanic(repo, "fetch", "--prune", remoteName, remoteBranch)
} }
/* /*
refsBytes, err := os.ReadFile(path.Join(e.GitPath, repo, ".git/refs/remotes", remoteName, "HEAD")) refsBytes, err := os.ReadFile(path.Join(e.GitPath, repo, ".git/refs/remotes", remoteName, "HEAD"))
if err != nil { if err != nil {
LogError("Cannot read HEAD of remote", remoteName) LogError("Cannot read HEAD of remote", remoteName)
return remoteName, fmt.Errorf("Cannot read HEAD of remote %s", remoteName) return remoteName, fmt.Errorf("Cannot read HEAD of remote %s", remoteName)
} }
refs := string(refsBytes) refs := string(refsBytes)
if refs[0:5] != "ref: " { if refs[0:5] != "ref: " {
LogError("Unexpected format of remote HEAD ref:", refs) LogError("Unexpected format of remote HEAD ref:", refs)
return remoteName, fmt.Errorf("Unexpected format of remote HEAD ref: %s", refs) return remoteName, fmt.Errorf("Unexpected format of remote HEAD ref: %s", refs)
} }
if len(branch) == 0 || branch == "HEAD" { if len(branch) == 0 || branch == "HEAD" {
remoteRef = strings.TrimSpace(refs[5:]) remoteRef = strings.TrimSpace(refs[5:])
branch = remoteRef[strings.LastIndex(remoteRef, "/")+1:] branch = remoteRef[strings.LastIndex(remoteRef, "/")+1:]
LogDebug("remoteRef", remoteRef) LogDebug("remoteRef", remoteRef)
LogDebug("branch", branch) LogDebug("branch", branch)
} }
*/ */
args := []string{"fetch", "--prune", remoteName, branch} args := []string{"fetch", "--prune", remoteName, branch}
if strings.TrimSpace(e.GitExecWithOutputOrPanic(repo, "rev-parse", "--is-shallow-repository")) == "true" { if strings.TrimSpace(e.GitExecWithOutputOrPanic(repo, "rev-parse", "--is-shallow-repository")) == "true" {
args = slices.Insert(args, 1, "--unshallow") args = slices.Insert(args, 1, "--unshallow")
@@ -778,6 +783,80 @@ func (e *GitHandlerImpl) GitCatFile(cwd, commitId, filename string) (data []byte
return return
} }
// return (filename) -> (hash) map for all submodules
func (e *GitHandlerImpl) GitDirectoryList(gitPath, commitId string) (directoryList map[string]string, err error) {
var done sync.Mutex
directoryList = make(map[string]string)
done.Lock()
data_in, data_out := ChanIO{make(chan byte)}, ChanIO{make(chan byte)}
LogDebug("Getting directory for:", commitId)
go func() {
defer done.Unlock()
defer close(data_out.ch)
data_out.Write([]byte(commitId))
data_out.ch <- '\x00'
var c GitCommit
c, err = parseGitCommit(data_in.ch)
if err != nil {
err = fmt.Errorf("Error parsing git commit. Err: %w", err)
return
}
trees := make(map[string]string)
trees[""] = c.Tree
for len(trees) > 0 {
for p, tree := range trees {
delete(trees, p)
data_out.Write([]byte(tree))
data_out.ch <- '\x00'
var tree GitTree
tree, err = parseGitTree(data_in.ch)
if err != nil {
err = fmt.Errorf("Error parsing git tree: %w", err)
return
}
for _, te := range tree.items {
if te.isTree() {
directoryList[p+te.name] = te.hash
}
}
}
}
}()
cmd := exec.Command("/usr/bin/git", "cat-file", "--batch", "-Z")
cmd.Env = []string{
"GIT_CEILING_DIRECTORIES=" + e.GitPath,
"GIT_LFS_SKIP_SMUDGE=1",
"GIT_CONFIG_GLOBAL=/dev/null",
}
cmd.Dir = filepath.Join(e.GitPath, gitPath)
cmd.Stdout = &data_in
cmd.Stdin = &data_out
cmd.Stderr = writeFunc(func(data []byte) (int, error) {
LogError(string(data))
return len(data), nil
})
LogDebug("command run:", cmd.Args)
if e := cmd.Run(); e != nil {
LogError(e)
close(data_in.ch)
close(data_out.ch)
return directoryList, e
}
done.Lock()
return directoryList, err
}
// return (filename) -> (hash) map for all submodules // return (filename) -> (hash) map for all submodules
func (e *GitHandlerImpl) GitSubmoduleList(gitPath, commitId string) (submoduleList map[string]string, err error) { func (e *GitHandlerImpl) GitSubmoduleList(gitPath, commitId string) (submoduleList map[string]string, err error) {
var done sync.Mutex var done sync.Mutex

View File

@@ -289,6 +289,23 @@ func GenerateObsPrjMeta(git common.Git, gitea common.Gitea, pr *models.PullReque
} }
} }
// find modified directories and assume they are packages
// TODO: use _manifest for this here
headDirectories, err := git.GitDirectoryList(dir, pr.Head.Sha)
if err != nil {
return nil, err
}
baseDirectories, err := git.GitDirectoryList(dir, pr.MergeBase)
if err != nil {
return nil, err
}
for pkg, headOid := range headDirectories {
if baseOid, exists := baseDirectories[pkg]; !exists || baseOid != headOid {
modifiedOrNew = append(modifiedOrNew, pkg)
}
}
common.LogDebug("Trying first staging master project: ", stagingMasterPrj) common.LogDebug("Trying first staging master project: ", stagingMasterPrj)
meta, err := ObsClient.GetProjectMeta(stagingMasterPrj) meta, err := ObsClient.GetProjectMeta(stagingMasterPrj)
if err == nil { if err == nil {