diff --git a/Cargo.lock b/Cargo.lock index d1553a6..38b8868 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -8,6 +8,17 @@ version = "1.0.69" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "224afbd727c3d6e4b90103ece64b8d1b67fbb1973b1046c2281eed3f3803f800" +[[package]] +name = "atty" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8" +dependencies = [ + "hermit-abi 0.1.19", + "libc", + "winapi", +] + [[package]] name = "autocfg" version = "1.1.0" @@ -31,6 +42,7 @@ name = "binggpt" version = "0.1.0" dependencies = [ "anyhow", + "colored", "futures", "gjson", "reqwest", @@ -86,6 +98,17 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" +[[package]] +name = "colored" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b3616f750b84d8f0de8a58bda93e08e2a81ad3f523089b05f1dffecab48c6cbd" +dependencies = [ + "atty", + "lazy_static", + "winapi", +] + [[package]] name = "core-foundation" version = "0.9.3" @@ -320,6 +343,15 @@ version = "0.12.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" +[[package]] +name = "hermit-abi" +version = "0.1.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33" +dependencies = [ + "libc", +] + [[package]] name = "hermit-abi" version = "0.2.6" @@ -529,7 +561,7 @@ version = "1.15.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0fac9e2da13b5eb447a6ce3d392f23a29d8694bff781bf03a16cd9ac8697593b" dependencies = [ - "hermit-abi", + "hermit-abi 0.2.6", "libc", ] diff --git a/Cargo.toml b/Cargo.toml index 91013a0..bf57099 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -7,6 +7,7 @@ edition = "2021" [dependencies] anyhow = "1.0.69" +colored = "2.0.0" futures = "0.3.26" gjson = "0.8.1" reqwest = "0.11.14" diff --git a/src/main.rs b/src/main.rs index f22b492..8671028 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,3 +1,4 @@ +use colored::Colorize; use pkg::bing::ChatHub; pub mod pkg; @@ -7,22 +8,25 @@ async fn main() { let mut chat_hub = match ChatHub::new().await { Ok(chat_hub) => chat_hub, Err(err) => { - println!("BingGPT create conversation error: {}", err); + println!( + "BingGPT create conversation error: {}", + err.to_string().red() + ); return; } }; if let Err(e) = chat_hub.create_websocket().await { - println!("BingGPT create websocket error: {}", e); + println!("BingGPT create websocket error: {}", e.to_string().red()); return; }; if let Err(e) = chat_hub.send_protocol().await { - println!("BingGPT send protocol error: {}", e); + println!("BingGPT send protocol error: {}", e.to_string().red()); return; }; if let Err(e) = chat_hub.run().await { - println!("BingGPT run error: {}", e); + println!("BingGPT run error: {}", e.to_string().red()); }; } diff --git a/src/pkg/bing.rs b/src/pkg/bing.rs index ffd068f..e9fd421 100644 --- a/src/pkg/bing.rs +++ b/src/pkg/bing.rs @@ -2,6 +2,7 @@ use std::io::{stdout, Write}; use super::http; use anyhow::{Ok, Result}; +use colored::Colorize; use futures::{ stream::{SplitSink, SplitStream}, SinkExt, StreamExt, @@ -22,11 +23,7 @@ impl Conversation { pub async fn new() -> Result { let json_str = http::Client::new() .get_html("https://www.bing.com/turing/conversation/create") - .await - .map_err(|e| { - println!("create_conversation error: {}", e); - e - })?; + .await?; if gjson::get(&json_str, "result.value").to_string() == "Success" { Ok(Conversation { client_id: gjson::get(&json_str, "clientId").to_string(), @@ -36,7 +33,6 @@ impl Conversation { }) } else { Err(anyhow::anyhow!( - "create_conversation error: {}", gjson::get(&json_str, "result.message").to_string() )) } @@ -82,7 +78,6 @@ impl ChatHub { pub async fn send_msg(&mut self, msg: &str) -> Result<()> { let write = self.read.as_mut().unwrap(); - write .send(OtherMessage::Text(fill_msg(msg, &self.conversation))) .await?; @@ -92,14 +87,14 @@ impl ChatHub { pub async fn recv_msg(&mut self) -> Result<()> { let read = self.write.as_mut().unwrap(); - println!("Bing:"); + println!("{}", "Bing:".blue()); let mut index = 0; loop { - let msg = read.next().await.unwrap()?; - let msg = msg.to_string(); + let msg = read.next().await.unwrap()?.to_string(); // println!("{}", msg); if gjson::get(&msg, "type").i32() == 1 { - let answer = gjson::get(&msg, "arguments.0.messages.0.text").to_string(); + let answer = gjson::get(&msg, "arguments.0.messages.0.adaptiveCards.0.body.0.text") + .to_string(); if !answer.is_empty() { print!("{}", utf8_slice::from(&answer, index)); stdout().flush().unwrap(); @@ -107,6 +102,11 @@ impl ChatHub { } } if gjson::get(&msg, "type").i32() == 2 { + let suggesteds = gjson::get(&msg, "item.messages.1.suggestedResponses.#.text"); + println!("\n{}", "Suggestions:".purple()); + for suggested in suggesteds.array() { + println!(" {}", suggested); + } println!(); break; } @@ -115,7 +115,7 @@ impl ChatHub { } pub fn input(&self) -> String { - println!("You:"); + println!("{}", "You:".cyan()); let mut input = String::new(); let mut more_line_mode = false; loop { @@ -125,7 +125,7 @@ impl ChatHub { if line.trim().is_empty() { break; } else if line.trim() == ":more" { - println!("(Enter ':end' to end the multi-line mode.)"); + println!("{}", "(Enter ':end' to end the multi-line mode.)".green()); more_line_mode = true; break; } else if line.trim() == ":end" { diff --git a/src/pkg/http.rs b/src/pkg/http.rs index b2d62ef..87b9d25 100644 --- a/src/pkg/http.rs +++ b/src/pkg/http.rs @@ -1,4 +1,5 @@ use anyhow::Result; +use colored::Colorize; use reqwest::header::{HeaderMap, HeaderValue}; use serde::{Deserialize, Serialize}; use std::fs; @@ -64,7 +65,10 @@ fn get_config() -> Result { let json_str = if let Ok(s) = fs::read_to_string(config_file) { s } else { - println!("Config file not found, please create ~/.config/bing-cookies.json"); + println!( + "{}", + "Config file not found, please create ~/.config/bing-cookies.json".red() + ); std::process::exit(1); }; let cookies: Vec = serde_json::from_str(&json_str)?;