cli: sync on patch and issue updates

When we perform updates to cobs we tend to want to sync those changes
to the network after. This patch automatically does this for
operations that perform updates to issues and patches.

Note that `--announce` becomes the default for the `rad patch`
command.

Signed-off-by: Fintan Halpenny <fintan.halpenny@gmail.com>
X-Clacks-Overhead: GNU Terry Pratchett
This commit is contained in:
Fintan Halpenny 2023-12-14 15:05:28 +00:00 committed by cloudhead
parent 13db55014b
commit f90421a6bb
No known key found for this signature in database
10 changed files with 106 additions and 30 deletions

View File

@ -51,8 +51,8 @@ Let's assign ourselves to this one, this is to ensure work is not
duplicated. While we're at it, let's add a label. duplicated. While we're at it, let's add a label.
``` ```
$ rad issue assign d185ee1 --add did:key:z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi $ rad issue assign d185ee1 --add did:key:z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi --no-announce
$ rad issue label d185ee1 --add good-first-issue $ rad issue label d185ee1 --add good-first-issue --no-announce
``` ```
It will now show in the list of issues assigned to us, along with the new label. It will now show in the list of issues assigned to us, along with the new label.
@ -69,7 +69,7 @@ $ rad issue list --assigned
Note: this can always be undone with the `unassign` subcommand. Note: this can always be undone with the `unassign` subcommand.
``` ```
$ rad issue assign d185ee1 --delete did:key:z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi $ rad issue assign d185ee1 --delete did:key:z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi --no-announce
``` ```
Great, now we have communicated to the world about our car's defect. Great, now we have communicated to the world about our car's defect.
@ -78,9 +78,9 @@ But wait! We've found an important detail about the car's power requirements.
It will help whoever works on a fix. It will help whoever works on a fix.
``` ```
$ rad issue comment d185ee16a00bac874c0bcbc2a8ad80fdce5e1e61 --message 'The flux capacitor needs 1.21 Gigawatts' -q $ rad issue comment d185ee16a00bac874c0bcbc2a8ad80fdce5e1e61 --message 'The flux capacitor needs 1.21 Gigawatts' -q --no-announce
80ef590710edb64dfa57e8e940d6e4d0b0ae4217 80ef590710edb64dfa57e8e940d6e4d0b0ae4217
$ rad issue comment d185ee16a00bac874c0bcbc2a8ad80fdce5e1e61 --reply-to 80ef590710edb64dfa57e8e940d6e4d0b0ae4217 --message 'More power!' -q $ rad issue comment d185ee16a00bac874c0bcbc2a8ad80fdce5e1e61 --reply-to 80ef590710edb64dfa57e8e940d6e4d0b0ae4217 --message 'More power!' -q --no-announce
91009820ca0996d93b9afd5739a4d2158a2ec898 91009820ca0996d93b9afd5739a4d2158a2ec898
``` ```

View File

@ -36,7 +36,7 @@ $ rad patch show 193a2540ded82245b49971de8afc89a129502c6d
Once the patch is ready for review, we can use the `ready` command: Once the patch is ready for review, we can use the `ready` command:
``` ```
$ rad patch ready 193a2540ded82245b49971de8afc89a129502c6d $ rad patch ready 193a2540ded82245b49971de8afc89a129502c6d --no-announce
``` ```
``` ```
@ -60,7 +60,7 @@ If for whatever reason, it needed to go back into draft mode, we could use
the `--undo` flag: the `--undo` flag:
``` ```
$ rad patch ready --undo 193a2540ded82245b49971de8afc89a129502c6d $ rad patch ready --undo 193a2540ded82245b49971de8afc89a129502c6d --no-announce
$ rad patch show 193a2540ded82245b49971de8afc89a129502c6d $ rad patch show 193a2540ded82245b49971de8afc89a129502c6d
╭────────────────────────────────────────────────────╮ ╭────────────────────────────────────────────────────╮
│ Title Nothing yet │ │ Title Nothing yet │

View File

@ -46,7 +46,7 @@ Now, instead of using `git push` to update the patch, as we normally would,
we run: we run:
``` ```
$ rad patch update 8f5dcedc07a89928fd450bce1479f2559bcfd1d4 -m "Updated patch" $ rad patch update 8f5dcedc07a89928fd450bce1479f2559bcfd1d4 -m "Updated patch" --no-announce
74d453f93d81bb535ffa4ef65c46e5bd0a76015d 74d453f93d81bb535ffa4ef65c46e5bd0a76015d
``` ```

