feat(trello): add command 'trello attachement get'
This commit is contained in:
parent
3f411f4b09
commit
0e8b2e8720
6 changed files with 220 additions and 15 deletions
|
@ -72,7 +72,7 @@ As part of building the import server, the following commands exercise each oper
|
||||||
- [x] trello board get - includes list of stacks
|
- [x] trello board get - includes list of stacks
|
||||||
- [x] trello stack get - includes list of cards
|
- [x] trello stack get - includes list of cards
|
||||||
- [x] trello card get - includes list of attachments
|
- [x] trello card get - includes list of attachments
|
||||||
- [ ] trello attachment get
|
- [x] trello attachment get - includes download url
|
||||||
- [ ] nextcloud deck get (was board list)
|
- [ ] nextcloud deck get (was board list)
|
||||||
- [ ] nextcloud board get (was stack list)
|
- [ ] nextcloud board get (was stack list)
|
||||||
- [ ] nextcloud stack get (was card list)
|
- [ ] nextcloud stack get (was card list)
|
||||||
|
|
78
src/tests/responses/trello-attachment-get.json
Normal file
78
src/tests/responses/trello-attachment-get.json
Normal file
|
@ -0,0 +1,78 @@
|
||||||
|
{
|
||||||
|
"id": "65ad94875aed24f70ecdd037",
|
||||||
|
"bytes": 184198,
|
||||||
|
"date": "2019-01-02T22:47:17.325Z",
|
||||||
|
"edgeColor": "#047cbc",
|
||||||
|
"idMember": "65ad94875aed24f70ecdd038",
|
||||||
|
"isUpload": true,
|
||||||
|
"mimeType": null,
|
||||||
|
"name": "Backlog.png",
|
||||||
|
"previews": [
|
||||||
|
{
|
||||||
|
"id": "65ad94875aed24f70ecdd039",
|
||||||
|
"_id": "65ad94875aed24f70ecdd039",
|
||||||
|
"scaled": false,
|
||||||
|
"url": "https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/previews/65ad94875aed24f70ecdd039/download/Backlog.png",
|
||||||
|
"bytes": 1064,
|
||||||
|
"height": 50,
|
||||||
|
"width": 70
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "65ad94875aed24f70ecdd03a",
|
||||||
|
"_id": "65ad94875aed24f70ecdd03a",
|
||||||
|
"scaled": false,
|
||||||
|
"url": "https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/previews/65ad94875aed24f70ecdd03a/download/Backlog.png",
|
||||||
|
"bytes": 4859,
|
||||||
|
"height": 150,
|
||||||
|
"width": 250
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "65ad94875aed24f70ecdd03b",
|
||||||
|
"_id": "65ad94875aed24f70ecdd03b",
|
||||||
|
"scaled": true,
|
||||||
|
"url": "https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/previews/65ad94875aed24f70ecdd03b/download/Backlog.png",
|
||||||
|
"bytes": 2721,
|
||||||
|
"height": 66,
|
||||||
|
"width": 150
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "65ad94875aed24f70ecdd03c",
|
||||||
|
"_id": "65ad94875aed24f70ecdd03c",
|
||||||
|
"scaled": true,
|
||||||
|
"url": "https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/previews/65ad94875aed24f70ecdd03c/download/Backlog.png",
|
||||||
|
"bytes": 5874,
|
||||||
|
"height": 132,
|
||||||
|
"width": 300
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "65ad94875aed24f70ecdd03d",
|
||||||
|
"_id": "65ad94875aed24f70ecdd03d",
|
||||||
|
"scaled": true,
|
||||||
|
"url": "https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/previews/65ad94875aed24f70ecdd03d/download/Backlog.png",
|
||||||
|
"bytes": 12946,
|
||||||
|
"height": 264,
|
||||||
|
"width": 600
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "65ad94875aed24f70ecdd03e",
|
||||||
|
"_id": "65ad94875aed24f70ecdd03e",
|
||||||
|
"scaled": true,
|
||||||
|
"url": "https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/previews/65ad94875aed24f70ecdd03e/download/Backlog.png",
|
||||||
|
"bytes": 30062,
|
||||||
|
"height": 527,
|
||||||
|
"width": 1200
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "65ad94875aed24f70ecdd03f",
|
||||||
|
"_id": "65ad94875aed24f70ecdd03f",
|
||||||
|
"scaled": true,
|
||||||
|
"url": "https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/previews/65ad94875aed24f70ecdd03f/download/Backlog.png",
|
||||||
|
"bytes": 184198,
|
||||||
|
"height": 3558,
|
||||||
|
"width": 8100
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"url": "https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/download/Backlog.png",
|
||||||
|
"pos": 49152,
|
||||||
|
"fileName": "Backlog.png"
|
||||||
|
}
|
45
src/trello/attachment.rs
Normal file
45
src/trello/attachment.rs
Normal file
|
@ -0,0 +1,45 @@
|
||||||
|
//
|
||||||
|
use clap::Parser;
|
||||||
|
use color_eyre::Result;
|
||||||
|
|
||||||
|
use crate::{execute::Execute, p, FullCtx};
|
||||||
|
|
||||||
|
use super::model::{TrelloAttachmentId, TrelloCardId};
|
||||||
|
|
||||||
|
#[derive(Parser, Debug)]
|
||||||
|
pub(crate) enum TrelloAttachmentCommand {
|
||||||
|
Get {
|
||||||
|
#[clap(long, action = clap::ArgAction::SetTrue)]
|
||||||
|
dump: bool,
|
||||||
|
|
||||||
|
card_id: String,
|
||||||
|
attachment_id: String,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Execute for TrelloAttachmentCommand {
|
||||||
|
async fn execute(self, ctx: FullCtx) -> Result<()> {
|
||||||
|
match self {
|
||||||
|
Self::Get {
|
||||||
|
dump,
|
||||||
|
card_id,
|
||||||
|
attachment_id,
|
||||||
|
} => {
|
||||||
|
let api_result = ctx
|
||||||
|
.trello_client()
|
||||||
|
.card_attachment(
|
||||||
|
&TrelloCardId::new(card_id),
|
||||||
|
&TrelloAttachmentId::new(attachment_id),
|
||||||
|
)
|
||||||
|
.await;
|
||||||
|
if dump {
|
||||||
|
p!(ctx.prt, "{}", api_result.text);
|
||||||
|
} else {
|
||||||
|
let attachment = api_result.result?;
|
||||||
|
p!(ctx.prt, "{}:{}", attachment.name, attachment.url);
|
||||||
|
}
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -3,6 +3,7 @@ use std::collections::HashMap;
|
||||||
|
|
||||||
use kxio::net::{Net, ReqBuilder};
|
use kxio::net::{Net, ReqBuilder};
|
||||||
|
|
||||||
|
use crate::trello::model::{TrelloAttachment, TrelloAttachmentId};
|
||||||
use crate::{
|
use crate::{
|
||||||
api_result::APIResult,
|
api_result::APIResult,
|
||||||
f, s,
|
f, s,
|
||||||
|
@ -84,18 +85,18 @@ impl<'ctx> TrelloClient<'ctx> {
|
||||||
.await
|
.await
|
||||||
}
|
}
|
||||||
|
|
||||||
// // https://developer.atlassian.com/cloud/trello/rest/api-group-cards/#api-cards-id-attachments-idattachment-get
|
// https://developer.atlassian.com/cloud/trello/rest/api-group-cards/#api-cards-id-attachments-idattachment-get
|
||||||
// pub(crate) async fn card_attachment(
|
pub(crate) async fn card_attachment(
|
||||||
// &self,
|
&self,
|
||||||
// card_id: &TrelloCardId,
|
card_id: &TrelloCardId,
|
||||||
// attachment_id: &TrelloAttachmentId,
|
attachment_id: &TrelloAttachmentId,
|
||||||
// ) -> APIResult<TrelloAttachment> {
|
) -> APIResult<TrelloAttachment> {
|
||||||
// self.request(
|
self.request(
|
||||||
// f!("/cards/{card_id}/attachments/{attachment_id}"),
|
f!("/cards/{card_id}/attachments/{attachment_id}"),
|
||||||
// |net, url| net.get(url),
|
|net, url| net.get(url),
|
||||||
// )
|
)
|
||||||
// .await
|
.await
|
||||||
// }
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl TrelloClient<'_> {
|
impl TrelloClient<'_> {
|
||||||
|
|
|
@ -4,6 +4,7 @@ use clap::Parser;
|
||||||
use crate::{
|
use crate::{
|
||||||
execute::Execute,
|
execute::Execute,
|
||||||
trello::{
|
trello::{
|
||||||
|
attachment::TrelloAttachmentCommand,
|
||||||
board::TrelloBoardCommand,
|
board::TrelloBoardCommand,
|
||||||
card::TrelloCardCommand,
|
card::TrelloCardCommand,
|
||||||
member::TrelloMemberCommand,
|
member::TrelloMemberCommand,
|
||||||
|
@ -16,6 +17,7 @@ use crate::{
|
||||||
FullCtx,
|
FullCtx,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
pub(crate) mod attachment;
|
||||||
pub(crate) mod board;
|
pub(crate) mod board;
|
||||||
pub(crate) mod card;
|
pub(crate) mod card;
|
||||||
pub(crate) mod client;
|
pub(crate) mod client;
|
||||||
|
@ -39,6 +41,9 @@ pub(crate) enum TrelloCommand {
|
||||||
|
|
||||||
#[clap(subcommand)]
|
#[clap(subcommand)]
|
||||||
Card(TrelloCardCommand),
|
Card(TrelloCardCommand),
|
||||||
|
|
||||||
|
#[clap(subcommand)]
|
||||||
|
Attachment(TrelloAttachmentCommand),
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Execute for TrelloCommand {
|
impl Execute for TrelloCommand {
|
||||||
|
@ -48,6 +53,7 @@ impl Execute for TrelloCommand {
|
||||||
Self::Board(cmd) => cmd.execute(ctx).await,
|
Self::Board(cmd) => cmd.execute(ctx).await,
|
||||||
Self::Stack(cmd) => cmd.execute(ctx).await,
|
Self::Stack(cmd) => cmd.execute(ctx).await,
|
||||||
Self::Card(cmd) => cmd.execute(ctx).await,
|
Self::Card(cmd) => cmd.execute(ctx).await,
|
||||||
|
Self::Attachment(cmd) => cmd.execute(ctx).await,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,12 +1,12 @@
|
||||||
//
|
//
|
||||||
use kxio::net::MockNet;
|
use kxio::net::{MockNet, StatusCode};
|
||||||
use kxio::net::StatusCode;
|
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
execute::Execute,
|
execute::Execute,
|
||||||
s,
|
s,
|
||||||
tests::given,
|
tests::given,
|
||||||
trello::{
|
trello::{
|
||||||
|
attachment::TrelloAttachmentCommand,
|
||||||
card::TrelloCardCommand,
|
card::TrelloCardCommand,
|
||||||
model::{
|
model::{
|
||||||
board::{TrelloBoard, TrelloBoards as _},
|
board::{TrelloBoard, TrelloBoards as _},
|
||||||
|
@ -178,4 +178,79 @@ mod commands {
|
||||||
.expect("mock request");
|
.expect("mock request");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mod attachments {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
mod get {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[tokio::test]
|
||||||
|
async fn get() {
|
||||||
|
//given
|
||||||
|
let mock_net = kxio::net::mock();
|
||||||
|
|
||||||
|
prep_mock_get(&mock_net);
|
||||||
|
|
||||||
|
// let fs = given::a_filesystem();
|
||||||
|
let ctx = given::a_full_context(mock_net);
|
||||||
|
let prt = ctx.prt.clone();
|
||||||
|
let prt = prt.as_test().unwrap();
|
||||||
|
let command =
|
||||||
|
Command::Trello(TrelloCommand::Attachment(TrelloAttachmentCommand::Get {
|
||||||
|
dump: false,
|
||||||
|
card_id: s!("65ad94865aed24f70ecdcebb"),
|
||||||
|
attachment_id: s!("65ad94875aed24f70ecdd037"),
|
||||||
|
}));
|
||||||
|
|
||||||
|
//when
|
||||||
|
command.execute(ctx).await;
|
||||||
|
|
||||||
|
//then
|
||||||
|
let output = prt.output();
|
||||||
|
assert_eq!(output, s!("Backlog.png:https://trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037/download/Backlog.png\n"));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[tokio::test]
|
||||||
|
async fn get_dump() {
|
||||||
|
//given
|
||||||
|
let mock_net = kxio::net::mock();
|
||||||
|
|
||||||
|
prep_mock_get(&mock_net);
|
||||||
|
|
||||||
|
// let fs = given::a_filesystem();
|
||||||
|
let ctx = given::a_full_context(mock_net);
|
||||||
|
let prt = ctx.prt.clone();
|
||||||
|
let prt = prt.as_test().unwrap();
|
||||||
|
let command =
|
||||||
|
Command::Trello(TrelloCommand::Attachment(TrelloAttachmentCommand::Get {
|
||||||
|
dump: true,
|
||||||
|
card_id: s!("65ad94865aed24f70ecdcebb"),
|
||||||
|
attachment_id: s!("65ad94875aed24f70ecdd037"),
|
||||||
|
}));
|
||||||
|
|
||||||
|
//when
|
||||||
|
command.execute(ctx).await;
|
||||||
|
|
||||||
|
//then
|
||||||
|
let output = prt.output();
|
||||||
|
assert_eq!(
|
||||||
|
output.trim(),
|
||||||
|
include_str!("../tests/responses/trello-attachment-get.json").trim()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn prep_mock_get(mock_net: &MockNet) {
|
||||||
|
mock_net
|
||||||
|
.on()
|
||||||
|
.get("https://api.trello.com/1/cards/65ad94865aed24f70ecdcebb/attachments/65ad94875aed24f70ecdd037")
|
||||||
|
.header("authorization", "OAuth oauth_consumer_key=\"trello-api-key\", oauth_token=\"trello-api-secret\"")
|
||||||
|
.header("accept", "application/json")
|
||||||
|
.header("content-type", "application/json")
|
||||||
|
.respond(StatusCode::OK)
|
||||||
|
.body(include_str!("../tests/responses/trello-attachment-get.json"))
|
||||||
|
.expect("mock request");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue