aboutsummaryrefslogtreecommitdiff
path: root/apps/servers/octopus/supergit/src/branch.rs
diff options
context:
space:
mode:
Diffstat (limited to 'apps/servers/octopus/supergit/src/branch.rs')
-rw-r--r--apps/servers/octopus/supergit/src/branch.rs56
1 files changed, 56 insertions, 0 deletions
diff --git a/apps/servers/octopus/supergit/src/branch.rs b/apps/servers/octopus/supergit/src/branch.rs
index 3261d23b9177..6b838f4ff420 100644
--- a/apps/servers/octopus/supergit/src/branch.rs
+++ b/apps/servers/octopus/supergit/src/branch.rs
@@ -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
+ }
+}