feat(nextcloud): add command 'nextcloud board labels'
This commit is contained in:
parent
336a5945a4
commit
bb0f2a905f
6 changed files with 223 additions and 8 deletions
|
@ -7,6 +7,11 @@ use crate::{p, FullCtx};
|
|||
|
||||
#[derive(Parser, Debug)]
|
||||
pub enum NextcloudBoardCommand {
|
||||
Labels {
|
||||
#[clap(long, action = clap::ArgAction::SetTrue)]
|
||||
dump: bool,
|
||||
board_id: i64,
|
||||
},
|
||||
Get {
|
||||
#[clap(long, action = clap::ArgAction::SetTrue)]
|
||||
dump: bool,
|
||||
|
@ -17,6 +22,22 @@ pub enum NextcloudBoardCommand {
|
|||
impl Execute for NextcloudBoardCommand {
|
||||
async fn execute(&self, ctx: &FullCtx) -> color_eyre::Result<()> {
|
||||
match self {
|
||||
Self::Labels { dump, board_id } => {
|
||||
let api_result = ctx
|
||||
.deck_client()
|
||||
.get_board(NextcloudBoardId::new(*board_id))
|
||||
.await;
|
||||
if *dump {
|
||||
p!(ctx.prt, "{}", api_result.text);
|
||||
} else {
|
||||
let mut labels = api_result.result?.labels;
|
||||
labels.sort_by(|a, b| a.title.cmp(&b.title));
|
||||
labels.into_iter().for_each(|label| {
|
||||
p!(ctx.prt, "{}:{}:{}:{}", board_id, label.id, label.color, label.title);
|
||||
});
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
Self::Get { dump, board_id } => {
|
||||
let api_result = ctx
|
||||
.deck_client()
|
||||
|
|
|
@ -119,6 +119,11 @@ impl<'ctx> DeckClient<'ctx> {
|
|||
self.request("boards", |net, url| net.get(url)).await
|
||||
}
|
||||
|
||||
pub(crate) async fn get_board(&self, board_id: NextcloudBoardId) -> APIResult<Board> {
|
||||
self.request(f!("boards/{board_id}"), |net, url| net.get(url))
|
||||
.await
|
||||
}
|
||||
|
||||
pub(crate) async fn get_stacks(&self, board_id: NextcloudBoardId) -> APIResult<Vec<Stack>> {
|
||||
self.request(f!("boards/{board_id}/stacks"), |net, url| net.get(url))
|
||||
.await
|
||||
|
|
85
src/nextcloud/tests/board/labels.rs
Normal file
85
src/nextcloud/tests/board/labels.rs
Normal file
|
@ -0,0 +1,85 @@
|
|||
//
|
||||
use super::*;
|
||||
|
||||
#[rstest::fixture]
|
||||
fn board_id() -> NextcloudBoardId {
|
||||
NextcloudBoardId::new(1)
|
||||
}
|
||||
|
||||
#[rstest::fixture]
|
||||
fn ctx() -> FullCtx {
|
||||
let fs = given::a_filesystem();
|
||||
|
||||
let nextcloud_config = given::a_nextcloud_config();
|
||||
|
||||
let hostname = &nextcloud_config.hostname;
|
||||
let board_id = board_id();
|
||||
|
||||
let mock_net = given::a_network();
|
||||
mock_net
|
||||
.on()
|
||||
.get(crate::f!(
|
||||
"{hostname}/index.php/apps/deck/api/v1.0/boards/{board_id}",
|
||||
))
|
||||
.respond(StatusCode::OK)
|
||||
.body(include_str!(
|
||||
"../../../tests/responses/nextcloud-board-labels.json"
|
||||
))
|
||||
.expect("mock request");
|
||||
|
||||
given::a_full_context(fs, mock_net)
|
||||
}
|
||||
|
||||
#[rstest::rstest]
|
||||
#[test_log::test(tokio::test)]
|
||||
async fn dump(ctx: FullCtx, board_id: NextcloudBoardId) {
|
||||
//given
|
||||
let prt = ctx.prt.clone();
|
||||
let prt = prt.as_test().unwrap();
|
||||
|
||||
//when
|
||||
Command::Nextcloud(NextcloudCommand::Board(NextcloudBoardCommand::Labels {
|
||||
dump: true,
|
||||
board_id: board_id.into(),
|
||||
}))
|
||||
.execute(&ctx)
|
||||
.await
|
||||
.expect("execute");
|
||||
|
||||
//then
|
||||
let output = prt.output();
|
||||
assert_eq!(
|
||||
output.trim(),
|
||||
include_str!("../../../tests/responses/nextcloud-board-labels.json").trim()
|
||||
);
|
||||
}
|
||||
|
||||
#[rstest::rstest]
|
||||
#[test_log::test(tokio::test)]
|
||||
async fn no_dump(ctx: FullCtx, board_id: NextcloudBoardId) {
|
||||
//given
|
||||
let prt = ctx.prt.clone();
|
||||
let prt = prt.as_test().unwrap();
|
||||
|
||||
//when
|
||||
Command::Nextcloud(NextcloudCommand::Board(NextcloudBoardCommand::Labels {
|
||||
dump: false,
|
||||
board_id: board_id.into(),
|
||||
}))
|
||||
.execute(&ctx)
|
||||
.await
|
||||
.expect("execute");
|
||||
|
||||
//then
|
||||
let output = prt.output();
|
||||
assert_eq!(
|
||||
output.trim(),
|
||||
[
|
||||
"1:3:FF7A66:Action needed",
|
||||
"1:1:31CC7C:Finished",
|
||||
"1:4:F1DB50:Later",
|
||||
"1:2:317CCC:To review"
|
||||
]
|
||||
.join("\n")
|
||||
);
|
||||
}
|
|
@ -2,3 +2,4 @@
|
|||
use super::*;
|
||||
|
||||
mod get;
|
||||
mod labels;
|
|
@ -8,24 +8,23 @@ use kxio::{
|
|||
use pretty_assertions::assert_eq as assert_peq;
|
||||
use serde_json::json;
|
||||
|
||||
use crate::execute::Execute;
|
||||
use crate::nextcloud::card::NextcloudCardCommand;
|
||||
use crate::nextcloud::deck::NextcloudDeckCommand;
|
||||
use crate::nextcloud::NextcloudCommand;
|
||||
use crate::Command;
|
||||
use crate::{
|
||||
execute::Execute,
|
||||
nextcloud::{
|
||||
board::NextcloudBoardCommand,
|
||||
card::NextcloudCardCommand,
|
||||
deck::NextcloudDeckCommand,
|
||||
model::{
|
||||
Card, Label, NextcloudBoardId, NextcloudCardId, NextcloudCardTitle, NextcloudETag,
|
||||
NextcloudHostname, NextcloudLabelId, NextcloudOrder, NextcloudPassword,
|
||||
NextcloudStackId, NextcloudStackTitle, NextcloudUsername, Stack,
|
||||
},
|
||||
NextcloudConfig,
|
||||
stack::NextcloudStackCommand,
|
||||
NextcloudCommand, NextcloudConfig,
|
||||
},
|
||||
s,
|
||||
tests::given,
|
||||
trello::TrelloConfig,
|
||||
AppConfig, FullCtx,
|
||||
AppConfig, Command, FullCtx,
|
||||
};
|
||||
|
||||
mod board;
|
||||
|
|
104
src/tests/responses/nextcloud-board-labels.json
Normal file
104
src/tests/responses/nextcloud-board-labels.json
Normal file
|
@ -0,0 +1,104 @@
|
|||
{
|
||||
"id": 1,
|
||||
"title": "Personal Board",
|
||||
"owner": {
|
||||
"primaryKey": "pcampbell",
|
||||
"uid": "pcampbell",
|
||||
"displayname": "Paul Campbell",
|
||||
"type": 0
|
||||
},
|
||||
"color": "0087C5",
|
||||
"archived": false,
|
||||
"labels": [
|
||||
{
|
||||
"id": 1,
|
||||
"title": "Finished",
|
||||
"color": "31CC7C",
|
||||
"boardId": 1,
|
||||
"cardId": null,
|
||||
"lastModified": 1670965629,
|
||||
"ETag": "983f87848dc9c18d0aee63e7ee0fc83f"
|
||||
},
|
||||
{
|
||||
"id": 2,
|
||||
"title": "To review",
|
||||
"color": "317CCC",
|
||||
"boardId": 1,
|
||||
"cardId": null,
|
||||
"lastModified": 1670965629,
|
||||
"ETag": "983f87848dc9c18d0aee63e7ee0fc83f"
|
||||
},
|
||||
{
|
||||
"id": 3,
|
||||
"title": "Action needed",
|
||||
"color": "FF7A66",
|
||||
"boardId": 1,
|
||||
"cardId": null,
|
||||
"lastModified": 1670965629,
|
||||
"ETag": "983f87848dc9c18d0aee63e7ee0fc83f"
|
||||
},
|
||||
{
|
||||
"id": 4,
|
||||
"title": "Later",
|
||||
"color": "F1DB50",
|
||||
"boardId": 1,
|
||||
"cardId": null,
|
||||
"lastModified": 1670965629,
|
||||
"ETag": "983f87848dc9c18d0aee63e7ee0fc83f"
|
||||
}
|
||||
],
|
||||
"acl": [],
|
||||
"permissions": {
|
||||
"PERMISSION_READ": true,
|
||||
"PERMISSION_EDIT": true,
|
||||
"PERMISSION_MANAGE": true,
|
||||
"PERMISSION_SHARE": true
|
||||
},
|
||||
"users": [
|
||||
{
|
||||
"primaryKey": "pcampbell",
|
||||
"uid": "pcampbell",
|
||||
"displayname": "Paul Campbell",
|
||||
"type": 0
|
||||
}
|
||||
],
|
||||
"stacks": [
|
||||
{
|
||||
"id": 3,
|
||||
"title": "Done",
|
||||
"boardId": 1,
|
||||
"deletedAt": 0,
|
||||
"lastModified": 1733515991,
|
||||
"order": 2,
|
||||
"ETag": "dda386b3b247d7b4bd8917e19d38c01b"
|
||||
},
|
||||
{
|
||||
"id": 1,
|
||||
"title": "To do",
|
||||
"boardId": 1,
|
||||
"deletedAt": 0,
|
||||
"lastModified": 1734639912,
|
||||
"order": 0,
|
||||
"ETag": "72a19db972245af551058eb5506adf68"
|
||||
},
|
||||
{
|
||||
"id": 2,
|
||||
"title": "Doing",
|
||||
"boardId": 1,
|
||||
"deletedAt": 0,
|
||||
"lastModified": 1733695323,
|
||||
"order": 1,
|
||||
"ETag": "9de45fc7d68507f1eaef462e90e6414c"
|
||||
}
|
||||
],
|
||||
"activeSessions": [
|
||||
"pcampbell"
|
||||
],
|
||||
"deletedAt": 0,
|
||||
"lastModified": 1734639912,
|
||||
"settings": {
|
||||
"notify-due": "assigned",
|
||||
"calendar": true
|
||||
},
|
||||
"ETag": "72a19db972245af551058eb5506adf68"
|
||||
}
|
Loading…
Reference in a new issue