From 0b3378a91d48cc9b06b83502a1b200e09dda8dd1 Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Mon, 16 Nov 2020 02:30:42 +0900 Subject: [PATCH 01/11] v2.0.0 --- Cargo.lock | 2 +- Cargo.toml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index ef23692..a0d6fe1 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -240,7 +240,7 @@ dependencies = [ [[package]] name = "colmsg" -version = "1.0.0" +version = "2.0.0" dependencies = [ "ansi_colours", "ansi_term 0.12.1", diff --git a/Cargo.toml b/Cargo.toml index 082e091..8bf7417 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "colmsg" -version = "1.0.0" +version = "2.0.0" authors = ["proshunsuke "] categories = ["command-line-utilities"] description="'欅坂46/日向坂46 メッセージ'アプリのメッセージをPCに保存します." From 652677f1de0309d1798f87088d8e0f046ef121fb Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Thu, 12 Nov 2020 00:35:43 +0900 Subject: [PATCH 02/11] =?UTF-8?q?=E3=83=9E=E3=82=A4=E3=83=8A=E3=83=BC?= =?UTF-8?q?=E3=83=90=E3=83=BC=E3=82=B8=E3=83=A7=E3=83=B3=E3=81=8C2.1?= =?UTF-8?q?=E3=81=AB=E5=A4=89=E3=82=8F=E3=81=A3=E3=81=A6=E3=81=84=E3=81=9F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/http/client.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/http/client.rs b/src/http/client.rs index 011ef15..925e8bc 100644 --- a/src/http/client.rs +++ b/src/http/client.rs @@ -78,7 +78,7 @@ impl Client { fn insert_headers(&self, mut header: HeaderMap) -> Result { header.insert(ACCEPT, "application/json".parse()?); header.insert(CONTENT_TYPE, "application/json".parse()?); - header.insert("X-Talk-App-ID", "jp.co.sonymusic.communication.keyakizaka 2.0".parse()?); + header.insert("X-Talk-App-ID", "jp.co.sonymusic.communication.keyakizaka 2.1".parse()?); header.insert(ACCEPT_LANGUAGE, "ja-JP".parse()?); header.insert(USER_AGENT, "Dalvik/2.1.0 (Linux; U; Android 6.0; Samsung Galaxy S7 for keyaki messages Build/MRA58K)".parse()?); header.insert(CONNECTION, "Keep-Alive".parse()?); From 6ed7c5ba76c255e398f78c967d95bf7942cbecc5 Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Mon, 16 Nov 2020 02:18:32 +0900 Subject: [PATCH 03/11] =?UTF-8?q?=E6=AB=BB=E5=9D=8246=E3=83=A1=E3=83=83?= =?UTF-8?q?=E3=82=BB=E3=83=BC=E3=82=B8=E3=81=A8=E6=97=A5=E5=90=91=E5=9D=82?= =?UTF-8?q?46=E3=83=A1=E3=83=83=E3=82=BB=E3=83=BC=E3=82=B8=E3=81=AB?= =?UTF-8?q?=E5=88=A5=E3=82=8C=E3=81=9F=E3=81=93=E3=81=A8=E3=81=AB=E3=82=88?= =?UTF-8?q?=E3=82=8B=E5=9F=BA=E6=9C=AC=E7=9A=84=E3=81=AA=E4=BB=95=E7=B5=84?= =?UTF-8?q?=E3=81=BF=E3=81=AE=E4=BF=AE=E6=AD=A3=20*=20refresh=5Ftoken?= =?UTF-8?q?=E3=81=AF=E3=81=9D=E3=82=8C=E3=81=9E=E3=82=8C=E3=81=AE=E3=82=B0?= =?UTF-8?q?=E3=83=AB=E3=83=BC=E3=83=97=E6=AF=8E=E3=81=AE=E8=A8=AD=E5=AE=9A?= =?UTF-8?q?=E3=81=AB=E5=88=86=E3=81=91=E3=82=8B=20*=20=E6=AB=BB=E5=9D=82?= =?UTF-8?q?=20->=20=E6=97=A5=E5=90=91=E5=9D=82=20=E3=81=AE=E9=A0=86?= =?UTF-8?q?=E7=95=AA=E3=81=AB=E3=83=A1=E3=83=83=E3=82=BB=E3=83=BC=E3=82=B8?= =?UTF-8?q?=E3=82=92=E4=BF=9D=E5=AD=98=E3=81=99=E3=82=8B=20*=20=E6=AB=BB?= =?UTF-8?q?=E5=9D=82=E3=81=A8=E6=97=A5=E5=90=91=E5=9D=82=E3=81=A7API?= =?UTF-8?q?=E3=81=AE=E3=82=A8=E3=83=B3=E3=83=89=E3=83=9D=E3=82=A4=E3=83=B3?= =?UTF-8?q?=E3=83=88=E3=81=A8API=E3=83=90=E3=83=BC=E3=82=B8=E3=83=A7?= =?UTF-8?q?=E3=83=B3=E4=BB=A5=E5=A4=96=E3=81=AB=E9=81=95=E3=81=84=E3=81=AF?= =?UTF-8?q?=E7=84=A1=E3=81=84=E3=81=AE=E3=81=A7=E3=80=81=E3=83=A1=E3=83=83?= =?UTF-8?q?=E3=82=BB=E3=83=BC=E3=82=B8=E4=BF=9D=E5=AD=98=E6=99=82=E3=81=AE?= =?UTF-8?q?=E4=B8=80=E9=80=A3=E3=81=AE=E3=83=AD=E3=82=B8=E3=83=83=E3=82=AF?= =?UTF-8?q?=E3=81=AF=E5=A4=89=E3=81=88=E3=81=AA=E3=81=84=20*=20http=20clie?= =?UTF-8?q?nt=E3=82=92=E6=AB=BB=E5=9D=82=E3=81=A8=E6=97=A5=E5=90=91?= =?UTF-8?q?=E5=9D=82=E3=81=A7=E5=88=86=E3=81=91=E3=81=A6=E3=80=81=E8=A8=AD?= =?UTF-8?q?=E5=AE=9A=E5=80=A4=E3=81=AE=E7=95=B0=E3=81=AA=E3=82=8B=E7=82=B9?= =?UTF-8?q?=E3=81=AF=E3=81=93=E3=81=93=E3=81=A7=E5=90=B8=E5=8F=8E=E3=81=99?= =?UTF-8?q?=E3=82=8B=20*=20=E5=BC=95=E6=95=B0=E3=81=A7=E6=8C=87=E5=AE=9A?= =?UTF-8?q?=E3=81=A7=E3=81=8D=E3=82=8Bgroup=E3=81=AE=E5=80=A4=E3=81=AB?= =?UTF-8?q?=E3=81=A4=E3=81=84=E3=81=A6=E3=81=AF=E3=80=81=E4=BF=9D=E5=AD=98?= =?UTF-8?q?=E3=81=97=E3=81=AA=E3=81=84=E3=82=B0=E3=83=AB=E3=83=BC=E3=83=97?= =?UTF-8?q?=E3=81=AE=E5=A0=B4=E5=90=88=E3=81=AF=E3=81=9D=E3=82=82=E3=81=9D?= =?UTF-8?q?=E3=82=82=E4=BF=9D=E5=AD=98=E3=83=AD=E3=82=B8=E3=83=83=E3=82=AF?= =?UTF-8?q?=E3=82=92=E3=81=97=E3=81=AA=E3=81=84=E3=82=88=E3=81=86=E3=81=AA?= =?UTF-8?q?=E5=87=A6=E7=90=86=E3=81=AB=E5=A4=89=E6=9B=B4=20*=20=E3=81=BE?= =?UTF-8?q?=E3=81=9A=E3=81=AF=E6=AB=BB=E5=9D=82=E3=81=AB=E3=81=A4=E3=81=84?= =?UTF-8?q?=E3=81=A6=E5=8B=95=E4=BD=9C=E3=81=99=E3=82=8B=E3=82=88=E3=81=86?= =?UTF-8?q?=E3=81=AB=E4=BF=AE=E6=AD=A3=E3=81=99=E3=82=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 2 +- src/bin/colmsg/app.rs | 29 ++++++++++++------ src/bin/colmsg/clap_app.rs | 13 ++++---- src/bin/colmsg/config.rs | 14 +++------ src/bin/colmsg/main.rs | 46 ++++++++++++++-------------- src/controller.rs | 12 ++++---- src/http/client.rs | 61 +++++++++++++++++++++++++++++++------- src/http/groups.rs | 12 ++++---- src/http/mod.rs | 4 +-- src/http/tags.rs | 12 ++++---- src/http/timeline.rs | 8 ++--- src/http/update_token.rs | 6 ++-- src/lib.rs | 6 ++-- src/message/file.rs | 8 ++--- src/message/saver.rs | 42 +++++++++++--------------- 15 files changed, 151 insertions(+), 124 deletions(-) diff --git a/README.md b/README.md index f6d098c..2fe50ae 100644 --- a/README.md +++ b/README.md @@ -51,7 +51,7 @@ $ colmsg -n 菅井友香 -n 佐々木久美 特定のグループのメッセージを保存したい場合 ```shell script -$ colmsg -g keyakizaka +$ colmsg -g sakurazaka ``` 特定の種類のメッセージを保存したい場合 diff --git a/src/bin/colmsg/app.rs b/src/bin/colmsg/app.rs index cbb084c..7d47a38 100644 --- a/src/bin/colmsg/app.rs +++ b/src/bin/colmsg/app.rs @@ -3,21 +3,27 @@ use std::fs; use clap::ArgMatches; use wild; +use chrono::NaiveDateTime; -use colmsg::dirs::PROJECT_DIRS; +use colmsg::{ + dirs::PROJECT_DIRS, + errors::*, + Config, + Group, + Kind, + http::client::{SClient, SHClient} +}; use crate::{ clap_app, config::get_args_from_config_file, - config::get_access_token_from_file + config::get_access_token_from_file, }; pub struct App { pub matches: ArgMatches<'static> } -use colmsg::{errors::*, Config, Group, Kind}; -use chrono::NaiveDateTime; impl App { pub fn new() -> Result { @@ -37,9 +43,14 @@ impl App { Ok(clap_app::build_app().get_matches_from(args)) } - pub fn config(&self) -> Result { + pub fn sakurazaka_config(&self) -> Result> { + let client = SClient::new(); + self.config("s_refresh_token", client) + } + + fn config, C: SHClient>(&self, refresh_token_str: S, client: C) -> Result> { let group = match self.matches.value_of("group") { - Some("keyakizaka") => Group::Keyakizaka, + Some("sakurazaka") => Group::Sakurazaka, Some("hinatazaka") => Group::Hinatazaka, _ => Group::All }; @@ -88,11 +99,11 @@ impl App { } let refresh_token = self.matches - .value_of("refresh_token") + .value_of(refresh_token_str) .map(String::from) .unwrap_or_else(|| String::from("invalid_refresh_token")); - let access_token = get_access_token_from_file(&refresh_token)?; - Ok(Config { group, name, from, kind, dir, access_token }) + let access_token = get_access_token_from_file(&refresh_token, client.clone())?; + Ok(Config { group, name, from, kind, dir, client: client.clone(), access_token }) } } diff --git a/src/bin/colmsg/clap_app.rs b/src/bin/colmsg/clap_app.rs index cea2507..efe250d 100644 --- a/src/bin/colmsg/clap_app.rs +++ b/src/bin/colmsg/clap_app.rs @@ -13,7 +13,7 @@ pub fn build_app() -> ClapApp<'static, 'static> { Arg::with_name("group") .long("group") .short("g") - .possible_values(&["keyakizaka", "hinatazaka"]) + .possible_values(&["sakurazaka", "hinatazaka"]) .help("Save messages of specific group.") .long_help("Save messages of specific group. If not specified, save messages both of groups") @@ -64,12 +64,11 @@ Use '--download-dir' to confirm the default directory.") .takes_value(true), ) .arg( - Arg::with_name("refresh_token") - .long("refresh_token") - .short("t") - .required(true) - .help("Set the refresh token.") - .long_help("Set the refresh token. refresh token is required.") + Arg::with_name("s_refresh_token") + .long("s_refresh_token") + .short("st") + .help("Set the sakurazaka refresh token.") + .long_help("Set the sakurazaka refresh token.") .takes_value(true), ) .arg( diff --git a/src/bin/colmsg/config.rs b/src/bin/colmsg/config.rs index 9909f34..acd36c3 100644 --- a/src/bin/colmsg/config.rs +++ b/src/bin/colmsg/config.rs @@ -1,14 +1,8 @@ -use std::env; -use std::ffi::OsString; -use std::fs; -use std::fs::File; -use std::io::Write; -use std::path::PathBuf; +use std::{env, ffi::OsString, fs, fs::File, io::Write, path::PathBuf}; use shell_words; -use colmsg::dirs::PROJECT_DIRS; -use colmsg::{errors::*, http}; +use colmsg::{errors::*, http, dirs::PROJECT_DIRS, http::client::SHClient}; pub fn config_file() -> PathBuf { env::var("COLMSG_CONFIG_PATH") @@ -42,12 +36,12 @@ fn get_args_from_str(content: &str) -> Result> { .collect::>()) } -pub fn get_access_token_from_file(refresh_token: &String) -> Result { +pub fn get_access_token_from_file(refresh_token: &String, client: C) -> Result { let dir = PROJECT_DIRS.config_dir().to_path_buf(); if !dir.is_dir() { fs::create_dir_all(&dir)? }; let file = dir.join("access_token"); if file.is_file() { return Ok(fs::read_to_string(file)?); } - let update_token_res = http::update_token::request(refresh_token)?; + let update_token_res = http::update_token::request(client, refresh_token)?; let mut f = File::create(file)?; f.write_all(update_token_res.access_token.as_ref())?; Ok(update_token_res.access_token) diff --git a/src/bin/colmsg/main.rs b/src/bin/colmsg/main.rs index 63c85a7..1120360 100644 --- a/src/bin/colmsg/main.rs +++ b/src/bin/colmsg/main.rs @@ -5,45 +5,42 @@ mod app; mod clap_app; pub mod config; -use std::process; -use std::io; -use std::io::Write; +use std::{process, io, io::Write}; use reqwest::StatusCode; -use crate::{ - app::App, - config::delete_access_token_file, -}; +use crate::{app::App, config::delete_access_token_file}; use colmsg::dirs::PROJECT_DIRS; -use colmsg::{errors::*, Config}; +use colmsg::{errors::*, Config, Group}; use colmsg::errors::ErrorKind::ReqwestError; use colmsg::controller::Controller; +use colmsg::http::client::{SClient, SHClient}; - -fn run_controller(config: &Config) -> Result { +fn run_controller(config: &Config) -> Result { let controller = Controller::new(config); controller.run() } +fn run_sakurazaka(app: &App) -> Result { + let config: Config = app.sakurazaka_config()?; + match &config.group { + Group::Sakurazaka | Group::All => run_controller(&config), + _ => Ok(true) + } +} + fn run() -> Result { let app = App::new()?; - let config = &app.config()?; - if app.matches.is_present("config-dir") { writeln!(io::stdout(), "{}", PROJECT_DIRS.config_dir().to_string_lossy())?; - Ok(true) - } else if app.matches.is_present("download-dir") { + return Ok(true); + } + if app.matches.is_present("download-dir") { writeln!(io::stdout(), "{}", PROJECT_DIRS.download_dir().to_string_lossy())?; - Ok(true) - } else { - run_controller(&config) + return Ok(true); } -} - -fn main() { - let mut result = run(); + let mut result = run_sakurazaka(&app); loop { match &result { Err(Error(ReqwestError(re), _)) => { @@ -52,11 +49,16 @@ fn main() { result = Err(de); break; }; - result = run(); + result = run_sakurazaka(&app); } _ => { break; } } } + result +} + +fn main() { + let result = run(); match result { Err(error) => { diff --git a/src/controller.rs b/src/controller.rs index f3f1925..9b5f9bb 100644 --- a/src/controller.rs +++ b/src/controller.rs @@ -1,13 +1,11 @@ -use crate::errors::*; -use crate::Config; -use crate::message::saver::Saver; +use crate::{errors::*, Config, message::saver::Saver, http::client::SHClient}; -pub struct Controller<'a> { - config: &'a Config<'a> +pub struct Controller<'a, C: SHClient> { + config: &'a Config<'a, C> } -impl<'b> Controller<'b> { - pub fn new<'a>(config: &'a Config) -> Controller<'a> { +impl<'b, C: SHClient> Controller<'b, C> { + pub fn new<'a>(config: &'a Config) -> Controller<'a, C> { Controller { config } } diff --git a/src/http/client.rs b/src/http/client.rs index 925e8bc..54e9e81 100644 --- a/src/http/client.rs +++ b/src/http/client.rs @@ -1,10 +1,10 @@ use std::env; -use reqwest::blocking::Client as reqwest_client; -use reqwest::blocking::Response; -use reqwest::header::{HeaderMap, CONTENT_TYPE, ACCEPT_LANGUAGE, USER_AGENT, CONNECTION, ACCEPT_ENCODING, TE, AUTHORIZATION, ACCEPT}; -use serde::Serialize; -use serde::de::DeserializeOwned; +use reqwest::{ + blocking::Client as reqwest_client, blocking::Response, + header::{HeaderMap, CONTENT_TYPE, ACCEPT_LANGUAGE, USER_AGENT, CONNECTION, ACCEPT_ENCODING, TE, AUTHORIZATION, ACCEPT}, +}; +use serde::{Serialize, de::DeserializeOwned}; use url::Url; #[cfg(feature = "401")] @@ -13,16 +13,19 @@ use rand::Rng; use crate::errors::*; use crate::reqwest; -pub struct Client { +#[derive(Debug, Clone)] +struct Client { client: reqwest_client, base_url: String, + x_talk_app_id: String, } impl Client { - pub fn new() -> Client { + pub fn new(base_url: String, x_talk_app_id: String) -> Client { Client { client: reqwest_client::new(), - base_url: base_url(), + base_url, + x_talk_app_id, } } @@ -78,7 +81,7 @@ impl Client { fn insert_headers(&self, mut header: HeaderMap) -> Result { header.insert(ACCEPT, "application/json".parse()?); header.insert(CONTENT_TYPE, "application/json".parse()?); - header.insert("X-Talk-App-ID", "jp.co.sonymusic.communication.keyakizaka 2.1".parse()?); + header.insert("X-Talk-App-ID", (&self.x_talk_app_id).parse()?); header.insert(ACCEPT_LANGUAGE, "ja-JP".parse()?); header.insert(USER_AGENT, "Dalvik/2.1.0 (Linux; U; Android 6.0; Samsung Galaxy S7 for keyaki messages Build/MRA58K)".parse()?); header.insert(CONNECTION, "Keep-Alive".parse()?); @@ -106,8 +109,44 @@ impl Client { fn insert_401_header(&self, header: HeaderMap) -> Result { Ok(header) } } +pub trait SHClient: Clone { + fn new() -> Self where Self: Sized; + + fn post_request(&self, path: &str, json: &JT) -> Result + where RT: DeserializeOwned, JT: Serialize + ?Sized; + + fn get_request(&self, path: &str, access_token: &str, parameters: Option>) -> Result + where RT: DeserializeOwned; +} + +#[derive(Debug, Clone)] +pub struct SClient { + client: Client, +} + +impl SHClient for SClient { + fn new() -> SClient { + SClient { + client: Client::new( + base_url(), + "jp.co.sonymusic.communication.sakurazaka 2.1".to_string(), + ), + } + } + + fn post_request(&self, path: &str, json: &JT) -> Result + where RT: DeserializeOwned, JT: Serialize + ?Sized { + self.client.post_request(path, json) + } + + fn get_request(&self, path: &str, access_token: &str, parameters: Option>) -> Result + where RT: DeserializeOwned { + self.client.get_request(path, access_token, parameters) + } +} + fn base_url() -> String { - env::var("BASE_URL") + env::var("BASE_S_URL") .ok() - .unwrap_or_else(|| "https://api.kh.glastonr.net".to_string()) + .unwrap_or_else(|| "https://api.s46.glastonr.net".to_string()) } diff --git a/src/http/groups.rs b/src/http/groups.rs index ee605c5..49f35b4 100644 --- a/src/http/groups.rs +++ b/src/http/groups.rs @@ -1,6 +1,5 @@ use serde::{Deserialize, Serialize}; -use crate::http; -use crate::errors::*; +use crate::{errors::*, http::client::SHClient}; const PATH: &str = "/v2/groups"; @@ -10,7 +9,7 @@ pub struct GroupsSubscription { pub end_at: Option, pub start_at: String, #[serde(rename = "type")] - pub subscription_type: String + pub subscription_type: String, } #[derive(Serialize, Deserialize, Debug)] @@ -25,12 +24,11 @@ pub struct Groups { pub thumbnail: String, pub trial_days: Option, pub updated_at: String, - pub subscription: Option + pub subscription: Option, } -pub fn request(access_token: &String) -> Result> { - let client = http::Client::new(); +pub fn request(client: C, access_token: &String) -> Result> { let access_token = String::from(access_token); - client.get_request::>(PATH, &access_token, None) + client.get_request::>(PATH, &access_token, None) } diff --git a/src/http/mod.rs b/src/http/mod.rs index 493a236..a712c7c 100644 --- a/src/http/mod.rs +++ b/src/http/mod.rs @@ -1,7 +1,5 @@ -mod client; +pub mod client; pub mod update_token; pub mod groups; pub mod tags; pub mod timeline; - -pub use self::client::Client; diff --git a/src/http/tags.rs b/src/http/tags.rs index a9c7226..62e5c77 100644 --- a/src/http/tags.rs +++ b/src/http/tags.rs @@ -1,13 +1,12 @@ use serde::{Deserialize, Serialize}; -use crate::http; -use crate::errors::*; +use crate::{errors::*, http::client::SHClient}; const PATH: &str = "/v2/tags"; #[derive(Serialize, Deserialize, Debug)] pub struct TagsMeta { pub color: String, - pub dimension: Option + pub dimension: Option, } #[derive(Serialize, Deserialize, Debug)] @@ -16,12 +15,11 @@ pub struct Tags { pub name: String, pub priority: u32, pub updated_at: String, - pub uuid: String + pub uuid: String, } -pub fn request(access_token: &String) -> Result> { - let client = http::Client::new(); +pub fn request(client: C, access_token: &String) -> Result> { let access_token = String::from(access_token); - client.get_request::>(PATH, &access_token, None) + client.get_request::>(PATH, &access_token, None) } diff --git a/src/http/timeline.rs b/src/http/timeline.rs index a35bec5..584f2b8 100644 --- a/src/http/timeline.rs +++ b/src/http/timeline.rs @@ -1,6 +1,5 @@ use serde::{Deserialize, Serialize}; -use crate::http; -use crate::errors::*; +use crate::{errors::*, http::client::SHClient}; const PATH: &str = "/v2/groups"; const PATH2: &str = "/timeline"; @@ -54,14 +53,13 @@ pub struct Timeline { pub queried_at: String, } -pub fn request(access_token: &String, id: &u32, fromdate: &String) -> Result { +pub fn request(client: C, access_token: &String, id: &u32, fromdate: &String) -> Result { let path = format!("{}/{}{}", PATH, id, PATH2); - let client = http::Client::new(); let access_token = String::from(access_token); let parameters = vec![ ("created_from", "2000-01-01T00:00:00Z"), ("updated_from", fromdate), - ("count", COUNT), + ("count", COUNT), ("order", ORDER) ]; diff --git a/src/http/update_token.rs b/src/http/update_token.rs index 499bebd..b61a2ba 100644 --- a/src/http/update_token.rs +++ b/src/http/update_token.rs @@ -1,6 +1,5 @@ use serde::{Deserialize, Serialize}; -use crate::http; -use crate::errors::*; +use crate::{errors::*, http::client::SHClient}; const PATH: &str = "/v2/update_token"; @@ -23,8 +22,7 @@ pub struct UpdateTokenReq { pub refresh_token: String } -pub fn request(refresh_token: &String) -> Result { - let client = http::Client::new(); +pub fn request(client: C, refresh_token: &String) -> Result { let refresh_token = String::from(refresh_token); let update_token_json = UpdateTokenReq { refresh_token }; diff --git a/src/lib.rs b/src/lib.rs index c96709c..ef60f39 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -46,10 +46,11 @@ pub mod errors { use std::path::PathBuf; use chrono::{NaiveDateTime}; +use crate::http::client::SHClient; #[derive(Debug, Clone, Copy, PartialEq)] pub enum Group { - Keyakizaka, + Sakurazaka, Hinatazaka, All, } @@ -62,11 +63,12 @@ pub enum Kind { Voice, } -pub struct Config<'a> { +pub struct Config<'a, C: SHClient> { pub group: Group, pub name: Vec<&'a str>, pub from: Option, pub kind: Vec, pub dir: PathBuf, + pub client: C, pub access_token: String, } diff --git a/src/message/file.rs b/src/message/file.rs index ad6dd3a..1af6cfc 100644 --- a/src/message/file.rs +++ b/src/message/file.rs @@ -1,7 +1,7 @@ -use std::io::{Write, copy}; -use std::fs::File; -use std::io; -use std::path::PathBuf; +use std::{ + io::{Write, copy}, + fs::File, io, path::PathBuf, +}; use chrono::NaiveDateTime; diff --git a/src/message/saver.rs b/src/message/saver.rs index c16021d..5741c9e 100644 --- a/src/message/saver.rs +++ b/src/message/saver.rs @@ -5,25 +5,24 @@ use regex::Regex; use walkdir::{WalkDir, DirEntry}; use chrono::NaiveDateTime; -use crate::errors::*; -use crate::{Config, http, message, Group, Kind}; -use crate::message::file::{Text, Picture, SaveToFile, Video, Voice}; -use crate::http::groups::Groups; -use crate::http::tags::Tags; -use crate::http::timeline::TimelineMessages; - -pub struct Saver<'a> { - config: &'a Config<'a> +use crate::{ + errors::*, Config, message, Kind, + http::{self, groups::Groups, tags::Tags, timeline::TimelineMessages, client::SHClient}, + message::file::{Text, Picture, SaveToFile, Video, Voice}, +}; + +pub struct Saver<'a, C: SHClient> { + config: &'a Config<'a, C> } -impl<'b> Saver<'b> { - pub fn new<'a>(config: &'a Config) -> Saver<'a> { +impl<'b, C: SHClient> Saver<'b, C> { + pub fn new<'a>(config: &'a Config) -> Saver<'a, C> { Saver { config } } pub fn save(&self) -> Result<()> { - let groups = http::groups::request(&self.config.access_token)?; - let tags = http::tags::request(&self.config.access_token)?; + let groups = http::groups::request(self.config.client.clone(), &self.config.access_token)?; + let tags = http::tags::request(self.config.client.clone(), &self.config.access_token)?; // TODO: 並列処理したい // 購読しているメンバー毎にメッセージを保存するためのループ @@ -39,13 +38,6 @@ impl<'b> Saver<'b> { .iter() .cloned() .filter(|m| { m.subscription }) - .filter(|m| { - match self.config.group { - Group::Keyakizaka => m.group == "欅坂46", - Group::Hinatazaka => m.group == "日向坂46", - Group::All => true - } - }) .filter(|m| { if self.config.name.is_empty() { return true; } // メンバー指定が無い場合は全メンバーを対象にする self.config.name.contains(&&*self.trim(&m.name)) @@ -86,7 +78,7 @@ impl<'b> Saver<'b> { // 購読しているメンバーのメッセージを取得するAPIを複数回叩くためのループ loop { - let timeline = http::timeline::request(&self.config.access_token, &member_identifier.id, &fromdate)?; + let timeline = http::timeline::request(self.config.client.clone(), &self.config.access_token, &member_identifier.id, &fromdate)?; // メッセージを取得するAPIを叩くと複数件のメッセージを取得出来る // そのメッセージを1件ずつ処理するためのループ @@ -134,7 +126,7 @@ impl<'b> Saver<'b> { &message.text, ); message_file_text.save()? - }, + } "picture" => { if !self.config.kind.contains(&Kind::Picture) { return Ok(()); } let message_file_picture = Picture::new( @@ -144,7 +136,7 @@ impl<'b> Saver<'b> { &message.file, ); message_file_picture.save()? - }, + } "video" => { if !self.config.kind.contains(&Kind::Video) { return Ok(()); } let message_file_video = Video::new( @@ -153,7 +145,7 @@ impl<'b> Saver<'b> { &message.file, ); message_file_video.save()? - }, + } "voice" => { if !self.config.kind.contains(&Kind::Voice) { return Ok(()); } let message_file_voice = Voice::new( @@ -162,7 +154,7 @@ impl<'b> Saver<'b> { &message.file, ); message_file_voice.save()? - }, + } _ => { let err = format!("unknown type: {}", message.messages_type.as_str()); return Err(err.into()); From 0a025e0daa0c6382fbbbc270f532525c8f01d08e Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Mon, 16 Nov 2020 22:06:18 +0900 Subject: [PATCH 04/11] =?UTF-8?q?=E6=97=A5=E5=90=91=E5=9D=82=E3=81=AE?= =?UTF-8?q?=E3=83=A1=E3=83=83=E3=82=BB=E3=83=BC=E3=82=B8=E3=81=8C=E4=BF=9D?= =?UTF-8?q?=E5=AD=98=E3=81=95=E3=82=8C=E3=82=8B=E3=82=88=E3=81=86=E3=81=AB?= =?UTF-8?q?=E4=BF=AE=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/bin/colmsg/app.rs | 7 ++++++- src/bin/colmsg/clap_app.rs | 8 ++++++++ src/bin/colmsg/main.rs | 28 +++++++++++++++++++++++----- src/http/client.rs | 36 ++++++++++++++++++++++++++++++++++-- 4 files changed, 71 insertions(+), 8 deletions(-) diff --git a/src/bin/colmsg/app.rs b/src/bin/colmsg/app.rs index 7d47a38..465fc19 100644 --- a/src/bin/colmsg/app.rs +++ b/src/bin/colmsg/app.rs @@ -11,7 +11,7 @@ use colmsg::{ Config, Group, Kind, - http::client::{SClient, SHClient} + http::client::{SClient, SHClient, HClient} }; use crate::{ @@ -48,6 +48,11 @@ impl App { self.config("s_refresh_token", client) } + pub fn hinatazaka_config(&self) -> Result> { + let client = HClient::new(); + self.config("h_refresh_token", client) + } + fn config, C: SHClient>(&self, refresh_token_str: S, client: C) -> Result> { let group = match self.matches.value_of("group") { Some("sakurazaka") => Group::Sakurazaka, diff --git a/src/bin/colmsg/clap_app.rs b/src/bin/colmsg/clap_app.rs index efe250d..9280f5a 100644 --- a/src/bin/colmsg/clap_app.rs +++ b/src/bin/colmsg/clap_app.rs @@ -71,6 +71,14 @@ Use '--download-dir' to confirm the default directory.") .long_help("Set the sakurazaka refresh token.") .takes_value(true), ) + .arg( + Arg::with_name("h_refresh_token") + .long("h_refresh_token") + .short("ht") + .help("Set the hinatazaka refresh token.") + .long_help("Set the hinatazaka refresh token.") + .takes_value(true), + ) .arg( Arg::with_name("delete") .long("delete") diff --git a/src/bin/colmsg/main.rs b/src/bin/colmsg/main.rs index 1120360..9f0f055 100644 --- a/src/bin/colmsg/main.rs +++ b/src/bin/colmsg/main.rs @@ -15,7 +15,7 @@ use colmsg::dirs::PROJECT_DIRS; use colmsg::{errors::*, Config, Group}; use colmsg::errors::ErrorKind::ReqwestError; use colmsg::controller::Controller; -use colmsg::http::client::{SClient, SHClient}; +use colmsg::http::client::{SClient, SHClient, HClient}; fn run_controller(config: &Config) -> Result { let controller = Controller::new(config); @@ -30,6 +30,14 @@ fn run_sakurazaka(app: &App) -> Result { } } +fn run_hinatazaka(app: &App) -> Result { + let config: Config = app.hinatazaka_config()?; + match &config.group { + Group::Hinatazaka | Group::All => run_controller(&config), + _ => Ok(true) + } +} + fn run() -> Result { let app = App::new()?; if app.matches.is_present("config-dir") { @@ -45,15 +53,25 @@ fn run() -> Result { match &result { Err(Error(ReqwestError(re), _)) => { if Some(StatusCode::UNAUTHORIZED) != re.status() { break; }; - if let Err(de) = delete_access_token_file() { - result = Err(de); - break; - }; + delete_access_token_file()?; result = run_sakurazaka(&app); } _ => { break; } } } + + result = run_hinatazaka(&app); + loop { + match &result { + Err(Error(ReqwestError(re), _)) => { + if Some(StatusCode::UNAUTHORIZED) != re.status() { break; }; + delete_access_token_file()?; + result = run_hinatazaka(&app); + } + _ => { break; } + } + } + result } diff --git a/src/http/client.rs b/src/http/client.rs index 54e9e81..0318abc 100644 --- a/src/http/client.rs +++ b/src/http/client.rs @@ -128,7 +128,7 @@ impl SHClient for SClient { fn new() -> SClient { SClient { client: Client::new( - base_url(), + s_base_url(), "jp.co.sonymusic.communication.sakurazaka 2.1".to_string(), ), } @@ -145,8 +145,40 @@ impl SHClient for SClient { } } -fn base_url() -> String { +fn s_base_url() -> String { env::var("BASE_S_URL") .ok() .unwrap_or_else(|| "https://api.s46.glastonr.net".to_string()) } + +#[derive(Debug, Clone)] +pub struct HClient { + client: Client, +} + +impl SHClient for HClient { + fn new() -> HClient { + HClient { + client: Client::new( + h_base_url(), + "jp.co.sonymusic.communication.keyakizaka 2.1".to_string(), + ), + } + } + + fn post_request(&self, path: &str, json: &JT) -> Result + where RT: DeserializeOwned, JT: Serialize + ?Sized { + self.client.post_request(path, json) + } + + fn get_request(&self, path: &str, access_token: &str, parameters: Option>) -> Result + where RT: DeserializeOwned { + self.client.get_request(path, access_token, parameters) + } +} + +fn h_base_url() -> String { + env::var("BASE_H_URL") + .ok() + .unwrap_or_else(|| "https://api.kh.glastonr.net".to_string()) +} From 18e7d84f170a739554b3b6fb2f65b834bc65c9ee Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Mon, 16 Nov 2020 22:53:56 +0900 Subject: [PATCH 05/11] =?UTF-8?q?=E4=BB=96=E3=81=AE=E8=A6=8F=E5=89=87?= =?UTF-8?q?=E3=81=AB=E5=BE=93=E3=81=A3=E3=81=A6base=5Furl=E3=81=AE?= =?UTF-8?q?=E7=92=B0=E5=A2=83=E5=A4=89=E6=95=B0=E5=90=8D=E3=82=92=E5=A4=89?= =?UTF-8?q?=E6=9B=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/http/client.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/http/client.rs b/src/http/client.rs index 0318abc..c1f6522 100644 --- a/src/http/client.rs +++ b/src/http/client.rs @@ -146,7 +146,7 @@ impl SHClient for SClient { } fn s_base_url() -> String { - env::var("BASE_S_URL") + env::var("S_BASE_URL") .ok() .unwrap_or_else(|| "https://api.s46.glastonr.net".to_string()) } @@ -178,7 +178,7 @@ impl SHClient for HClient { } fn h_base_url() -> String { - env::var("BASE_H_URL") + env::var("H_BASE_URL") .ok() .unwrap_or_else(|| "https://api.kh.glastonr.net".to_string()) } From 61b07073819cc493d3fbaa13a08ff0a17e622d30 Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Mon, 16 Nov 2020 22:54:36 +0900 Subject: [PATCH 06/11] =?UTF-8?q?=E3=83=89=E3=82=AD=E3=83=A5=E3=83=A1?= =?UTF-8?q?=E3=83=B3=E3=83=88,=20README.md,=20=E3=81=9D=E3=81=AE=E4=BB=96?= =?UTF-8?q?=E8=AA=AC=E6=98=8E=E6=96=87=E3=81=AE=E4=BF=AE=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Cargo.toml | 2 +- README.md | 31 +++++++++++++++++-------------- doc/how_to_get_refresh_token.md | 5 +++-- src/bin/colmsg/clap_app.rs | 4 ++-- 4 files changed, 23 insertions(+), 19 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 8bf7417..cfd11a9 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -3,7 +3,7 @@ name = "colmsg" version = "2.0.0" authors = ["proshunsuke "] categories = ["command-line-utilities"] -description="'欅坂46/日向坂46 メッセージ'アプリのメッセージをPCに保存します." +description="「櫻坂46メッセージ」「日向坂46メッセージ」アプリのメッセージをPCに保存します." homepage = "https://github.com/proshunsuke/colmsg" license = "MIT" readme = "README.md" diff --git a/README.md b/README.md index 2fe50ae..4b5cb4e 100644 --- a/README.md +++ b/README.md @@ -1,9 +1,6 @@ -# 欅坂46/日向坂46 メッセージのロゴ colmsg +# 櫻坂46メッセージのロゴ日向坂46メッセージのロゴ colmsg -### ※ **「欅坂46/日向坂46 メッセージ」が10/14に「櫻坂46メッセージ」と「日向坂46メッセージ」に分かれるため、colmsgは10/14以降に動作しなくなる可能性があります。対応状況は[こちら](https://github.com/proshunsuke/colmsg/issues/33)を参照してください** -### (※ **"欅坂46/日向坂46 メッセージ" will be divided into "櫻坂46メッセージ" and "日向坂46メッセージ" on 10/14, so the colmsg may not work after 10/14. Please reference [this](https://github.com/proshunsuke/colmsg/issues/33))**) - -「欅坂46/日向坂46 メッセージ」アプリのメッセージをPCに保存します。 +「櫻坂46メッセージ」「日向坂46メッセージ」アプリのメッセージをPCに保存します。 ![sample.png](https://user-images.githubusercontent.com/3148511/85219015-fef60580-b3da-11ea-8b99-51666d27abe3.png) @@ -11,15 +8,16 @@ `colmsg` のインストール方法は[こちら](#インストール)を参照してください。 -**まず初めに**「欅坂46/日向坂46 メッセージ」アプリのrefresh_tokenを取得してください。 +**まず初めに**「櫻坂46メッセージ」「日向坂46メッセージ」アプリそれぞれのrefresh_tokenを取得してください。 取得方法は[こちら](doc/how_to_get_refresh_token.md)を参照してください。 取得出来たら以下を実行してください。 -`` に取得してきたrefresh_tokenを入れてください。 +`` , `` に「櫻坂46メッセージ」「日向坂46メッセージ」それぞれで取得してきたrefresh_tokenを入れてください。 +※片方のアプリのみ購読している方は片方のみを指定してください。 購読しているメンバー全員の全期間のメッセージが保存されます。 ```shell script -$ colmsg -t +$ colmsg -st -ht ``` Windowsの場合は実行ファイル名を `colmsg.exe` に読み替えてください。 @@ -30,7 +28,9 @@ Windowsの場合は実行ファイル名を `colmsg.exe` に読み替えてく * ✅ Android, iosアプリどちらにも対応しています * ✅ Windows, macos, Linuxで実行できます * ✅ 様々な保存方法が選べます -* ✅ 2020年6月10日のアプリアップデート後のバージョン(2.0.00)に対応しています +* ✅ 2020年10月14日のアプリアップデート後のバージョンに対応しています + * 「櫻坂46メッセージ」: バージョン1.0.00.65 + * 「日向坂46メッセージ」: バージョン2.1.00.10020.68 ## 使い方 @@ -82,7 +82,7 @@ $ colmsg --help │   └── 佐々木久美 │   ├── 1_0_20191231235959.txt │   └── 2_1_20200101000000.jpg - └── 欅坂46 + └── 櫻坂46 └── 菅井友香 ├── 3_2_20200101000001.mp4 └── 4_3_20200101000002.mp4 @@ -122,8 +122,11 @@ export COLMSG_CONFIG_PATH="/path/to/colmsg.conf" 設定ファイルの例: ```bash -# refresh_tokenを指定 --t refresh_token +# s_refresh_tokenを指定 +-st s_refresh_token + +# h_refresh_tokenを指定 +-ht h_refresh_token # メディアファイルだけ保存するように設定 -k image -k video -k voice @@ -164,10 +167,10 @@ yay -S colmsg `colmsg` は外部APIを叩きます。開発時はAPIのモックサーバを建てると良いでしょう。そのためのSwagger Specを配置してあります。 TODO: Swagger Specを置く -モックサーバのbase urlを環境変数 `BASE_URL` で指定することが出来ます。以下のように指定することでモックサーバ宛てにAPIを叩きにいきます。 +モックサーバのbase urlを環境変数 `S_BASE_URL` , `H_BASE_URL` で指定することが出来ます。以下のように指定することでモックサーバ宛てにAPIを叩きにいきます。 ```shell script -$ BASE_URL=http://127.0.0.1:3100 cargo run -- --help +$ S_BASE_URL=http://127.0.0.1:3100 cargo run -- --help ``` ## TODO diff --git a/doc/how_to_get_refresh_token.md b/doc/how_to_get_refresh_token.md index 2d05510..d7a90e2 100644 --- a/doc/how_to_get_refresh_token.md +++ b/doc/how_to_get_refresh_token.md @@ -2,7 +2,8 @@ ## はじめに -以下で説明する方法によってデータ損失等が発生する可能性があります。自己責任でお願いします。 +以下で説明する方法によってデータ損失等が発生する可能性があります。自己責任でお願いします。 +また、以下の説明に用いている画像は「欅坂46/日向坂46 メッセージ」アプリのものですが、「櫻坂46メッセージ」「日向坂46メッセージ」共に同様の方法でrefresh_tokenは取得可能なため、適宜それぞれのアプリ用に読み替えてください。 ## 外部サービス連携 @@ -35,7 +36,7 @@ Android 6 以前を使用している人の場合は [Androidアプリ共通の Android 7 以降を使用している人の場合は後述するmitmproxyが動作しないため、[Genymotion](https://www.genymotion.com/)などのエミュレータを使用し、Android 6 以前の環境を作ってください。 [こちらの記事](https://qiita.com/sou_lab/items/bb06bb653b291c90bf45)などを参考にしてGenymotionにGoogle Play ストアを入れてください。 -その後「欅坂46/日向坂46 メッセージ」アプリをインストールしてください。 +その後「櫻坂46メッセージ」「日向坂46メッセージ」アプリをインストールしてください。 [Androidアプリ共通のデータ削除](#Androidアプリ共通のデータ削除) へ進んでください。 #### Androidアプリ共通のデータ削除 diff --git a/src/bin/colmsg/clap_app.rs b/src/bin/colmsg/clap_app.rs index 9280f5a..50c15be 100644 --- a/src/bin/colmsg/clap_app.rs +++ b/src/bin/colmsg/clap_app.rs @@ -5,10 +5,10 @@ pub fn build_app() -> ClapApp<'static, 'static> { .version(crate_version!()) .global_setting(AppSettings::ColoredHelp) .about( - "A CLI tool for '欅坂/日向坂メッセージアプリ'.\n\n\ + "A CLI tool for '櫻坂46メッセージ/日向坂46メッセージ' app.\n\n\ Use '--help' instead of '-h' to see a more detailed version of the help text.", ) - .long_about("A CLI tool for saving messages of '欅坂/日向坂メッセージアプリ' locally.") + .long_about("A CLI tool for saving messages of '櫻坂46メッセージ/日向坂46メッセージ' app locally.") .arg( Arg::with_name("group") .long("group") From 71af3a2d52a21306cac4c53000b523227ca85ad1 Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Tue, 17 Nov 2020 00:23:14 +0900 Subject: [PATCH 07/11] update changelog --- CHANGELOG.md | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 8459cbf..bea5171 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,21 @@ ## Packaging +# v2.0.0 + +https://github.com/proshunsuke/colmsg/pull/37 + +## BREAKING CHANGES + +* support "櫻坂46メッセージ" and "日向坂46メッセージ" +* **no longer support "欅坂46/日向坂46 メッセージ"** +* add --s_refresh_token and --h_refresh_token options +* remove --refresh_token option + +## Changes + +* update README.md +* update doc + # v1.0.0 https://github.com/proshunsuke/colmsg/pull/30 From 22a04eebe2f1ca759bb040751019923ae2bd2ac3 Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Tue, 17 Nov 2020 01:00:18 +0900 Subject: [PATCH 08/11] =?UTF-8?q?v1.0.0=E3=82=92=E4=BD=BF=E7=94=A8?= =?UTF-8?q?=E3=81=97=E3=81=A6=E3=81=84=E3=81=9F=E6=96=B9=E3=81=AB=E5=90=91?= =?UTF-8?q?=E3=81=91=E3=81=A6=E3=81=AE=E3=83=89=E3=82=AD=E3=83=A5=E3=83=A1?= =?UTF-8?q?=E3=83=B3=E3=83=88=E4=BD=9C=E6=88=90?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 8 +++++--- ...anges_about_sakurazaka_and_hinatazaka_app.md | 17 +++++++++++++++++ src/bin/colmsg/clap_app.rs | 2 -- 3 files changed, 22 insertions(+), 5 deletions(-) create mode 100644 doc/changes_about_sakurazaka_and_hinatazaka_app.md diff --git a/README.md b/README.md index 4b5cb4e..ef3b4cc 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,7 @@ # 櫻坂46メッセージのロゴ日向坂46メッセージのロゴ colmsg +[「欅坂46/日向坂46 メッセージ」アプリを使用していた方へ](doc/changes_about_sakurazaka_and_hinatazaka_app.md) + 「櫻坂46メッセージ」「日向坂46メッセージ」アプリのメッセージをPCに保存します。 ![sample.png](https://user-images.githubusercontent.com/3148511/85219015-fef60580-b3da-11ea-8b99-51666d27abe3.png) @@ -17,7 +19,7 @@ 購読しているメンバー全員の全期間のメッセージが保存されます。 ```shell script -$ colmsg -st -ht +$ colmsg --s_refresh_token --h_refresh_token ``` Windowsの場合は実行ファイル名を `colmsg.exe` に読み替えてください。 @@ -123,10 +125,10 @@ export COLMSG_CONFIG_PATH="/path/to/colmsg.conf" ```bash # s_refresh_tokenを指定 --st s_refresh_token +--s_refresh_token s_refresh_token # h_refresh_tokenを指定 --ht h_refresh_token +--h_refresh_token h_refresh_token # メディアファイルだけ保存するように設定 -k image -k video -k voice diff --git a/doc/changes_about_sakurazaka_and_hinatazaka_app.md b/doc/changes_about_sakurazaka_and_hinatazaka_app.md new file mode 100644 index 0000000..a82bf06 --- /dev/null +++ b/doc/changes_about_sakurazaka_and_hinatazaka_app.md @@ -0,0 +1,17 @@ +# 「欅坂46/日向坂46 メッセージ」アプリを使用していた方へ + +「欅坂46/日向坂46 メッセージ」アプリは2020年10月14日に「櫻坂46メッセージ」アプリと「日向坂46メッセージ」アプリに分かれました。 +「欅坂46/日向坂46 メッセージ」アプリの頃からcolmsgを使用していた方には注意事項があります。 + +## 指定するオプションが変わります + +今までは `-t` または `--refresh_token` を指定していましたが、今後は櫻坂46と日向坂46それぞれ専用のrefresh_tokenを指定する必要があります。 +櫻坂46の場合は `--s_refresh_token` 、 日向坂46の場合は `--h_refresh_token` となります。 + +## 櫻坂46(欅坂46)の保存先が変わります + +今までは `欅坂46` が付いた名前のフォルダが作成され、そこに各メンバーのメッセージが保存されていました。 +今後は新たに `櫻坂46` が付いた名前のフォルダが作成され、そこに新たに各メンバーのメッセージが保存されます。 +そのため、今までに保存されていた `欅坂46` フォルダの内容と今後保存される `櫻坂46` フォルダの内容が重複してしまいます。 + +内容を重複させたくない場合は、手動で `欅坂46` のフォルダ名を `櫻坂46` に変更してください。 diff --git a/src/bin/colmsg/clap_app.rs b/src/bin/colmsg/clap_app.rs index 50c15be..46faf8e 100644 --- a/src/bin/colmsg/clap_app.rs +++ b/src/bin/colmsg/clap_app.rs @@ -66,7 +66,6 @@ Use '--download-dir' to confirm the default directory.") .arg( Arg::with_name("s_refresh_token") .long("s_refresh_token") - .short("st") .help("Set the sakurazaka refresh token.") .long_help("Set the sakurazaka refresh token.") .takes_value(true), @@ -74,7 +73,6 @@ Use '--download-dir' to confirm the default directory.") .arg( Arg::with_name("h_refresh_token") .long("h_refresh_token") - .short("ht") .help("Set the hinatazaka refresh token.") .long_help("Set the hinatazaka refresh token.") .takes_value(true), From 870ff9120ea8b11ea3d2f321b80a5b3572b91a25 Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Tue, 17 Nov 2020 01:04:22 +0900 Subject: [PATCH 09/11] =?UTF-8?q?=E3=81=A4=E3=81=84=E3=81=A7=E3=81=AB?= =?UTF-8?q?=E8=AA=AC=E6=98=8E=E6=96=87=E3=82=82=E5=B0=91=E3=81=97=E4=BF=AE?= =?UTF-8?q?=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/bin/colmsg/clap_app.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/bin/colmsg/clap_app.rs b/src/bin/colmsg/clap_app.rs index 46faf8e..111e64d 100644 --- a/src/bin/colmsg/clap_app.rs +++ b/src/bin/colmsg/clap_app.rs @@ -5,10 +5,10 @@ pub fn build_app() -> ClapApp<'static, 'static> { .version(crate_version!()) .global_setting(AppSettings::ColoredHelp) .about( - "A CLI tool for '櫻坂46メッセージ/日向坂46メッセージ' app.\n\n\ + "A CLI tool for '櫻坂46メッセージ' and '日向坂46メッセージ' app.\n\n\ Use '--help' instead of '-h' to see a more detailed version of the help text.", ) - .long_about("A CLI tool for saving messages of '櫻坂46メッセージ/日向坂46メッセージ' app locally.") + .long_about("A CLI tool for saving messages of '櫻坂46メッセージ' and '日向坂46メッセージ' app locally.") .arg( Arg::with_name("group") .long("group") From 747ddea0e66abf6c973774b468e5a6c78216b606 Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Tue, 17 Nov 2020 01:11:31 +0900 Subject: [PATCH 10/11] =?UTF-8?q?=E5=AE=9F=E3=81=AF=E3=83=95=E3=82=A9?= =?UTF-8?q?=E3=83=AB=E3=83=80=E6=A7=8B=E6=88=90=E5=A4=89=E3=82=8F=E3=81=A3?= =?UTF-8?q?=E3=81=A6=E3=81=84=E3=81=9F=E3=81=AE=E3=81=A7=E3=81=A4=E3=81=84?= =?UTF-8?q?=E3=81=A7=E3=81=AB=E4=BF=AE=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index ef3b4cc..6913fe0 100644 --- a/README.md +++ b/README.md @@ -79,16 +79,15 @@ $ colmsg --help * 既にいくつかメッセージが保存されている場合にコマンドを実行すると、最後に保存したメッセージ以降のメッセージを取得して保存します * 保存されるメッセージは次のディレクトリ構造で保存されます * ```shell script - . - ├── 日向坂46 + colmsg/ + ├── 日向坂46 一期生 │   └── 佐々木久美 │   ├── 1_0_20191231235959.txt │   └── 2_1_20200101000000.jpg - └── 櫻坂46 + └── 櫻坂46 一期生 └── 菅井友香 ├── 3_2_20200101000001.mp4 └── 4_3_20200101000002.mp4 - ``` * ファイル名の形式は `<シーケンス番号>_<種類>_<日付>.<拡張子>` となっています * シーケンス番号はメッセージの時系列を表す番号になっています。若い数字程昔のメッセージです。ファイルブラウザで辞書順に並べると保存したメッセージが時系列通りに並びます From 47ce6b73f4ae6307240714b797b00f797ac1a452 Mon Sep 17 00:00:00 2001 From: proshunsuke Date: Tue, 17 Nov 2020 01:14:10 +0900 Subject: [PATCH 11/11] =?UTF-8?q?add=20doc=20for=20=E6=AC=85=E5=9D=8246/?= =?UTF-8?q?=E6=97=A5=E5=90=91=E5=9D=8246=20=E3=83=A1=E3=83=83=E3=82=BB?= =?UTF-8?q?=E3=83=BC=E3=82=B8=20users?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index bea5171..a6c688e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -15,6 +15,7 @@ https://github.com/proshunsuke/colmsg/pull/37 * update README.md * update doc +* add doc for "欅坂46/日向坂46 メッセージ" users # v1.0.0