cli: Make patch editable

Add `rad patch edit` to make the patch description editable.
This commit is contained in:
Slack Coder 2023-05-01 13:38:24 -05:00 committed by Alexis Sellier
parent c20421b0c6
commit 6bedb1256c
No known key found for this signature in database
5 changed files with 98 additions and 12 deletions

View File

@ -140,3 +140,25 @@ $ rad patch show de3096d
│ ✓ accepted by z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi (you) [ ... ]│
╰─────────────────────────────────────────────────────────────────────────────────────────╯
```
If you make a mistake on the patch description, you can always change it!
```
$ rad patch edit de3096d --message "Define power requirements" --message "Add requirements file"
$ rad patch show de3096d
╭─────────────────────────────────────────────────────────────────────────────────────────╮
│ Title Define power requirements │
│ Patch de3096d5cc422136016ac210b870bfa9d0f11481 │
│ Author did:key:z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi │
│ Head 27857ec9eb04c69cacab516e8bf4b5fd36090f66 │
│ Branches flux-capacitor-power, patch/de3096d │
│ Commits ahead 2, behind 0 │
│ Status open │
│ │
│ Add requirements file │
├─────────────────────────────────────────────────────────────────────────────────────────┤
│ ● opened by did:key:z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi (you) [ ... ]│
│ ↑ updated to d00f978a43a255c7f2f9f23d39b555d103900c6d (27857ec) [ ... ]│
│ ✓ accepted by z6MknSLrJoTcukLrE435hVNQT4JUhbvWLX4kUzqkEStBU8Vi (you) [ ... ]│
╰─────────────────────────────────────────────────────────────────────────────────────────╯
```

View File

@ -8,6 +8,8 @@ mod common;
mod create;
#[path = "patch/delete.rs"]
mod delete;
#[path = "patch/edit.rs"]
mod edit;
#[path = "patch/list.rs"]
mod list;
#[path = "patch/ready.rs"]
@ -48,11 +50,16 @@ Usage
rad patch checkout <patch-id> [<option>...]
rad patch delete <patch-id> [<option>...]
rad patch ready <patch-id> [--undo] [<option>...]
rad patch edit <patch-id> [<option>...]
Show options
-p, --patch Show the actual patch diff
Edit options
-m, --message [<string>] Provide a comment message to the patch or revision (default: prompt)
Open/Update options
--draft Open patch in draft mode
@ -91,6 +98,7 @@ pub enum OperationName {
Ready,
#[default]
List,
Edit,
}
#[derive(Debug)]
@ -125,6 +133,10 @@ pub enum Operation {
List {
filter: Option<patch::State>,
},
Edit {
patch_id: Rev,
message: Message,
},
}
#[derive(Debug)]
@ -240,6 +252,7 @@ impl Args for Options {
"c" | "checkout" => op = Some(OperationName::Checkout),
"a" | "archive" => op = Some(OperationName::Archive),
"y" | "ready" => op = Some(OperationName::Ready),
"e" | "edit" => op = Some(OperationName::Edit),
unknown => anyhow::bail!("unknown operation '{}'", unknown),
},
Value(val)
@ -251,6 +264,7 @@ impl Args for Options {
Some(OperationName::Archive),
Some(OperationName::Ready),
Some(OperationName::Checkout),
Some(OperationName::Edit),
]
.contains(&op) =>
{
@ -290,6 +304,10 @@ impl Args for Options {
patch_id: patch_id.ok_or_else(|| anyhow!("a patch must be provided"))?,
undo,
},
OperationName::Edit => Operation::Edit {
patch_id: patch_id.ok_or_else(|| anyhow!("a patch must be provided"))?,
message,
},
};
Ok((
@ -376,6 +394,10 @@ pub fn run(options: Options, ctx: impl term::Context) -> anyhow::Result<()> {
let patch_id = patch_id.resolve(&repository.backend)?;
checkout::run(&repository, &workdir, &patch_id)?;
}
Operation::Edit { patch_id, message } => {
let patch_id = patch_id.resolve(&repository.backend)?;
edit::run(&repository, &profile, &patch_id, message)?;
}
}
Ok(())
}

View File

@ -11,6 +11,18 @@ use crate::terminal::args::Error;
use super::Options;
pub const PATCH_MSG: &str = r#"
<!--
Please enter a patch message for your changes. An empty
message aborts the patch proposal.
The first line is the patch title. The patch description
follows, and must be separated with a blank line, just
like a commit message. Markdown is supported in the title
and description.
-->
"#;
/// Give the name of the branch or an appropriate error.
#[inline]
pub fn branch_name<'a>(branch: &'a git::raw::Branch) -> anyhow::Result<&'a str> {

View File

@ -12,18 +12,6 @@ use crate::terminal as term;
use super::common::*;
use super::Options;
const PATCH_MSG: &str = r#"
<!--
Please enter a patch message for your changes. An empty
message aborts the patch proposal.
The first line is the patch title. The patch description
follows, and must be separated with a blank line, just
like a commit message. Markdown is supported in the title
and description.
-->
"#;
pub fn handle_patch_message(
message: term::patch::Message,
storage: &Repository,

View File

@ -0,0 +1,42 @@
use super::common::*;
use super::*;
use radicle::cob::patch;
use radicle::prelude::*;
use radicle::storage::git::Repository;
pub fn run(
repository: &Repository,
profile: &Profile,
patch_id: &PatchId,
message: term::patch::Message,
) -> anyhow::Result<()> {
let signer = term::signer(profile)?;
let mut patches = patch::Patches::open(repository)?;
let Ok(mut patch) = patches.get_mut(patch_id) else {
anyhow::bail!("Patch `{patch_id}` not found");
};
let title = patch.title();
let description = patch.description();
let message = message.get(&format!("{title}\n\n{description}\n\n{PATCH_MSG}"))?;
let message = message.replace(PATCH_MSG.trim(), ""); // Delete help message.
let (title, description) = message.split_once("\n\n").unwrap_or((&message, ""));
let (title, description) = (title.trim(), description.trim());
if title.is_empty() {
anyhow::bail!("a patch title must be provided");
} else if title == patch.title() && description == patch.description() {
// Nothing to do
return Ok(());
}
patch.edit(
title.to_string(),
description.to_string(),
patch.target(),
&signer,
)?;
Ok(())
}