doufei16736 2018-12-23 06:26
浏览 90
已采纳

如何使git2go tree.Walk()非递归并显示文件夹并从目标文件夹开始?

I have the following code:

branch, err := gR.LookupBranch(branchName, git.BranchLocal)
if err != nil {
    return err
}
defer branch.Free()

commit, err := gR.LookupCommit(branch.Target())
if err != nil {
    return err
}
defer commit.Free()

tree, err := gR.LookupTree(commit.TreeId())
if err != nil {
    return err
}
defer tree.Free()

err = tree.Walk(func(td string, te *git.TreeEntry) int {
    if te.Type == git.ObjectBlob {
        fmt.Println(te.Name)
    }
    return 0
})

This recursively prints out all the files in the repository. For example, if we had the following files in our repo:

test_file.txt
test_file_2.txt
test_folder/test_subfile_1.txt
test_folder/test_subfolder/test_subfile_2.txt

Then it would print:

test_file.txt
test_file2.txt
test_subfile_1.txt
test_subfile_2.txt

Instead, my aim is to print:

test_file.txt
test_file_2.txt
test_folder

But then also be able to choose to start the walk from inside the folder, so be able to print:

test_subfile_1.txt
test_subfolder

How can I achieve this? (The aim is to lazy load a directory structure into a web client i.e. to allow the web client to load contents of folders when the user opens them - also note this is a bare repo)

  • 写回答

1条回答 默认 最新

  • dtihe8614 2019-01-24 23:25
    关注

    To avoid entering a given directory, it's enough to return 1 from a function passed to Walk.

    You can save seen directories in an array or a channel.

    Example:

    func echoFilesCollectDirs(repo *git.Repository, tree *git.Tree, ch chan *git.Tree) {
        tree.Walk(func(td string, te *git.TreeEntry) int {
            fmt.Println(te.Name)
            if te.Type == git.ObjectTree {
                t, _ := repo.LookupTree(te.Id)
                go func() { ch <- t }() // send tree into channel to process it later
                return 1
            }
            return 0
        })
    }
    
    func main() {
        gR, tree := getRepoAndTree() // returns (*git.Repository, *git.Tree)
        ch := make(chan *git.Tree)
        echoFilesCollectDirs(gR, tree, ch)
        // process next directory in a channel
        // t := <-ch
        // echoFilesCollectDirs(gR, t, ch)
    }
    

    Note: to make the code shorter, I've removed error handling and a boilerplate part that gets *git.Repository and root *git.Tree (function getRepoAndTree()).

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 Qt下使用tcp获取数据的详细操作
  • ¥15 idea右下角设置编码是灰色的
  • ¥15 全志H618ROM新增分区
  • ¥15 在grasshopper里DrawViewportWires更改预览后,禁用电池仍然显示
  • ¥15 NAO机器人的录音程序保存问题
  • ¥15 C#读写EXCEL文件,不同编译
  • ¥15 MapReduce结果输出到HBase,一直连接不上MySQL
  • ¥15 扩散模型sd.webui使用时报错“Nonetype”
  • ¥15 stm32流水灯+呼吸灯+外部中断按键
  • ¥15 将二维数组,按照假设的规定,如0/1/0 == "4",把对应列位置写成一个字符并打印输出该字符