View File

@ -93,8 +93,8 @@ We can also label patches as well as assign DIDs to the patch to help
organise your workflow: organise your workflow:
``` ```
$ rad patch label 6ff4f09 --add fun $ rad patch label 6ff4f09 --add fun --no-announce
$ rad patch assign 6ff4f09 --add did:key:z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi $ rad patch assign 6ff4f09 --add did:key:z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi --no-announce
$ rad patch show 6ff4f09 $ rad patch show 6ff4f09
╭────────────────────────────────────────────────────╮ ╭────────────────────────────────────────────────────╮
│ Title Define power requirements │ │ Title Define power requirements │
@ -134,12 +134,12 @@ To rad://z42hL2jL4XNk6K8oHQaSWfMgCL7ji/z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkE
And let's leave a quick comment for our team: And let's leave a quick comment for our team:
``` ```
$ rad patch comment 6ff4f09 --message 'I cannot wait to get back to the 90s!' $ rad patch comment 6ff4f09 --message 'I cannot wait to get back to the 90s!' --no-announce
╭───────────────────────────────────────╮ ╭───────────────────────────────────────╮
│ z6MknSL…StBU8Vi (you) now f5b4613 │ │ z6MknSL…StBU8Vi (you) now f5b4613 │
│ I cannot wait to get back to the 90s! │ │ I cannot wait to get back to the 90s! │
╰───────────────────────────────────────╯ ╰───────────────────────────────────────╯
$ rad patch comment 6ff4f09 --message 'My favorite decade!' --reply-to f5b4613 -q $ rad patch comment 6ff4f09 --message 'My favorite decade!' --reply-to f5b4613 -q --no-announce
611df66ccb3803b604a59f2efa9a42d72256dd49 611df66ccb3803b604a59f2efa9a42d72256dd49
``` ```
@ -154,7 +154,7 @@ $ rad patch checkout 6ff4f09
We can also add a review verdict as such: We can also add a review verdict as such:
``` ```
$ rad patch review 6ff4f09 --accept --no-message $ rad patch review 6ff4f09 --accept --no-message --no-announce
✓ Patch 6ff4f09 accepted ✓ Patch 6ff4f09 accepted
``` ```
@ -186,7 +186,7 @@ $ rad patch show 6ff4f09
If you make a mistake on the patch description, you can always change it! If you make a mistake on the patch description, you can always change it!
``` ```
$ rad patch edit 6ff4f09 --message "Define power requirements" --message "Add requirements file" $ rad patch edit 6ff4f09 --message "Define power requirements" --message "Add requirements file" --no-announce
$ rad patch show 6ff4f09 $ rad patch show 6ff4f09
╭─────────────────────────────────────────────────────────────────────╮ ╭─────────────────────────────────────────────────────────────────────╮
│ Title Define power requirements │ │ Title Define power requirements │

View File

