supergit: starting work on implementing branching iterators

wip/yesman
Katharina Fey 4 years ago committed by Mx Kookie
parent a2513a72e6
commit b2681a59d5
  1. 16
      apps/servers/octopus/supergit/src/bin/test.rs
  2. 56
      apps/servers/octopus/supergit/src/branch.rs

@ -22,12 +22,12 @@ fn main() {
let head = main.get_head();
let tree = head.get_tree();
println!(
"{:?}",
tree.history(main.get_all(), "Cargo.toml")
.into_iter()
.map(|c| c.summary())
.collect::<Vec<_>>()
);
// println!(
// "{:?}",
// tree.history(main.get_all(), "infra/libkookie/nixpkgs/nixos/modules/module-list.nix")
// .into_iter()
// .map(|c| c.summary())
// .collect::<Vec<_>>()
// );
}

@ -1,4 +1,5 @@
use crate::{Commit, HashId};
use atomptr::AtomPtr;
use git2::Repository;
use std::{mem, sync::Arc};
@ -124,6 +125,8 @@ impl Branch {
/// handles. This means that without explicitly branching, this
/// iterator is first-parent.
pub struct BranchIter {
rec: AtomPtr<IterMode>,
splits: AtomPtr<Vec<HashId>>,
repo: Arc<Repository>,
curr: Option<HashId>,
limit: SegLimit,
@ -133,6 +136,8 @@ impl BranchIter {
/// Create a new branch segment iterator
fn new(repo: Arc<Repository>, last: HashId, limit: SegLimit) -> Self {
Self {
rec: AtomPtr::new(IterMode::FirstParent),
splits: AtomPtr::new(vec![]),
repo,
curr: Some(last),
limit,
@ -214,6 +219,25 @@ impl Iterator for BranchIter {
}
}
/// Specify the mode of a branch iterator
///
/// The default value is `FirstParent`, meaning that merged branches
/// will create a new `Branch` handle that the user must iterate
/// manually.
///
/// This is a reasonable default, but means that history searches for
/// files become more tedious. To improve this use-case, iterators
/// can internally be set to change their iteration behaviour, meaning
/// that returned commits are always `BranchCommit::Commit`, and can
pub enum IterMode {
/// Default value, iterating only first-parent commits
FirstParent,
/// Iterate a branch to completion, before picking the next
DepthFirst,
/// Iterate branches as they come up
BreadthFirst,
}
/// the limit applied to a branch segment
pub enum SegLimit {
/// No limit, enumerating all children
@ -259,3 +283,35 @@ impl BranchCommit {
}
}
}
/// Additional iterator data
struct IterData {
splits: AtomPtr<Vec<HashId>>,
}
impl IterData {
fn new() -> Self {
Self {
splits: AtomPtr::new(vec![]),
}
}
fn append(&self, id: HashId) {
let mut vec = (**self.splits.get_ref()).clone();
let mut new = vec![id];
new.append(&mut vec);
self.splits.swap(new);
}
fn next(&self) -> Option<HashId> {
let mut vec = (**self.splits.get_ref()).clone();
let next = if vec.len() < 0 {
Some(vec.remove(0))
} else {
None
};
self.splits.swap(vec);
next
}
}

Loading…
Cancel
Save