首页 > 解决方案 > 如何使用 libgit2 在内存上构建/表示 git bare repo 的工作树

问题描述

我正在构建一个用 rust 编写的 git 服务器,我正在使用 git2 库,它是 libgit2 的 rust 绑定。

实际上我可以通过 API 创建裸存储库,现在我想从裸存储库在内存上构建工作树,以便以后在 web ui 中服务和渲染工作树,但我不明白如何制作它。

Git2 提供了 Repository 和 Worktree 结构来操作它,无论是创建、操作还是打开它们,都具有使用工作树的方法,但两者都需要或存在于 repo 中(不再是一个裸 repo),或者用于创建工作树在 repo 中制作它(这将不再是一个裸 repo)。

我想我说的是“从 git 对象构建验证副本(工作树)的过程”,但我不明白这是如何工作的,在第 10 章第 2 节的 git pro 书中,这本书谈到了 git代表一个工作树(对象树和 blob),但我不知道“过程是如何工作的”。

任何人都可以分享这方面的资源,或者向我解释我缺少什么?

标签: gitrustlibgit2

解决方案


感谢@torek的评论,我刚刚找到了一种遍历文件树的方法,将repo的头部作为一个Reference结构,这个结构提供了peel_to_tree()将底层树作为结构返回给引用的方法,Tree这提供了walk方法,从这里我检查树。

    let repo = Repository::open_bare( Path::new("/some/path.git") ).expect("error open repo");
    
    let head = repo.head().expect("error");

    let tree = head.peel_to_tree();

    match tree {
        Ok(tree) => {
            let mut ct = 0;
            tree.walk( TreeWalkMode::PreOrder, |root, entry| {
                println!("root_path: {}\nName: {}\nKind: {:?}\n\n", root, entry.name().expect("error name"), entry.kind().expect("error kind")  );
                ct +=1;
                TreeWalkResult::Ok
            } ).unwrap();

            println!("All entries: {}",ct);
        },
        Err(e) => println!("{:?}", e),
    }

我不完全确定这个过程的好坏,但我认为这是我想做的一个很好的起点。


推荐阅读