@ -70,7 +70,7 @@ Finally, we do a review of the patch by hunk. The output of this command should
match `git diff master -W100% -U5 --patience`: match `git diff master -W100% -U5 --patience`:
``` ```
$ rad patch review --patch -U5 52da8356aa9beec08e6943cb3c4063fa37f3241b $ rad patch review --patch -U5 52da8356aa9beec08e6943cb3c4063fa37f3241b --no-announce
diff --git a/.gitignore b/.gitignore diff --git a/.gitignore b/.gitignore
deleted file mode 100644 deleted file mode 100644
index 7937fb3..0000000 index 7937fb3..0000000
@ -116,7 +116,7 @@ rename to notes/INSTRUCTIONS.txt
Now let's accept these hunks one by one.. Now let's accept these hunks one by one..
``` ```
$ rad patch review --patch --accept --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b $ rad patch review --patch --accept --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b --no-announce
✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b ✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b
diff --git a/.gitignore b/.gitignore diff --git a/.gitignore b/.gitignore
deleted file mode 100644 deleted file mode 100644
@ -127,7 +127,7 @@ index 7937fb3..0000000
-*.draft -*.draft
``` ```
``` ```
$ rad patch review --patch --accept --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b $ rad patch review --patch --accept --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b --no-announce
✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b ✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b
diff --git a/DISCLAIMER.txt b/DISCLAIMER.txt diff --git a/DISCLAIMER.txt b/DISCLAIMER.txt
new file mode 100644 new file mode 100644
@ -138,7 +138,7 @@ index 0000000..2b5bd86
+All food is served as-is, with no warranty! +All food is served as-is, with no warranty!
``` ```
``` ```
$ rad patch review --patch --accept -U3 --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b $ rad patch review --patch --accept -U3 --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b --no-announce
✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b ✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b
diff --git a/MENU.txt b/MENU.txt diff --git a/MENU.txt b/MENU.txt
index 867958c..3af9741 100644 index 867958c..3af9741 100644
@ -153,7 +153,7 @@ index 867958c..3af9741 100644
[..] [..]
``` ```
``` ```
$ rad patch review --patch --accept -U3 --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b $ rad patch review --patch --accept -U3 --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b --no-announce
✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b ✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b
diff --git a/MENU.txt b/MENU.txt diff --git a/MENU.txt b/MENU.txt
index 4e2e828..3af9741 100644 index 4e2e828..3af9741 100644
@ -169,7 +169,7 @@ index 4e2e828..3af9741 100644
``` ```
``` ```
$ rad patch review --patch --accept --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b $ rad patch review --patch --accept --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b --no-announce
✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b ✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b
diff --git a/INSTRUCTIONS.txt b/notes/INSTRUCTIONS.txt diff --git a/INSTRUCTIONS.txt b/notes/INSTRUCTIONS.txt
similarity index 100% similarity index 100%
@ -178,7 +178,7 @@ rename to notes/INSTRUCTIONS.txt
``` ```
``` ```
$ rad patch review --patch --accept --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b $ rad patch review --patch --accept --hunk 1 52da8356aa9beec08e6943cb3c4063fa37f3241b --no-announce
✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b ✓ Loaded existing review ([..]) for patch 52da8356aa9beec08e6943cb3c4063fa37f3241b
✓ All hunks have been reviewed ✓ All hunks have been reviewed
``` ```

View File

@ -87,4 +87,5 @@ And let's leave a quick comment for our team:
``` ```
$ rad patch comment 3581e83ad18f5cdd806ab50fa11cfd5dd4e8ae1c --message 'I cannot wait to get back to the 90s!' -q $ rad patch comment 3581e83ad18f5cdd806ab50fa11cfd5dd4e8ae1c --message 'I cannot wait to get back to the 90s!' -q
b6711a58b45323f3ef2bb87cfb2b3b4d04c22a8b b6711a58b45323f3ef2bb87cfb2b3b4d04c22a8b
✓ Synced with 1 node(s)
``` ```

View File

