From bf57a504b7a9ef435f9e2ec9d792bc5c3882438e Mon Sep 17 00:00:00 2001 From: yuluo Date: Thu, 18 Apr 2024 22:19:30 +0800 Subject: [PATCH] Optimize HTTP calls --- flutter/lib/models/user_model.dart | 6 +-- flutter/lib/utils/http_service.dart | 80 ++++++++++++++++++++++++++--- src/flutter_ffi.rs | 4 ++ src/ipc.rs | 3 ++ src/ui_interface.rs | 8 +++ 5 files changed, 90 insertions(+), 11 deletions(-) diff --git a/flutter/lib/models/user_model.dart b/flutter/lib/models/user_model.dart index 6cf4cb152..12b905ee6 100644 --- a/flutter/lib/models/user_model.dart +++ b/flutter/lib/models/user_model.dart @@ -9,7 +9,7 @@ import 'package:get/get.dart'; import 'package:http/http.dart' as http; import '../common.dart'; -import '../utils/http_service.dart'; +import '../utils/http_service.dart' as httpR; import 'model.dart'; import 'platform_model.dart'; @@ -136,9 +136,7 @@ class UserModel { /// throw [RequestException] Future login(LoginRequest loginRequest) async { final url = await bind.mainGetApiServer(); - final resp = await HttpService().sendRequest( - '$url/api/login', HttpMethod.post, - body: jsonEncode(loginRequest.toJson())); + final resp = await httpR.post('$url/api/login', body: jsonEncode(loginRequest.toJson())); final Map body; try { diff --git a/flutter/lib/utils/http_service.dart b/flutter/lib/utils/http_service.dart index 35bab842a..cd5080c0c 100644 --- a/flutter/lib/utils/http_service.dart +++ b/flutter/lib/utils/http_service.dart @@ -7,21 +7,65 @@ enum HttpMethod { get, post, put, delete } class HttpService { Future sendRequest( - String url, - HttpMethod method, { - Map? headers, - dynamic body, - }) async { + String url, + HttpMethod method, { + Map? headers, + dynamic body, + }) async { headers ??= {'Content-Type': 'application/json'}; String headersJson = jsonEncode(headers); String methodName = method.toString().split('.').last; - await bind.mainHttpRequest(url: url, method: methodName.toLowerCase(), body: body, header: headersJson); + // Determine if there is currently a proxy setting, and if so, use FFI to call the Rust HTTP method. + final isProxy = await bind.mainGetProxyStatus(); + + if (!isProxy) { + return await _pollFultterHttp(url, method, headers: headers, body: body); + } + + if (body is! String) { + throw Exception('Unsupported HTTP body type'); + } + + await bind.mainHttpRequest( + url: url, + method: methodName.toLowerCase(), + body: body, + header: headersJson); var resJson = await _pollForResponse(); return _parseHttpResponse(resJson); } + Future _pollFultterHttp( + String url, + HttpMethod method, { + Map? headers, + dynamic body, + }) async { + var response = http.Response('', 400); // 默认响应 + Uri uri = Uri.parse(url); + + switch (method) { + case HttpMethod.get: + response = await http.get(uri, headers: headers); + break; + case HttpMethod.post: + response = await http.post(uri, headers: headers, body: body); + break; + case HttpMethod.put: + response = await http.put(uri, headers: headers, body: body); + break; + case HttpMethod.delete: + response = await http.delete(uri, headers: headers, body: body); + break; + default: + throw Exception('Unsupported HTTP method'); + } + + return response; + } + Future _pollForResponse() async { String responseJson = await bind.mainGetAsyncStatus(); while (responseJson == " ") { @@ -45,4 +89,26 @@ class HttpService { throw Exception('Failed to parse response: $e'); } } -} \ No newline at end of file +} + +Future get(String url, {Map? headers}) async { + return await HttpService().sendRequest(url, HttpMethod.get, headers: headers); +} + +Future post(String url, + {Map? headers, Object? body, Encoding? encoding}) async { + return await HttpService() + .sendRequest(url, HttpMethod.post, body: body, headers: headers); +} + +Future put(String url, + {Map? headers, Object? body, Encoding? encoding}) async { + return await HttpService() + .sendRequest(url, HttpMethod.put, body: body, headers: headers); +} + +Future delete(String url, + {Map? headers, Object? body, Encoding? encoding}) async { + return await HttpService() + .sendRequest(url, HttpMethod.delete, body: body, headers: headers); +} diff --git a/src/flutter_ffi.rs b/src/flutter_ffi.rs index efc3c3f43..623c6078f 100644 --- a/src/flutter_ffi.rs +++ b/src/flutter_ffi.rs @@ -801,6 +801,10 @@ pub fn main_set_socks(proxy: String, username: String, password: String) { set_socks(proxy, username, password) } +pub fn main_get_proxy_status() -> bool { + get_proxy_status() +} + pub fn main_get_socks() -> Vec { get_socks() } diff --git a/src/ipc.rs b/src/ipc.rs index 29954d61f..50cc1de47 100644 --- a/src/ipc.rs +++ b/src/ipc.rs @@ -895,6 +895,9 @@ pub async fn set_socks(value: config::Socks5Server) -> ResultType<()> { Ok(()) } +pub fn get_proxy_status() -> bool { + Config::get_socks().is_some() +} #[tokio::main(flavor = "current_thread")] pub async fn test_rendezvous_server() -> ResultType<()> { let mut c = connect(1000, "").await?; diff --git a/src/ui_interface.rs b/src/ui_interface.rs index 87f8b4f7c..4766f046d 100644 --- a/src/ui_interface.rs +++ b/src/ui_interface.rs @@ -421,6 +421,14 @@ pub fn set_socks(proxy: String, username: String, password: String) { .ok(); } +#[inline] +pub fn get_proxy_status() -> bool { + #[cfg(not(any(target_os = "android", target_os = "ios")))] + return ipc::get_proxy_status(); + #[cfg(any(target_os = "android", target_os = "ios"))] + return false; +} + #[cfg(any(target_os = "android", target_os = "ios"))] pub fn set_socks(_: String, _: String, _: String) {}