chimes_utils/utils/
global_data.rs

1use std::collections::HashMap;
2
3use std::time::SystemTime;
4
5use std::sync::Mutex;
6
7use base64::display::Base64Display;
8use base64::prelude::*;
9use rand::thread_rng;
10
11use rsa::pkcs8::{DecodePrivateKey, DecodePublicKey};
12use rsa::{PaddingScheme, PublicKey, RsaPrivateKey, RsaPublicKey};
13// use serde_derive::{Deserialize, Serialize};
14use crate::get_local_timestamp;
15use chrono::offset::Local;
16use chrono::{DateTime, NaiveDateTime};
17use serde::{Deserialize, Deserializer};
18
19use super::AppConfig;
20
21pub struct ValuePaire {
22    value: String,
23    key: String,
24    timestamp: u64,
25    expired: u64,
26}
27
28lazy_static! {
29    pub static ref APP_DATA: Mutex<HashMap<String, ValuePaire>> = Mutex::new(HashMap::new());
30}
31
32/**
33 * 当这个APP_DATA的大小太大了后,就需要进行resizing操作
34 */
35pub fn global_app_data_resizing() {
36    let dts = APP_DATA.lock().unwrap();
37    let len = dts.len();
38    let mut keys = vec![];
39    if len > 10usize {
40        let t = get_local_timestamp();
41        let values = dts.values();
42
43        values.for_each(|f| {
44            let ts = f.timestamp + f.expired;
45            if t >= ts {
46                // global_app_data_remove(&f.key);
47                keys.push(f.key.clone());
48            }
49        });
50    }
51    drop(dts);
52
53    for key in keys {
54        global_app_data_remove(&key);
55    }
56}
57
58#[allow(dead_code)]
59pub fn global_app_data_insert(key: &str, val: &str) {
60    //let mut hs = APP_DATA.lock().as_mut().unwrap().to_owned();
61    //hs.insert(key.to_string(), val.to_string());
62    //log::info!("Size Of Hash: {}", hs.len());
63    global_app_data_insert_with_expire(key, val, 1000 * 60);
64}
65
66#[allow(dead_code)]
67pub fn global_app_data_insert_with_expire(key: &str, val: &str, exp: u64) {
68    //let mut hs = APP_DATA.lock().as_mut().unwrap().to_owned();
69    //hs.insert(key.to_string(), val.to_string());
70    //log::info!("Size Of Hash: {}", hs.len());
71    let value = ValuePaire {
72        value: val.to_owned(),
73        key: key.to_owned(),
74        timestamp: get_local_timestamp(),
75        expired: exp,
76    };
77
78    APP_DATA
79        .lock()
80        .as_mut()
81        .unwrap()
82        .insert(key.to_string(), value);
83
84    global_app_data_resizing();
85}
86
87#[allow(dead_code)]
88pub fn global_app_data_remove(key: &String) {
89    //let mut hs = APP_DATA.lock().as_mut().unwrap().to_owned();
90    //hs.insert(key.to_string(), val.to_string());
91    //log::info!("Size Of Hash: {}", hs.len());
92    APP_DATA.lock().as_mut().unwrap().remove(key);
93}
94
95#[allow(dead_code)]
96pub fn global_app_data_get(key: &String) -> Option<String> {
97    let dt = APP_DATA.lock().unwrap();
98    let cp = dt.get(key);
99    if cp.is_none() {
100        None
101    } else {
102        let mpt = cp.unwrap();
103        if mpt.expired > 0 {
104            let tm = get_local_timestamp();
105            if tm > mpt.timestamp + mpt.expired {
106                global_app_data_remove(key);
107                return None;
108            }
109        }
110        Some(cp.unwrap().value.clone())
111    }
112}
113
114#[allow(dead_code)]
115pub fn rsa_decrypt_by_private_key(token: &String) -> Option<String> {
116    let private_key = AppConfig::get()
117        .lock()
118        .unwrap()
119        .to_owned()
120        .webserver_conf
121        .rsa_password_private_key;
122
123    let bs = match BASE64_STANDARD.decode(private_key) {
124        Ok(rs) => rs,
125        Err(_) => {
126            vec![]
127        }
128    };
129
130    let priv_key = match RsaPrivateKey::from_pkcs8_der(&bs) {
131        Ok(r) => Some(r),
132        Err(err) => {
133            log::warn!("Decode the Private Key with an error {}", err);
134            None
135        }
136    };
137
138    match priv_key {
139        Some(pkey) => {
140            let basedecode = match BASE64_STANDARD.decode(token) {
141                Ok(ts) => ts,
142                Err(_) => vec![],
143            };
144            let dcode = pkey.decrypt(PaddingScheme::PKCS1v15Encrypt, &basedecode);
145            match dcode {
146                Ok(rs) => match String::from_utf8(rs) {
147                    Ok(text) => Some(text),
148                    Err(err) => {
149                        log::warn!("Convert to utf8 with an error {}", err);
150                        None
151                    }
152                },
153                Err(err) => {
154                    log::warn!("Decode the token with an error {}", err.to_string());
155                    None
156                }
157            }
158        }
159        None => None,
160    }
161}
162
163#[allow(dead_code)]
164pub fn rsa_encrypt_by_public_key(token: &String) -> Option<String> {
165    let public_key = AppConfig::get()
166        .lock()
167        .unwrap()
168        .to_owned()
169        .webserver_conf
170        .rsa_password_public_key;
171
172    let bs = match BASE64_STANDARD.decode(public_key) {
173        Ok(rs) => rs,
174        Err(_) => {
175            vec![]
176        }
177    };
178
179    let pub_key = match RsaPublicKey::from_public_key_der(&bs) {
180        Ok(r) => Some(r),
181        Err(err) => {
182            log::warn!("Decode the Private Key with an error {}", err);
183            None
184        }
185    };
186
187    match pub_key {
188        Some(pkey) => {
189            let mut rng = thread_rng();
190            let encoded = pkey.encrypt(&mut rng, PaddingScheme::PKCS1v15Encrypt, token.as_bytes());
191            match encoded {
192                Ok(rs) => {
193                    let encodebase = Base64Display::new(&rs, &BASE64_STANDARD).to_string(); // .decode(rs);
194                    Some(encodebase)
195                }
196                Err(err) => {
197                    log::warn!("Decode the token with an error {}", err.to_string());
198                    None
199                }
200            }
201        }
202        None => None,
203    }
204}
205
206#[derive(Deserialize)]
207#[serde(untagged)] // 枚举类型的无标签方式
208enum StrOrU64 {
209    None,
210    String(String),
211    U64(u64),
212}
213
214#[derive(Deserialize)]
215#[serde(untagged)] // 枚举类型的无标签方式
216enum StrOrI64 {
217    None,
218    String(String),
219    I64(i64),
220}
221
222#[derive(Deserialize)]
223#[serde(untagged)] // 枚举类型的无标签方式
224enum StrOrF64 {
225    None,
226    String(String),
227    F64(f64),
228}
229
230#[derive(Deserialize)]
231#[serde(untagged)] // 枚举类型的无标签方式
232enum StrOrF32 {
233    None,
234    String(String),
235    F32(f32),
236}
237
238#[derive(Deserialize)]
239#[serde(untagged)] // 枚举类型的无标签方式
240enum StrOrBool {
241    String(String),
242    I64(i64),
243    Bool(bool),
244    None,
245}
246
247#[allow(dead_code)]
248pub fn u64_from_str<'de, D>(deserializer: D) -> Result<u64, D::Error>
249where
250    D: Deserializer<'de>,
251{
252    Ok(match StrOrU64::deserialize(deserializer)? {
253        StrOrU64::String(v) => v.parse().unwrap_or_default(),
254        StrOrU64::U64(v) => v,
255        StrOrU64::None => 0u64,
256    })
257}
258
259#[allow(dead_code)]
260pub fn i64_from_str<'de, D>(deserializer: D) -> Result<Option<i64>, D::Error>
261where
262    D: Deserializer<'de>,
263{
264    Ok(match StrOrI64::deserialize(deserializer)? {
265        StrOrI64::String(v) => match v.parse::<i64>() {
266            Ok(st) => Some(st),
267            Err(_) => None,
268        },
269        StrOrI64::I64(v) => Some(v),
270        StrOrI64::None => None,
271    })
272}
273
274#[allow(dead_code)]
275pub fn i32_from_str<'de, D>(deserializer: D) -> Result<Option<i32>, D::Error>
276where
277    D: Deserializer<'de>,
278{
279    Ok(match StrOrI64::deserialize(deserializer)? {
280        StrOrI64::String(v) => match v.parse::<i64>() {
281            Ok(st) => Some(st as i32),
282            Err(_) => None,
283        },
284        StrOrI64::I64(v) => Some(v as i32),
285        StrOrI64::None => None,
286    })
287}
288
289#[allow(dead_code)]
290pub fn f64_from_str<'de, D>(deserializer: D) -> Result<Option<f64>, D::Error>
291where
292    D: Deserializer<'de>,
293{
294    Ok(match StrOrF64::deserialize(deserializer)? {
295        StrOrF64::String(v) => Some(v.parse().unwrap_or_default()),
296        StrOrF64::F64(v) => Some(v),
297        StrOrF64::None => None,
298    })
299}
300
301#[allow(dead_code)]
302pub fn f32_from_str<'de, D>(deserializer: D) -> Result<f32, D::Error>
303where
304    D: Deserializer<'de>,
305{
306    Ok(match StrOrF32::deserialize(deserializer)? {
307        StrOrF32::String(v) => v.parse().unwrap_or_default(),
308        StrOrF32::F32(v) => v,
309        StrOrF32::None => 0.0f32,
310    })
311}
312
313#[allow(dead_code)]
314pub fn bool_from_str<'de, D>(deserializer: D) -> Result<Option<bool>, D::Error>
315where
316    D: Deserializer<'de>,
317{
318    Ok(match StrOrBool::deserialize(deserializer) {
319        Ok(t) => match t {
320            StrOrBool::String(v) => match v.parse::<bool>() {
321                Ok(tf) => Some(tf),
322                Err(err) => {
323                    log::warn!("Parse erroor {}", err);
324                    None
325                }
326            },
327            StrOrBool::I64(v) => Some(v != 0i64),
328            StrOrBool::Bool(v) => Some(v),
329            StrOrBool::None => Some(false),
330        },
331        Err(err) => {
332            log::warn!("Deserializer erroor {}", err);
333            None
334        }
335    })
336}
337
338pub fn num_to_string(n: i64) -> String {
339    let base_codec = [
340        'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S',
341        'T', 'U', 'V', 'W', 'X', 'Y', 'Z', '2', '3', '4', '5', '7', '8', '9',
342    ];
343    let len = base_codec.len() as i64;
344    let mut t = n;
345    let mut result = "".to_string();
346    while t > 0 {
347        let idx = (t % len) as usize;
348        let ch = base_codec[idx];
349        t /= len;
350        result.insert(0, ch);
351    }
352    result
353}
354
355pub fn number_to_string(n: i64) -> String {
356    let base_codec = ['1', '2', '3', '4', '5', '6', '7', '8', '9', '0'];
357    let len = base_codec.len() as i64;
358    let mut t = n;
359    let mut result = "".to_string();
360    while t > 0 {
361        let idx = (t % len) as usize;
362        let ch = base_codec[idx];
363        t /= len;
364        result.insert(0, ch);
365    }
366    result
367}
368
369pub fn generate_rand_string(len: usize) -> String {
370    let mut retkey = "".to_string();
371
372    while retkey.len() < len {
373        let rng = rand::random::<u16>();
374        let key = num_to_string(rng as i64);
375        retkey += key.as_str();
376    }
377
378    retkey.chars().take(len).collect()
379}
380
381pub fn generate_rand_numberstring(len: usize) -> String {
382    let mut retkey = "".to_string();
383
384    while retkey.len() < len {
385        let rng = rand::random::<u16>();
386        let key = number_to_string(rng as i64);
387        retkey += key.as_str();
388    }
389
390    retkey.chars().take(len).collect()
391}
392
393#[allow(dead_code)]
394pub fn num_to_string_v2(n: i64) -> String {
395    let base_codec = [
396        'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'j', 'k', 'l', 'm', 'n', 'p', 'q', 'r', 's', 't',
397        'u', 'v', 'w', 'x', 'y', 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'J', 'K', 'L', 'M',
398        'N', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', '2', '3', '4', '5', '6', '7',
399        '8', '9',
400    ];
401    let len = base_codec.len() as i64;
402    let mut t = n;
403    let mut result = "".to_string();
404    while t > 0 {
405        let idx = (t % len) as usize;
406        let ch = base_codec[idx];
407        t /= len;
408        result.insert(0, ch);
409    }
410    result
411}
412#[allow(dead_code)]
413pub fn f32_to_decimal(f: f32) -> Option<rbatis::Decimal> {
414    match rbatis::Decimal::from_str(format!("{:.2}", f).as_str()) {
415        Ok(r) => Some(r),
416        Err(_) => None,
417    }
418}
419
420#[allow(dead_code)]
421pub fn f64_to_decimal(f: f64) -> Option<rbatis::Decimal> {
422    println!("f64: value:  {:.2}, {}", f.clone(), f.clone());
423    match rbatis::Decimal::from_str(format!("{:.2}", f).as_str()) {
424        Ok(r) => Some(r),
425        Err(_) => None,
426    }
427}
428
429#[allow(dead_code)]
430pub fn f64_to_decimal_v2(f: f64) -> Option<rbatis::Decimal> {
431    println!("f64: value:  {:.2}, {}", f.clone(), f.clone());
432    let cff = if f < 0.01f64 { 0.00 } else { f };
433
434    match rbatis::Decimal::from_str(format!("{:.2}", cff).as_str()) {
435        Ok(r) => Some(r),
436        Err(_) => None,
437    }
438}
439
440#[allow(dead_code)]
441pub fn decimal_to_f32(dc: Option<rbatis::Decimal>) -> f32 {
442    dc.map(|r| r.to_string().parse::<f32>().unwrap_or_default())
443        .unwrap_or_default()
444}
445
446#[allow(dead_code)]
447pub fn decimal_to_f64(dc: Option<rbatis::Decimal>) -> f64 {
448    dc.map(|r| r.to_string().parse::<f64>().unwrap_or_default())
449        .unwrap_or_default()
450}
451
452#[allow(dead_code)]
453pub fn decimal_compare(dc: Option<rbatis::Decimal>, dc2: Option<rbatis::Decimal>) -> i64 {
454    let f1 = decimal_to_f64(dc);
455    let f2 = decimal_to_f64(dc2);
456
457    if f1 == f2 {
458        0i64
459    } else if f1 > f2 {
460        1i64
461    } else {
462        -1i64
463    }
464}
465
466#[allow(dead_code)]
467pub fn decimal_add(
468    dc: Option<rbatis::Decimal>,
469    dc2: Option<rbatis::Decimal>,
470    ng: bool,
471) -> Option<rbatis::Decimal> {
472    let f1 = decimal_to_f64(dc);
473    let f2 = decimal_to_f64(dc2);
474
475    if ng {
476        f64_to_decimal(f1 - f2)
477    } else {
478        f64_to_decimal(f1 + f2)
479    }
480}
481
482#[allow(dead_code)]
483pub fn make_decimal_negative(dc: Option<rbatis::Decimal>) -> Option<rbatis::Decimal> {
484    match dc {
485        Some(r) => match r.to_string().parse::<f32>() {
486            Ok(t) => f32_to_decimal(-t),
487            Err(_) => f32_to_decimal(0f32),
488        },
489        None => f32_to_decimal(0f32),
490    }
491}
492
493#[allow(dead_code)]
494pub fn int_to_decimal(val: &Option<i64>, mltp: f64) -> Option<rbatis::Decimal> {
495    if val.is_none() {
496        None
497    } else {
498        let fx = val.unwrap() as f64;
499        f64_to_decimal(fx / mltp)
500    }
501}
502
503#[allow(dead_code)]
504pub fn decimal_mult_decimal(
505    val: &Option<rbatis::Decimal>,
506    val2: &Option<rbatis::Decimal>,
507) -> Option<rbatis::Decimal> {
508    f64_to_decimal_v2(decimal_to_f64(val.clone()) * decimal_to_f64(val2.clone()))
509}
510
511#[allow(dead_code)]
512pub fn decimal_plus_decimal(
513    val: &Option<rbatis::Decimal>,
514    val2: &Option<rbatis::Decimal>,
515) -> Option<rbatis::Decimal> {
516    f64_to_decimal_v2(decimal_to_f64(val.clone()) + decimal_to_f64(val2.clone()))
517}
518
519#[allow(dead_code)]
520pub fn generate_rand_string_v2(len: usize) -> String {
521    let mut retkey = "".to_string();
522
523    while retkey.len() < len {
524        let rng = rand::random::<u16>();
525        let key = num_to_string_v2(rng as i64);
526        retkey += key.as_str();
527    }
528
529    retkey.chars().take(len).collect()
530}
531
532#[allow(dead_code)]
533pub fn get_date_string() -> String {
534    let now = SystemTime::now();
535    let date: DateTime<Local> = now.into();
536    let fmt = format!("{}", date.format("%Y%m%d"));
537    fmt
538}
539
540#[allow(dead_code)]
541pub fn format_date_string(dt: &NaiveDateTime) -> String {
542    let fmt = format!("{}", dt.format("%Y年%m月%d日 %H:%M"));
543    fmt
544}
545
546pub fn get_url_encode(c: &str) -> String {
547    use percent_encoding::{utf8_percent_encode, AsciiSet, CONTROLS};
548    const FRAGMENT: &AsciiSet = &CONTROLS
549        .add(b' ')
550        .add(b'"')
551        .add(b'<')
552        .add(b'>')
553        .add(b'`')
554        .add(b'+')
555        .add(b'=')
556        // .add(b'/')
557        ;
558    utf8_percent_encode(c, FRAGMENT).to_string()
559}
560
561pub fn get_url_encode2(c: &str) -> String {
562    urlencoding::encode_binary(c.as_bytes()).into_owned()
563}