@ -9,7 +9,6 @@ use radicle::cob::issue;
use radicle::cob::issue::{CloseReason, Issues, State}; use radicle::cob::issue::{CloseReason, Issues, State};
use radicle::cob::thread; use radicle::cob::thread;
use radicle::crypto::Signer; use radicle::crypto::Signer;
use radicle::node::Handle;
use radicle::prelude::Did; use radicle::prelude::Did;
use radicle::profile; use radicle::profile;
use radicle::storage; use radicle::storage;
@ -18,6 +17,7 @@ use radicle::Profile;
use radicle::{cob, Node}; use radicle::{cob, Node};
use crate::git::Rev; use crate::git::Rev;
use crate::node;
use crate::terminal as term; use crate::terminal as term;
use crate::terminal::args::{Args, Error, Help}; use crate::terminal::args::{Args, Error, Help};
use crate::terminal::format::Author; use crate::terminal::format::Author;
@ -401,7 +401,6 @@ pub fn run(options: Options, ctx: impl term::Context) -> anyhow::Result<()> {
| Operation::Label { .. } | Operation::Label { .. }
); );
let mut node = Node::new(profile.socket());
let mut issues = Issues::open(&repo)?; let mut issues = Issues::open(&repo)?;
match options.op { match options.op {
@ -528,11 +527,8 @@ pub fn run(options: Options, ctx: impl term::Context) -> anyhow::Result<()> {
} }
if announce { if announce {
match node.announce_refs(rid) { let mut node = Node::new(profile.socket());
Ok(_) => {} node::sync(rid, &mut node)?;
Err(e) if e.is_connection_err() => {}
Err(e) => return Err(e.into()),
}
} }
Ok(()) Ok(())

View File

@ -34,10 +34,11 @@ use anyhow::anyhow;
use radicle::cob::patch::PatchId; use radicle::cob::patch::PatchId;
use radicle::cob::{patch, Label}; use radicle::cob::{patch, Label};
use radicle::prelude::*;
use radicle::storage::git::transport; use radicle::storage::git::transport;
use radicle::{prelude::*, Node};
use crate::git::Rev; use crate::git::Rev;
use crate::node;
use crate::terminal as term; use crate::terminal as term;
use crate::terminal::args::{string, Args, Error, Help}; use crate::terminal::args::{string, Args, Error, Help};
use crate::terminal::patch::Message; use crate::terminal::patch::Message;
@ -134,6 +135,7 @@ Checkout options
Other options Other options
--[no-]announce Announce changes made to the network
-q, --quiet Quiet output -q, --quiet Quiet output
--help Print help --help Print help
"#, "#,
@ -249,6 +251,25 @@ pub enum Operation {
}, },
} }
impl Operation {
fn is_announce(&self) -> bool {
match self {
Operation::Update { .. }
| Operation::Archive { .. }
| Operation::Ready { .. }
| Operation::Delete { .. }
| Operation::Comment { .. }
| Operation::Review { .. }
| Operation::Assign { .. }
| Operation::Label { .. }
| Operation::Edit { .. }
| Operation::Redact { .. }
| Operation::Set { .. } => true,
Operation::Show { .. } | Operation::Checkout { .. } | Operation::List { .. } => false,
}
}
}
#[derive(Debug)] #[derive(Debug)]
pub struct Options { pub struct Options {
pub op: Operation, pub op: Operation,
@ -270,7 +291,7 @@ impl Args for Options {
let mut quiet = false; let mut quiet = false;
let mut authored = false; let mut authored = false;
let mut authors = vec![]; let mut authors = vec![];
let mut announce = false; let mut announce = true;
let mut patch_id = None; let mut patch_id = None;
let mut revision_id = None; let mut revision_id = None;
let mut message = Message::default(); let mut message = Message::default();
@ -604,6 +625,7 @@ pub fn run(options: Options, ctx: impl term::Context) -> anyhow::Result<()> {
let profile = ctx.profile()?; let profile = ctx.profile()?;
let repository = profile.storage.repository(id)?; let repository = profile.storage.repository(id)?;
let announce = options.announce && options.op.is_announce();
transport::local::register(profile.storage.clone()); transport::local::register(profile.storage.clone());
@ -720,5 +742,10 @@ pub fn run(options: Options, ctx: impl term::Context) -> anyhow::Result<()> {
radicle::rad::setup_patch_upstream(&patch_id, *patch.head(), &workdir, true)?; radicle::rad::setup_patch_upstream(&patch_id, *patch.head(), &workdir, true)?;
} }
} }
if announce {
let mut node = Node::new(profile.socket());
node::sync(id, &mut node)?;
}
Ok(()) Ok(())
} }

View File

@ -3,6 +3,7 @@
#![allow(clippy::too_many_arguments)] #![allow(clippy::too_many_arguments)]
pub mod commands; pub mod commands;
pub mod git; pub mod git;
pub mod node;
pub mod pager; pub mod pager;
pub mod project; pub mod project;
pub mod terminal; pub mod terminal;

51
radicle-cli/src/node.rs Normal file
View File

@ -0,0 +1,51 @@
use std::time::Duration;
use radicle::identity::Id;
use radicle::node;
use radicle::node::Handle as _;
use radicle::Node;
use crate::terminal as term;
pub fn sync(rid: Id, node: &mut Node) -> anyhow::Result<()> {
match sync_(rid, node) {
Ok(()) => Ok(()),
Err(e) if e.is_connection_err() => {
term::hint("Node is stopped. To announce changes to the network, start it with `rad node start`.");
Ok(())
}
Err(e) => Err(e.into()),
}
}
/// Sync with the network.
fn sync_(rid: Id, node: &mut Node) -> Result<(), radicle::node::Error> {
let seeds = node.seeds(rid)?;
let connected = seeds.connected().map(|s| s.nid).collect::<Vec<_>>();
if connected.is_empty() {
term::info!("Not connected to any seeds.");
return Ok(());
}
let mut spinner = term::spinner(format!("Syncing with {} node(s)..", connected.len()));
let result = node.announce(
rid,
connected,
Duration::from_secs(9),
|event| match event {
node::AnnounceEvent::Announced => {}
node::AnnounceEvent::RefsSynced { remote } => {
spinner.message(format!("Synced with {remote}.."));
}
},
)?;
if result.synced.is_empty() {
spinner.failed();
} else {
spinner.message(format!("Synced with {} node(s)", result.synced.len()));
spinner.finish();
}
Ok(())
}