cli: Tell the user when canonical head is updated
This is useful especially in multi-delegate repos, since patches can be merged without the head being updated.
This commit is contained in:
parent
6bc7d297a5
commit
7169e97bd5
|
|
@ -62,6 +62,7 @@ f2de534 Second commit
|
||||||
```
|
```
|
||||||
``` ~alice RAD_SOCKET=/dev/null (stderr)
|
``` ~alice RAD_SOCKET=/dev/null (stderr)
|
||||||
$ git push rad
|
$ git push rad
|
||||||
|
✓ Canonical head updated to f6cff86594495e9beccfeda7c20173e55c1dd9fc
|
||||||
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
||||||
f2de534..f6cff86 master -> master
|
f2de534..f6cff86 master -> master
|
||||||
```
|
```
|
||||||
|
|
@ -79,6 +80,7 @@ We have to use the `allow.rollback` option:
|
||||||
|
|
||||||
``` ~alice RAD_SOCKET=/dev/null (stderr)
|
``` ~alice RAD_SOCKET=/dev/null (stderr)
|
||||||
$ git push -f -o allow.rollback
|
$ git push -f -o allow.rollback
|
||||||
|
✓ Canonical head updated to 319a7dc3b195368ded4b099f8c90bbb80addccd3
|
||||||
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
||||||
+ f6cff86...319a7dc master -> master (forced update)
|
+ f6cff86...319a7dc master -> master (forced update)
|
||||||
```
|
```
|
||||||
|
|
|
||||||
|
|
@ -16,6 +16,7 @@ $ git commit --amend --allow-empty -q -m "Amended change"
|
||||||
$ git checkout master -q
|
$ git checkout master -q
|
||||||
$ git merge feature/1 -q
|
$ git merge feature/1 -q
|
||||||
$ git push rad master
|
$ git push rad master
|
||||||
|
✓ Canonical head updated to 954bcdb5008447ce294a61a21d7eb87afbe7f4a6
|
||||||
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
||||||
f2de534..954bcdb master -> master
|
f2de534..954bcdb master -> master
|
||||||
```
|
```
|
||||||
|
|
|
||||||
|
|
@ -37,6 +37,7 @@ Finally, we push master and expect the patch to be merged.
|
||||||
``` (stderr) RAD_SOCKET=/dev/null
|
``` (stderr) RAD_SOCKET=/dev/null
|
||||||
$ git push rad master
|
$ git push rad master
|
||||||
✓ Patch a1207f6e82700e42cc46c9c38c7786b18cbd2040 merged
|
✓ Patch a1207f6e82700e42cc46c9c38c7786b18cbd2040 merged
|
||||||
|
✓ Canonical head updated to 737a10cfa29111afeb0d43cf3545cee386b939ec
|
||||||
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
||||||
f2de534..737a10c master -> master
|
f2de534..737a10c master -> master
|
||||||
```
|
```
|
||||||
|
|
|
||||||
|
|
@ -63,6 +63,7 @@ When we push to `rad/master`, we automatically merge the patches:
|
||||||
$ git push rad master
|
$ git push rad master
|
||||||
✓ Patch 8357a9f1d61e80309d314491aa754969d9f47d77 merged
|
✓ Patch 8357a9f1d61e80309d314491aa754969d9f47d77 merged
|
||||||
✓ Patch a1207f6e82700e42cc46c9c38c7786b18cbd2040 merged
|
✓ Patch a1207f6e82700e42cc46c9c38c7786b18cbd2040 merged
|
||||||
|
✓ Canonical head updated to d6399c71702b40bae00825b3c444478d06b4e91c
|
||||||
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
||||||
f2de534..d6399c7 master -> master
|
f2de534..d6399c7 master -> master
|
||||||
```
|
```
|
||||||
|
|
|
||||||
|
|
@ -14,6 +14,7 @@ $ git checkout master -q
|
||||||
$ git merge feature/1
|
$ git merge feature/1
|
||||||
$ git push rad master
|
$ git push rad master
|
||||||
✓ Patch cf29ac6b10141058be66b94a92a81c703b972751 merged
|
✓ Patch cf29ac6b10141058be66b94a92a81c703b972751 merged
|
||||||
|
✓ Canonical head updated to 20aa5dde6210796c3a2f04079b42316a31d02689
|
||||||
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
||||||
f2de534..20aa5dd master -> master
|
f2de534..20aa5dd master -> master
|
||||||
```
|
```
|
||||||
|
|
|
||||||
|
|
@ -90,6 +90,7 @@ Fast-forward
|
||||||
``` (stderr)
|
``` (stderr)
|
||||||
$ git push rad master
|
$ git push rad master
|
||||||
✓ Patch 3581e83ad18f5cdd806ab50fa11cfd5dd4e8ae1c merged at revision abb0360
|
✓ Patch 3581e83ad18f5cdd806ab50fa11cfd5dd4e8ae1c merged at revision abb0360
|
||||||
|
✓ Canonical head updated to f567f695d25b4e8fb63b5f5ad2a584529826e908
|
||||||
✓ Synced with 1 node(s)
|
✓ Synced with 1 node(s)
|
||||||
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi
|
||||||
f2de534..f567f69 master -> master
|
f2de534..f567f69 master -> master
|
||||||
|
|
|
||||||
|
|
@ -279,8 +279,16 @@ pub fn run(
|
||||||
|
|
||||||
// Sign refs and sync if at least one ref pushed successfully.
|
// Sign refs and sync if at least one ref pushed successfully.
|
||||||
if !ok.is_empty() {
|
if !ok.is_empty() {
|
||||||
stored.sign_refs(&signer)?;
|
let _ = stored.sign_refs(&signer)?;
|
||||||
stored.set_head()?;
|
let head = stored.set_head()?;
|
||||||
|
|
||||||
|
if head.is_updated() {
|
||||||
|
eprintln!(
|
||||||
|
"{} Canonical head updated to {}",
|
||||||
|
cli::format::positive("✓"),
|
||||||
|
cli::format::secondary(head.new),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
if !opts.no_sync {
|
if !opts.no_sync {
|
||||||
// Connect to local node and announce refs to the network.
|
// Connect to local node and announce refs to the network.
|
||||||
|
|
|
||||||
|
|
@ -21,7 +21,7 @@ fn main() -> anyhow::Result<()> {
|
||||||
|
|
||||||
radicle::Node::new(profile.socket()).announce_refs(id)?;
|
radicle::Node::new(profile.socket()).announce_refs(id)?;
|
||||||
|
|
||||||
println!("head: {head}");
|
println!("head: {}", head.new);
|
||||||
println!("ok: {}", sigrefs.signature);
|
println!("ok: {}", sigrefs.signature);
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
|
|
|
||||||
|
|
@ -10,10 +10,10 @@ fn main() -> anyhow::Result<()> {
|
||||||
let repo = profile.storage.repository_mut(rid)?;
|
let repo = profile.storage.repository_mut(rid)?;
|
||||||
|
|
||||||
let id_oid = repo.set_identity_head()?;
|
let id_oid = repo.set_identity_head()?;
|
||||||
let branch_oid = repo.set_head()?;
|
let branch = repo.set_head()?;
|
||||||
|
|
||||||
println!("ok: identity: {id_oid}");
|
println!("ok: identity: {id_oid}");
|
||||||
println!("ok: branch: {branch_oid}");
|
println!("ok: branch: {}", branch.new);
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -69,6 +69,21 @@ impl FromIterator<PublicKey> for Namespaces {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Output of [`WriteRepository::set_head`].
|
||||||
|
pub struct SetHead {
|
||||||
|
/// Old branch head.
|
||||||
|
pub old: Option<Oid>,
|
||||||
|
/// New branch head.
|
||||||
|
pub new: Oid,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SetHead {
|
||||||
|
/// Check if the head was updated.
|
||||||
|
pub fn is_updated(&self) -> bool {
|
||||||
|
self.old != Some(self.new)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// Repository error.
|
/// Repository error.
|
||||||
#[derive(Error, Debug)]
|
#[derive(Error, Debug)]
|
||||||
pub enum RepositoryError {
|
pub enum RepositoryError {
|
||||||
|
|
@ -536,7 +551,7 @@ where
|
||||||
pub trait WriteRepository: ReadRepository + SignRepository {
|
pub trait WriteRepository: ReadRepository + SignRepository {
|
||||||
/// Set the repository head to the canonical branch.
|
/// Set the repository head to the canonical branch.
|
||||||
/// This computes the head based on the delegate set.
|
/// This computes the head based on the delegate set.
|
||||||
fn set_head(&self) -> Result<Oid, RepositoryError>;
|
fn set_head(&self) -> Result<SetHead, RepositoryError>;
|
||||||
/// Set the repository 'rad/id' to the canonical commit, agreed by quorum.
|
/// Set the repository 'rad/id' to the canonical commit, agreed by quorum.
|
||||||
fn set_identity_head(&self) -> Result<Oid, RepositoryError> {
|
fn set_identity_head(&self) -> Result<Oid, RepositoryError> {
|
||||||
let head = self.canonical_identity_head()?;
|
let head = self.canonical_identity_head()?;
|
||||||
|
|
|
||||||
|
|
@ -19,8 +19,8 @@ use crate::identity::{Identity, Project};
|
||||||
use crate::storage::refs;
|
use crate::storage::refs;
|
||||||
use crate::storage::refs::{Refs, SignedRefs, SignedRefsAt};
|
use crate::storage::refs::{Refs, SignedRefs, SignedRefsAt};
|
||||||
use crate::storage::{
|
use crate::storage::{
|
||||||
Inventory, ReadRepository, ReadStorage, Remote, Remotes, RepositoryError, SignRepository,
|
Inventory, ReadRepository, ReadStorage, Remote, Remotes, RepositoryError, SetHead,
|
||||||
WriteRepository, WriteStorage,
|
SignRepository, WriteRepository, WriteStorage,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub use crate::git::{
|
pub use crate::git::{
|
||||||
|
|
@ -799,19 +799,27 @@ impl ReadRepository for Repository {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl WriteRepository for Repository {
|
impl WriteRepository for Repository {
|
||||||
fn set_head(&self) -> Result<Oid, RepositoryError> {
|
fn set_head(&self) -> Result<SetHead, RepositoryError> {
|
||||||
let head_ref = refname!("HEAD");
|
let head_ref = refname!("HEAD");
|
||||||
let (branch_ref, head) = self.canonical_head()?;
|
let old = self
|
||||||
|
.raw()
|
||||||
|
.refname_to_id(&head_ref)
|
||||||
|
.ok()
|
||||||
|
.map(|oid| oid.into());
|
||||||
|
let (branch_ref, new) = self.canonical_head()?;
|
||||||
|
|
||||||
log::debug!(target: "storage", "Setting ref: {} -> {}", &branch_ref, head);
|
if old == Some(new) {
|
||||||
|
return Ok(SetHead { old, new });
|
||||||
|
}
|
||||||
|
log::debug!(target: "storage", "Setting ref: {} -> {}", &branch_ref, new);
|
||||||
self.raw()
|
self.raw()
|
||||||
.reference(&branch_ref, *head, true, "set-local-branch (radicle)")?;
|
.reference(&branch_ref, *new, true, "set-local-branch (radicle)")?;
|
||||||
|
|
||||||
log::debug!(target: "storage", "Setting ref: {} -> {}", head_ref, branch_ref);
|
log::debug!(target: "storage", "Setting ref: {} -> {}", head_ref, branch_ref);
|
||||||
self.raw()
|
self.raw()
|
||||||
.reference_symbolic(&head_ref, &branch_ref, true, "set-head (radicle)")?;
|
.reference_symbolic(&head_ref, &branch_ref, true, "set-head (radicle)")?;
|
||||||
|
|
||||||
Ok(head)
|
Ok(SetHead { old, new })
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_identity_head_to(&self, commit: Oid) -> Result<(), RepositoryError> {
|
fn set_identity_head_to(&self, commit: Oid) -> Result<(), RepositoryError> {
|
||||||
|
|
|
||||||
|
|
@ -288,7 +288,7 @@ impl WriteRepository for MockRepository {
|
||||||
todo!()
|
todo!()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_head(&self) -> Result<Oid, RepositoryError> {
|
fn set_head(&self) -> Result<SetHead, RepositoryError> {
|
||||||
todo!()
|
todo!()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue