Skip to main content

crypt_config/convert/
convert.rs

1use std::str::FromStr;
2use std::sync::{Arc, RwLock};
3
4use serde_json::{json, Map, Number, Value};
5
6use crate::config::Config;
7use crate::error::{CryptError, CryptResult};
8
9pub fn encrypt_document(config: &Arc<RwLock<Box<Config>>>, json: &str) -> CryptResult<String> {
10  let config = config.read().unwrap();
11  let v: Value = serde_json::from_str(json)?;
12
13  if let Value::Object(obj) = v {
14    let v = encrypt_object(&config, "", obj);
15    Ok(serde_json::to_string(&v)?)
16  } else {
17    Err(CryptError::InvalidDocument("Document is not a json object".to_string()))
18  }
19}
20
21pub fn decrypt_document(config: &Arc<RwLock<Box<Config>>>, json: &str) -> CryptResult<String> {
22  let config = config.read().unwrap();
23  let v: Value = serde_json::from_str(json)?;
24
25  if let Value::Object(obj) = v {
26    let v = decrypt_element(&config, "", obj)?;
27    Ok(serde_json::to_string(&v)?)
28  } else {
29    Err(CryptError::InvalidDocument("Document is not a json object".to_string()))
30  }
31}
32
33pub fn modify_find_query(config: &Arc<RwLock<Box<Config>>>, query: &str) -> CryptResult<String> {
34  let config = config.read().unwrap();
35  let v: Value = serde_json::from_str(query)?;
36
37  if let Value::Object(obj) = v {
38    let v = modify_find_element(&config, obj)?;
39    Ok(serde_json::to_string(&v)?)
40  } else {
41    Err(CryptError::InvalidDocument("Query is not a json object".to_string()))
42  }
43}
44
45fn encrypt_object<'a>(config: &'a Config, start_point: &'a str, obj: Map<String, Value>) -> Value {
46  let mut map = Map::new();
47  let all_elements = join(start_point, "*");
48  let hasher_version = config.get_hasher_latest_version(&all_elements);
49  if let Some(hasher) = config.get_hasher(hasher_version, &all_elements) {
50    let object = Value::Object(obj.clone());
51    let object_serialized = serde_json::to_string(&object).unwrap();
52    let hash = hasher.encrypt(&object_serialized);
53    map.insert("hashed_field".to_string(), hash_value(hasher_version, &hash));
54  }
55
56  let cipher_version = config.get_cipher_latest_version(&all_elements);
57  if let Some(cipher) = config.get_cipher(cipher_version, &all_elements) {
58    let object = Value::Object(obj.clone());
59    let object_serialized = serde_json::to_string(&object).unwrap();
60    match cipher.encrypt(&object_serialized) {
61      Ok(data) => map.insert("crypted_field".to_string(), crypt_value(cipher_version, cipher.get_salt(), &data)),
62      Err(err) => {
63        println!("[crypt-config][ERROR] Error occured during crypting {} value: {}", all_elements, err);
64        None
65      }
66    };
67  }
68
69  if !map.is_empty() {
70    map.insert("type".to_string(), json!("object"));
71    Value::Object(map)
72  } else {
73    let mut out = Map::new();
74    for (k, v) in obj {
75      let key = join(start_point, k.as_str());
76      match v {
77        Value::Null => out.insert(key, Value::Null),
78        Value::Bool(val) => out.insert(k, encrypt_bool(config, &key, val)),
79        Value::Number(val) => out.insert(k, encrypt_number(config, &key, val)),
80        Value::String(val) => out.insert(k, encrypt_string(config, &key, val)),
81        Value::Array(arr) => out.insert(k, encrypt_array(config, &key, arr)),
82        Value::Object(map) => out.insert(k, encrypt_object(config, &key, map))
83      };
84    }
85
86    Value::Object(out)
87  }
88}
89
90fn encrypt_bool<'a>(config: &'a Config, key: &'a str, obj: bool) -> Value {
91  let mut map = Map::new();
92  let hasher_version = config.get_hasher_latest_version(key);
93  if let Some(hash) = hash_string(&config, hasher_version, key, &obj.to_string()) {
94    map.insert("hashed_field".to_string(), hash);
95  }
96
97  let cipher_version = config.get_cipher_latest_version(key);
98  if let Some(cipher) = config.get_cipher(cipher_version, key) {
99    let resp = if obj { cipher.encrypt("true") } else { cipher.encrypt("false") };
100
101    match resp {
102      Ok(data) => map.insert("crypted_field".to_string(), crypt_value(cipher_version, cipher.get_salt(), &data)),
103      Err(err) => {
104        println!("[crypt-config][ERROR] Error occured during crypting {} value: {}", key, err);
105        None
106      }
107    };
108  }
109
110  if !map.is_empty() {
111    map.insert("type".to_string(), json!("bool"));
112    Value::Object(map)
113  } else {
114    Value::Bool(obj)
115  }
116}
117
118fn encrypt_number<'a>(config: &'a Config, key: &'a str, obj: Number) -> Value {
119  let mut map = Map::new();
120  let val = obj.as_f64().unwrap().to_string();
121  let hasher_version = config.get_hasher_latest_version(key);
122  if let Some(hash) = hash_string(&config, hasher_version, key, &val) {
123    map.insert("hashed_field".to_string(), hash);
124  }
125
126  let cipher_version = config.get_cipher_latest_version(key);
127  if let Some(cipher) = config.get_cipher(cipher_version, key) {
128    match cipher.encrypt(&val) {
129      Ok(data) => map.insert("crypted_field".to_string(), crypt_value(cipher_version, cipher.get_salt(), &data)),
130      Err(err) => {
131        println!("[crypt-config][ERROR] Error occured during crypting {} value: {}", key, err);
132        None
133      }
134    };
135  }
136
137  if !map.is_empty() {
138    map.insert("type".to_string(), json!("number"));
139    Value::Object(map)
140  } else {
141    Value::Number(obj)
142  }
143}
144
145fn encrypt_string<'a>(config: &'a Config, key: &'a str, obj: String) -> Value {
146  let mut map = Map::new();
147  let hasher_version = config.get_hasher_latest_version(key);
148  if let Some(hash) = hash_string(&config, hasher_version, key, &obj) {
149    map.insert("hashed_field".to_string(), hash);
150  }
151
152  let cipher_version = config.get_cipher_latest_version(key);
153  if let Some(cipher) = config.get_cipher(cipher_version, key) {
154    match cipher.encrypt(&obj) {
155      Ok(data) => map.insert("crypted_field".to_string(), crypt_value(cipher_version, cipher.get_salt(), &data)),
156      Err(err) => {
157        println!("[crypt-config][ERROR] Error occured during crypting {} value: {}", key, err);
158        None
159      }
160    };
161  }
162
163  if !map.is_empty() {
164    map.insert("type".to_string(), json!("string"));
165    Value::Object(map)
166  } else {
167    Value::String(obj)
168  }
169}
170
171fn hash_string<'a>(config: &'a Config, version: &'a str, key: &'a str, obj: &str) -> Option<Value> {
172  if let Some(hasher) = config.get_hasher(version, key) {
173    let hash = hasher.encrypt(&obj);
174    Some(hash_value(version, &hash))
175  } else {
176    None
177  }
178}
179
180fn encrypt_array<'a>(config: &'a Config, key: &'a str, arr: Vec<Value>) -> Value {
181  let mut map = Map::new();
182  let all_elements = join(key, "*");
183  let hasher_version = config.get_hasher_latest_version(&all_elements);
184  if let Some(hasher) = config.get_hasher(hasher_version, &all_elements) {
185    let array = Value::Array(arr.clone());
186    let arr_serialized = serde_json::to_string(&array).unwrap();
187    let hash = hasher.encrypt(&arr_serialized);
188    map.insert("hashed_field".to_string(), hash_value(hasher_version, &hash));
189  }
190
191  let cipher_version = config.get_cipher_latest_version(&all_elements);
192  if let Some(cipher) = config.get_cipher(cipher_version, &all_elements) {
193    let array = Value::Array(arr.clone());
194    let arr_serialized = serde_json::to_string(&array).unwrap();
195    match cipher.encrypt(&arr_serialized) {
196      Ok(data) => map.insert("crypted_field".to_string(), crypt_value(cipher_version, cipher.get_salt(), &data)),
197      Err(err) => {
198        println!("[crypt-config][ERROR] Error occured during crypting {} value: {}", key, err);
199        None
200      }
201    };
202  }
203
204  if !map.is_empty() {
205    map.insert("type".to_string(), json!("array"));
206    Value::Object(map)
207  } else {
208    let mut out = Vec::new();
209    for v in arr {
210      match v {
211        Value::Null => out.push(Value::Null),
212        Value::Bool(val) => out.push(encrypt_bool(config, &key, val)),
213        Value::Number(val) => out.push(encrypt_number(config, &key, val)),
214        Value::String(val) => out.push(encrypt_string(config, &key, val)),
215        Value::Array(arr) => out.push(encrypt_array(config, &key, arr)),
216        Value::Object(map) => out.push(encrypt_object(config, &key, map))
217      };
218    }
219
220    Value::Array(out)
221  }
222}
223
224fn decrypt_element<'a>(config: &'a Config, key: &'a str, obj: Map<String, Value>) -> CryptResult<Value> {
225  if is_crypted(&obj) {
226    if let Some(value) = obj.get("type") {
227      if let Some(obj) = obj.get("crypted_field") {
228        if let Value::Object(obj) = obj {
229          if let Value::String(value_type) = value {
230            match value_type.as_str() {
231              "bool" => decrypt_bool(config, &key, obj),
232              "number" => decrypt_number(config, &key, obj),
233              "string" => decrypt_string(config, &key, obj),
234              "array" => decrypt_array(config, &key, obj),
235              "object" => decrypt_object(config, &key, obj),
236              _ => {
237                let message = format!("Invalid value of `{}.type`, got `{}`, expected one of: `bool`, `number`, `string`, `array`, `object`", key, value_type);
238                println!("[crypt-config][ERROR] {}", message);
239                Err(CryptError::InvalidDocument(message))
240              }
241            }
242          } else {
243            let message = format!("`{}.type` must be string type", key);
244            println!("[crypt-config][ERROR] {}", message);
245            Err(CryptError::InvalidDocument(message))
246          }
247        } else {
248          let message = format!("`{}.crypted_fiels` must be object type", key);
249          println!("[crypt-config][ERROR] {}", message);
250          Err(CryptError::InvalidDocument(message))
251        }
252      } else {
253        let message = format!("Invalid crypted field `{}`, lack of `crypted_field` object", key);
254        println!("[crypt-config][ERROR] {}", message);
255        Err(CryptError::InvalidDocument(message))
256      }
257    } else {
258      let message = format!("Invalid crypted field `{}`, lack of `type` information", key);
259      println!("[crypt-config][ERROR] {}", message);
260      Err(CryptError::InvalidDocument(message))
261    }
262  } else {
263    let mut out = Map::new();
264    for (k, v) in obj {
265      let key = join(key, k.as_str());
266      match v {
267        Value::Null => out.insert(key, Value::Null),
268        Value::Bool(val) => out.insert(k, Value::Bool(val)),
269        Value::Number(val) => out.insert(k, Value::Number(val)),
270        Value::String(val) => out.insert(k, Value::String(val)),
271        Value::Array(arr) => match decrypt_array_elements(config, &key, arr) {
272          Ok(val) => out.insert(k, val),
273          Err(err) => return Err(err)
274        },
275        Value::Object(map) => match decrypt_element(config, &key, map) {
276          Ok(val) => out.insert(k, val),
277          Err(err) => return Err(err)
278        }
279      };
280    }
281
282    Ok(Value::Object(out))
283  }
284}
285
286fn decrypt_array_elements<'a>(config: &'a Config, key: &'a str, arr: Vec<Value>) -> CryptResult<Value> {
287  let mut out = Vec::new();
288  for v in arr {
289    match v {
290      Value::Null => out.push(Value::Null),
291      Value::Bool(val) => out.push(Value::Bool(val)),
292      Value::Number(val) => out.push(Value::Number(val)),
293      Value::String(val) => out.push(Value::String(val)),
294      Value::Array(arr) => match decrypt_array_elements(config, &key, arr) {
295        Ok(val) => out.push(val),
296        Err(err) => return Err(err)
297      },
298      Value::Object(map) => match decrypt_element(config, &key, map) {
299        Ok(val) => out.push(val),
300        Err(err) => return Err(err)
301      }
302    };
303  }
304
305  Ok(Value::Array(out))
306}
307
308fn decrypt_bool<'a>(config: &'a Config, key: &'a str, obj: &Map<String, Value>) -> CryptResult<Value> {
309  let string = get_value(config, key, obj)?;
310  match bool::from_str(&string) {
311    Ok(boolean) => Ok(Value::Bool(boolean)),
312    Err(_) => {
313      let message = format!("Field `{}` is not a boolean type", key);
314      println!("[crypt-config][ERROR] {}, the decrypted value is `{}`", message, string);
315      Err(CryptError::InvalidDocument(message))
316    }
317  }
318}
319
320fn decrypt_number<'a>(config: &'a Config, key: &'a str, obj: &Map<String, Value>) -> CryptResult<Value> {
321  let string = get_value(config, key, obj)?;
322  if let Ok(number) = string.parse::<u64>() {
323    Ok(Value::Number(Number::from(number)))
324  } else if let Ok(number) = string.parse::<i64>() {
325    Ok(Value::Number(Number::from(number)))
326  } else if let Ok(number) = string.parse::<f64>() {
327    Ok(Value::Number(Number::from_f64(number).unwrap()))
328  } else {
329    let message = format!("Field `{}` is not a number type", key);
330    println!("[crypt-config][ERROR] {}, the decrypted value is `{}`", message, string);
331    Err(CryptError::InvalidDocument(message))
332  }
333}
334
335fn decrypt_string<'a>(config: &'a Config, key: &'a str, obj: &Map<String, Value>) -> CryptResult<Value> {
336  let string = get_value(config, key, obj)?;
337  Ok(Value::String(string))
338}
339
340fn decrypt_array<'a>(config: &'a Config, key: &'a str, obj: &Map<String, Value>) -> CryptResult<Value> {
341  let key = join(key, "*");
342  let string = get_value(config, &key, obj)?;
343  match serde_json::from_str(&string) {
344    Ok(value) => Ok(value),
345    Err(err) => {
346      let message = format!("Error occured during deserializing `{}`: {}", key, err);
347      println!("[crypt-config][ERROR] {}", message);
348      Err(CryptError::InvalidDocument(message))
349    }
350  }
351}
352
353fn decrypt_object<'a>(config: &'a Config, key: &'a str, obj: &Map<String, Value>) -> CryptResult<Value> {
354  let key = join(key, "*");
355  let string = get_value(config, &key, obj)?;
356  match serde_json::from_str(&string) {
357    Ok(value) => Ok(value),
358    Err(err) => {
359      let message = format!("Error occured during deserializing `{}`: {}", key, err);
360      println!("[crypt-config][ERROR] {}", message);
361      Err(CryptError::InvalidDocument(message))
362    }
363  }
364}
365
366fn hash_value(hasher_version: &str, data: &[u8]) -> Value {
367  let mut map = Map::new();
368
369  map.insert("data".to_string(), hash_data(data));
370  map.insert("version".to_string(), Value::String(hasher_version.to_string()));
371
372  Value::Object(map)
373}
374
375fn hash_data(data: &[u8]) -> Value {
376  Value::String(base64::encode(&data))
377}
378
379fn crypt_value(cipher_version: &str, salt: &[u8], data: &[u8]) -> Value {
380  let mut map = Map::new();
381
382  map.insert("data".to_string(), Value::String(base64::encode(&data)));
383  map.insert("salt".to_string(), Value::String(base64::encode(&salt)));
384  map.insert("version".to_string(), Value::String(cipher_version.to_string()));
385
386  Value::Object(map)
387}
388
389fn get_value<'a>(config: &'a Config, key: &'a str, obj: &Map<String, Value>) -> CryptResult<String> {
390  if let Some((data, salt, version)) = get_data_salt_version(obj) {
391    if let Some(cipher) = config.get_cipher(&version, key) {
392      match cipher.decrypt_with_salt(&data, &salt) {
393        Ok(string) => Ok(string),
394        Err(err) => {
395          println!("[crypt-config][ERROR] Unable to decrypt `{}`, error occured: {}", key, err);
396          Err(err)
397        }
398      }
399    } else {
400      let message = format!("Unable to find cipher of field `{}` with version: {}", key, version);
401      println!("[crypt-config][ERROR] {}", message);
402      Err(CryptError::CipherNotFound(message))
403    }
404  } else {
405    let message = format!("Invalid format of crypted_field for field `{}`, expected: `data`, `salt` and `version`", key);
406    println!("[crypt-config][ERROR] {}", message);
407    Err(CryptError::InvalidDocument(message))
408  }
409}
410
411fn get_data_salt_version(obj: &Map<String, Value>) -> Option<(Vec<u8>, Vec<u8>, &String)> {
412  let data = obj.get("data").and_then(|data| if let Value::String(string) = data { base64::decode(string).ok() } else { None });
413  let salt = obj.get("salt").and_then(|salt| if let Value::String(string) = salt { base64::decode(string).ok() } else { None });
414  let version = obj.get("version").and_then(|version| if let Value::String(string) = version { Some(string) } else { None });
415  if data.is_some() && salt.is_some() && version.is_some() {
416    Some((data.unwrap(), salt.unwrap(), version.unwrap()))
417  } else {
418    None
419  }
420}
421
422fn is_crypted(obj: &Map<String, Value>) -> bool {
423  obj.contains_key("crypted_field") && obj.contains_key("type")
424}
425
426fn join<'a>(a: &'a str, b: &'a str) -> String {
427  if a.is_empty() {
428    b.to_string()
429  } else {
430    String::from(a) + "." + &String::from(b)
431  }
432}
433
434fn modify_find_element(config: &Config, obj: Map<String, Value>) -> CryptResult<Value> {
435  let mut out = Map::new();
436  for (key, val) in obj {
437    if config.is_hasher_exist(&key) {
438      let hashed_key = key.clone() + ".hashed_field.data";
439      let versions = config.get_all_hasher_versions(&key);
440      if versions.is_empty() {
441        out.insert(key, val);
442      } else {
443        match val {
444          Value::Null => out.insert(hashed_key, Value::Null),
445          Value::Bool(val) => out.insert(hashed_key, hash_all_versions(&config, &versions, &key, val.to_string(), "$in")),
446          Value::Number(val) => {
447            let val = val.as_f64().unwrap().to_string();
448            out.insert(hashed_key, hash_all_versions(&config, &versions, &key, val, "$in"))
449          }
450          Value::String(val) => out.insert(hashed_key, hash_all_versions(&config, &versions, &key, val, "$in")),
451          Value::Array(arr) => out.insert(hashed_key, Value::Array(arr)),
452          Value::Object(map) => match hash_operation(config, &versions, &key, map) {
453            Ok(val) => out.insert(hashed_key, val),
454            Err(err) => return Err(err)
455          }
456        };
457      }
458    } else {
459      if let Value::Object(obj) = val {
460        let res = modify_find_element(config, obj);
461        if let Ok(val) = res {
462          out.insert(key.clone(), val);
463        } else {
464          return res;
465        }
466      } else {
467        out.insert(key.clone(), val);
468      }
469    }
470  }
471
472  Ok(Value::Object(out))
473}
474
475fn hash_all_versions(config: &Config, versions: &Vec<&String>, key: &str, string: String, op: &str) -> Value {
476  if versions.len() == 1 {
477    let ver = versions.get(0).unwrap().as_str();
478    let hasher = config.get_hasher(ver, key).unwrap();
479    let hash = hasher.encrypt(&string);
480    hash_data(&hash)
481  } else {
482    let vec = versions
483      .iter()
484      .map(|ver| {
485        let hasher = config.get_hasher(ver, key).unwrap();
486        let hash = hasher.encrypt(&string);
487        hash_data(&hash)
488      })
489      .collect();
490
491    let mut obj = Map::new();
492    obj.insert(op.to_string(), Value::Array(vec));
493    Value::Object(obj)
494  }
495}
496
497fn hash_operation(cfg: &Config, vers: &Vec<&String>, key: &String, obj: Map<String, Value>) -> CryptResult<Value> {
498  let mut out = Map::new();
499  for (op, val) in obj {
500    match op.as_str() {
501      "$eq" => match val {
502        Value::Null => {
503          out.insert(op.clone(), Value::Null);
504        }
505        Value::Bool(val) => {
506          let val = hash_all_versions(&cfg, &vers, &key, val.to_string(), "$in");
507          match val {
508            Value::Object(map) => {
509              out.extend(map.into_iter());
510            }
511            _ => {
512              out.insert(op.clone(), val);
513            }
514          };
515        }
516        Value::Number(val) => {
517          let val = val.as_f64().unwrap().to_string();
518          let val = hash_all_versions(&cfg, &vers, &key, val, "$in");
519          match val {
520            Value::Object(map) => {
521              out.extend(map.into_iter());
522            }
523            _ => {
524              out.insert(op.clone(), val);
525            }
526          };
527        }
528        Value::String(val) => {
529          let val = hash_all_versions(&cfg, &vers, &key, val, "$in");
530          match val {
531            Value::Object(map) => {
532              out.extend(map.into_iter());
533            }
534            _ => {
535              out.insert(op.clone(), val);
536            }
537          };
538        }
539        _ => {
540          out.insert(op.clone(), val);
541        }
542      },
543      "$ne" => match val {
544        Value::Null => {
545          out.insert(op.clone(), Value::Null);
546        }
547        Value::Bool(val) => {
548          let val = hash_all_versions(&cfg, &vers, &key, val.to_string(), "$nin");
549          match val {
550            Value::Object(map) => {
551              out.extend(map.into_iter());
552            }
553            _ => {
554              out.insert(op.clone(), val);
555            }
556          };
557        }
558        Value::Number(val) => {
559          let val = val.as_f64().unwrap().to_string();
560          let val = hash_all_versions(&cfg, &vers, &key, val, "$nin");
561          match val {
562            Value::Object(map) => {
563              out.extend(map.into_iter());
564            }
565            _ => {
566              out.insert(op.clone(), val);
567            }
568          };
569        }
570        Value::String(val) => {
571          let val = hash_all_versions(&cfg, &vers, &key, val, "$nin");
572          match val {
573            Value::Object(map) => {
574              out.extend(map.into_iter());
575            }
576            _ => {
577              out.insert(op.clone(), val);
578            }
579          };
580        }
581        _ => {
582          out.insert(op.clone(), val);
583        }
584      },
585      "$in" | "$nin" => match val {
586        Value::Array(arr) => {
587          let mut out_arr = Vec::new();
588          for val in arr {
589            let hashed_val = match val {
590              Value::Null => Value::Null,
591              Value::Bool(val) => hash_all_versions(&cfg, &vers, &key, val.to_string(), "op"),
592              Value::Number(val) => {
593                let val = val.as_f64().unwrap().to_string();
594                hash_all_versions(&cfg, &vers, &key, val, "op")
595              }
596              Value::String(val) => hash_all_versions(&cfg, &vers, &key, val, "op"),
597              _ => val
598            };
599            match hashed_val {
600              Value::Object(map) => {
601                if let Value::Array(arr) = map.get("op").unwrap() {
602                  out_arr.extend_from_slice(arr);
603                }
604              }
605              _ => out_arr.push(hashed_val)
606            };
607          }
608          out.insert(op.clone(), Value::Array(out_arr));
609        }
610        _ => return Err(CryptError::InvalidQuery(format!("`$in` operation requires object as a value")))
611      },
612      "$not" => match val {
613        Value::Object(obj) => match hash_operation(cfg, vers, &key, obj) {
614          Ok(val) => {
615            out.insert(op.clone(), val);
616          }
617          Err(err) => return Err(err)
618        },
619        _ => return Err(CryptError::InvalidQuery(format!("`$not` operation requires object as a value")))
620      },
621      _ => return Err(CryptError::OperationNotImplemented(key.clone()))
622    };
623  }
624  Ok(Value::Object(out))
625}
626
627#[cfg(test)]
628mod tests {
629  use std::sync::{Arc, RwLock};
630
631  use crate::config::Config;
632  use crate::config::{CipherConfig, CipherData, HasherConfig, HasherData};
633
634  static JSON: &'static str = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":25,"email":"jonny.bravo@cn.com","empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
635
636  #[test]
637  fn hash_single_array_field() {
638    let mut config = Config::new();
639    let salt = [15u8; 16].to_vec();
640    let hash_config = Box::new(HasherConfig::new("pbkdf2".to_string(), 7, salt));
641    let mut hasher = Box::new(HasherData::new());
642    hasher.insert_configuration("1", hash_config);
643    config.insert_hasher("series.*".to_string(), hasher);
644
645    let config = Arc::new(RwLock::new(Box::new(config)));
646    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
647    let expected_json = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":25,"email":"jonny.bravo@cn.com","empty":null,"name":"John","series":{"hashed_field":{"data":"giAS02dOap4MHEx9m5Cl0xIdL37f/QobI29TDyBN0JY=","version":"1"},"type":"array"},"surname":"Bravo"}"#;
648
649    assert_eq!(expected_json, encrypted_json);
650  }
651
652  #[test]
653  fn hash_single_bool_field() {
654    let mut config = Config::new();
655    let salt = [12u8; 16].to_vec();
656    let hash_config = Box::new(HasherConfig::new("pbkdf2".to_string(), 10, salt));
657    let mut hasher = Box::new(HasherData::new());
658    hasher.insert_configuration("1", hash_config);
659    config.insert_hasher("active".to_string(), hasher);
660
661    let config = Arc::new(RwLock::new(Box::new(config)));
662    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
663    let expected_json = r#"{"active":{"hashed_field":{"data":"IkG35GNCWPPOnXYFLQ64zTNIwBadyLvlHi1JWvAXlfU=","version":"1"},"type":"bool"},"address":{"city":"New York","country":"USA"},"age":25,"email":"jonny.bravo@cn.com","empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
664
665    assert_eq!(expected_json, encrypted_json);
666  }
667
668  #[test]
669  fn hash_single_number_field() {
670    let mut config = Config::new();
671    let salt = [15u8; 16].to_vec();
672    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 5, salt));
673    let mut hasher = Box::new(HasherData::new());
674    hasher.insert_configuration("2", hash_config);
675    config.insert_hasher("age".to_string(), hasher);
676
677    let config = Arc::new(RwLock::new(Box::new(config)));
678    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
679    let expected_json = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":{"hashed_field":{"data":"/6TDu9lIIcx5ux5K1Zyo40K2MsYJ+gZe2LU0HZVp3jA=","version":"2"},"type":"number"},"email":"jonny.bravo@cn.com","empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
680
681    assert_eq!(expected_json, encrypted_json);
682  }
683
684  #[test]
685  fn hash_single_string_field() {
686    let mut config = Config::new();
687    let salt = [10u8; 16].to_vec();
688    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 10, salt));
689    let mut hasher = Box::new(HasherData::new());
690    hasher.insert_configuration("1", hash_config);
691    config.insert_hasher("email".to_string(), hasher);
692
693    let config = Arc::new(RwLock::new(Box::new(config)));
694    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
695    let expected_json = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":25,"email":{"hashed_field":{"data":"zzzknrIcELaK5xDZnDWNnT4JSCseusMX0h2WdBdgTfE=","version":"1"},"type":"string"},"empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
696
697    assert_eq!(expected_json, encrypted_json);
698  }
699
700  #[test]
701  fn hash_single_object_field() {
702    let mut config = Config::new();
703    let salt = [14u8; 16].to_vec();
704    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 8, salt));
705    let mut hasher = Box::new(HasherData::new());
706    hasher.insert_configuration("5", hash_config);
707    config.insert_hasher("address.*".to_string(), hasher);
708
709    let config = Arc::new(RwLock::new(Box::new(config)));
710    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
711    let expected_json = r#"{"active":true,"address":{"hashed_field":{"data":"8Gur9ZcF3bgukZQP3mtvQEst0uTG2D50VqlMOyOHTPM=","version":"5"},"type":"object"},"age":25,"email":"jonny.bravo@cn.com","empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
712
713    assert_eq!(expected_json, encrypted_json);
714  }
715
716  #[test]
717  fn hash_two_fields() {
718    let mut config = Config::new();
719
720    let salt = [18u8; 16].to_vec();
721    let hash_config = Box::new(HasherConfig::new("pbkdf2".to_string(), 9, salt));
722    let mut hasher = Box::new(HasherData::new());
723    hasher.insert_configuration("1", hash_config);
724    config.insert_hasher("email".to_string(), hasher);
725
726    let salt = [16u8; 16].to_vec();
727    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 8, salt));
728    let mut hasher = Box::new(HasherData::new());
729    hasher.insert_configuration("1", hash_config);
730    config.insert_hasher("address.*".to_string(), hasher);
731
732    let config = Arc::new(RwLock::new(Box::new(config)));
733    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
734    let expected_json = r#"{"active":true,"address":{"hashed_field":{"data":"WBlBT6nFvqWJ+1bxbtPAX+H0K/FMAq3FfC9kaZq/CIg=","version":"1"},"type":"object"},"age":25,"email":{"hashed_field":{"data":"rCknP8kn627oZ96uTiR7d+hZTyS8QZImUazpF8ryIxs=","version":"1"},"type":"string"},"empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
735
736    assert_eq!(expected_json, encrypted_json);
737  }
738
739  #[test]
740  fn crypt_single_array_field() {
741    let mut config = Config::new();
742    let secret = [19u8; 32].to_vec();
743    let cipher_config = Box::new(CipherConfig::new("aes_cbc".to_string(), secret));
744    let mut cipher = Box::new(CipherData::new());
745    cipher.insert_configuration("1", cipher_config);
746    config.insert_cipher("series.*".to_string(), cipher);
747
748    let config = Arc::new(RwLock::new(Box::new(config)));
749    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
750
751    assert_ne!(JSON, encrypted_json);
752  }
753
754  #[test]
755  fn crypt_single_bool_field() {
756    let mut config = Config::new();
757    let secret = [21u8; 32].to_vec();
758    let cipher_config = Box::new(CipherConfig::new("aes_cfb1".to_string(), secret));
759    let mut cipher = Box::new(CipherData::new());
760    cipher.insert_configuration("4", cipher_config);
761    config.insert_cipher("active".to_string(), cipher);
762
763    let config = Arc::new(RwLock::new(Box::new(config)));
764    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
765
766    assert_ne!(JSON, encrypted_json);
767  }
768
769  #[test]
770  fn crypt_single_number_field() {
771    let mut config = Config::new();
772    let secret = [22u8; 32].to_vec();
773    let cipher_config = Box::new(CipherConfig::new("aes_ecb".to_string(), secret));
774    let mut cipher = Box::new(CipherData::new());
775    cipher.insert_configuration("3", cipher_config);
776    config.insert_cipher("age".to_string(), cipher);
777
778    let config = Arc::new(RwLock::new(Box::new(config)));
779    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
780
781    assert_ne!(JSON, encrypted_json);
782  }
783
784  #[test]
785  fn crypt_single_string_field() {
786    let mut config = Config::new();
787    let secret = [22u8; 32].to_vec();
788    let cipher_config = Box::new(CipherConfig::new("aes_ecb".to_string(), secret));
789    let mut cipher = Box::new(CipherData::new());
790    cipher.insert_configuration("2", cipher_config);
791    config.insert_cipher("email".to_string(), cipher);
792
793    let config = Arc::new(RwLock::new(Box::new(config)));
794    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
795
796    assert_ne!(JSON, encrypted_json);
797  }
798
799  #[test]
800  fn crypt_single_object_field() {
801    let mut config = Config::new();
802    let secret = [22u8; 32].to_vec();
803    let cipher_config = Box::new(CipherConfig::new("aes_ecb".to_string(), secret));
804    let mut cipher = Box::new(CipherData::new());
805    cipher.insert_configuration("2", cipher_config);
806    config.insert_cipher("address.*".to_string(), cipher);
807
808    let config = Arc::new(RwLock::new(Box::new(config)));
809    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
810
811    assert_ne!(JSON, encrypted_json);
812  }
813
814  #[test]
815  fn crypt_two_fields() {
816    let mut config = Config::new();
817
818    let secret = [22u8; 32].to_vec();
819    let cipher_config = Box::new(CipherConfig::new("aes_ecb".to_string(), secret));
820    let mut cipher = Box::new(CipherData::new());
821    cipher.insert_configuration("2", cipher_config);
822    config.insert_cipher("address.*".to_string(), cipher);
823
824    let secret = [23u8; 32].to_vec();
825    let cipher_config = Box::new(CipherConfig::new("aes_cbc".to_string(), secret));
826    let mut cipher = Box::new(CipherData::new());
827    cipher.insert_configuration("7", cipher_config);
828    config.insert_cipher("email".to_string(), cipher);
829
830    let config = Arc::new(RwLock::new(Box::new(config)));
831    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
832
833    assert_ne!(JSON, encrypted_json);
834  }
835
836  #[test]
837  fn crypt_and_hash_same_field() {
838    let mut config = Config::new();
839
840    let secret = [22u8; 32].to_vec();
841    let cipher_config = Box::new(CipherConfig::new("aes_ecb".to_string(), secret));
842    let mut cipher = Box::new(CipherData::new());
843    cipher.insert_configuration("2", cipher_config);
844    config.insert_cipher("address.*".to_string(), cipher);
845
846    let salt = [24u8; 16].to_vec();
847    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 8, salt));
848    let mut hasher = Box::new(HasherData::new());
849    hasher.insert_configuration("4", hash_config);
850    config.insert_hasher("address.*".to_string(), hasher);
851
852    let config = Arc::new(RwLock::new(Box::new(config)));
853    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
854
855    assert_ne!(JSON, encrypted_json);
856  }
857
858  #[test]
859  fn crypt_and_hash_other_fields() {
860    let mut config = Config::new();
861
862    let secret = [23u8; 32].to_vec();
863    let cipher_config = Box::new(CipherConfig::new("aes_cbc".to_string(), secret));
864    let mut cipher = Box::new(CipherData::new());
865    cipher.insert_configuration("2", cipher_config);
866    config.insert_cipher("address.*".to_string(), cipher);
867
868    let salt = [25u8; 16].to_vec();
869    let hash_config = Box::new(HasherConfig::new("pbkdf2".to_string(), 8, salt));
870    let mut hasher = Box::new(HasherData::new());
871    hasher.insert_configuration("4", hash_config);
872    config.insert_hasher("email".to_string(), hasher);
873
874    let config = Arc::new(RwLock::new(Box::new(config)));
875    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
876
877    assert_ne!(JSON, encrypted_json);
878  }
879
880  #[test]
881  fn encrypt_decrypt_single_array_field() {
882    let mut config = Config::new();
883    let secret = [28u8; 32].to_vec();
884    let cipher_config = Box::new(CipherConfig::new("aes_cfb1".to_string(), secret));
885    let mut cipher = Box::new(CipherData::new());
886    cipher.insert_configuration("5", cipher_config);
887    config.insert_cipher("series.*".to_string(), cipher);
888
889    let config = Arc::new(RwLock::new(Box::new(config)));
890    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
891    let decrypted_json = super::decrypt_document(&config, &encrypted_json).unwrap();
892
893    assert_eq!(JSON, decrypted_json);
894  }
895
896  #[test]
897  fn encrypt_decrypt_single_bool_field() {
898    let mut config = Config::new();
899    let secret = [21u8; 32].to_vec();
900    let cipher_config = Box::new(CipherConfig::new("aes_cfb1".to_string(), secret));
901    let mut cipher = Box::new(CipherData::new());
902    cipher.insert_configuration("4", cipher_config);
903    config.insert_cipher("active".to_string(), cipher);
904
905    let config = Arc::new(RwLock::new(Box::new(config)));
906    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
907    let decrypted_json = super::decrypt_document(&config, &encrypted_json).unwrap();
908
909    assert_eq!(JSON, decrypted_json);
910  }
911
912  #[test]
913  fn encrypt_decrypt_single_number_field() {
914    let mut config = Config::new();
915    let secret = [26u8; 32].to_vec();
916    let cipher_config = Box::new(CipherConfig::new("aes_ecb".to_string(), secret));
917    let mut cipher = Box::new(CipherData::new());
918    cipher.insert_configuration("2", cipher_config);
919    config.insert_cipher("age".to_string(), cipher);
920
921    let config = Arc::new(RwLock::new(Box::new(config)));
922    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
923    let decrypted_json = super::decrypt_document(&config, &encrypted_json).unwrap();
924
925    assert_eq!(JSON, decrypted_json);
926  }
927
928  #[test]
929  fn encrypt_decrypt_single_string_field() {
930    let mut config = Config::new();
931    let secret = [27u8; 32].to_vec();
932    let cipher_config = Box::new(CipherConfig::new("aes_ecb".to_string(), secret));
933    let mut cipher = Box::new(CipherData::new());
934    cipher.insert_configuration("2", cipher_config);
935    config.insert_cipher("address.city".to_string(), cipher);
936
937    let config = Arc::new(RwLock::new(Box::new(config)));
938    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
939    let decrypted_json = super::decrypt_document(&config, &encrypted_json).unwrap();
940
941    assert_eq!(JSON, decrypted_json);
942  }
943
944  #[test]
945  fn encrypt_decrypt_single_object_field() {
946    let mut config = Config::new();
947    let secret = [27u8; 32].to_vec();
948    let cipher_config = Box::new(CipherConfig::new("aes_cbc".to_string(), secret));
949    let mut cipher = Box::new(CipherData::new());
950    cipher.insert_configuration("5", cipher_config);
951    config.insert_cipher("address.*".to_string(), cipher);
952
953    let config = Arc::new(RwLock::new(Box::new(config)));
954    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
955    let decrypted_json = super::decrypt_document(&config, &encrypted_json).unwrap();
956
957    assert_eq!(JSON, decrypted_json);
958  }
959
960  #[test]
961  fn eq_query_single_string_field() {
962    let mut config = Config::new();
963    let salt = [10u8; 16].to_vec();
964    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 10, salt));
965    let mut hasher = Box::new(HasherData::new());
966    hasher.insert_configuration("1", hash_config);
967    config.insert_hasher("email".to_string(), hasher);
968
969    let config = Arc::new(RwLock::new(Box::new(config)));
970    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
971    let expected_json = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":25,"email":{"hashed_field":{"data":"zzzknrIcELaK5xDZnDWNnT4JSCseusMX0h2WdBdgTfE=","version":"1"},"type":"string"},"empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
972
973    assert_eq!(expected_json, encrypted_json);
974
975    let query = r#"{"email": "jonny.bravo@cn.com"}"#;
976    let new_query = super::modify_find_query(&config, &query).unwrap();
977
978    assert_eq!(r#"{"email.hashed_field.data":"zzzknrIcELaK5xDZnDWNnT4JSCseusMX0h2WdBdgTfE="}"#, new_query);
979
980    let query = r#"{"email": { "$eq": "jonny.bravo@cn.com"}}"#;
981    let new_query = super::modify_find_query(&config, &query).unwrap();
982
983    assert_eq!(r#"{"email.hashed_field.data":{"$eq":"zzzknrIcELaK5xDZnDWNnT4JSCseusMX0h2WdBdgTfE="}}"#, new_query);
984  }
985
986  #[test]
987  fn ne_query_single_number_field() {
988    let mut config = Config::new();
989    let salt = [10u8; 16].to_vec();
990    let hash_config = Box::new(HasherConfig::new("pbkdf2".to_string(), 10, salt));
991    let mut hasher = Box::new(HasherData::new());
992    hasher.insert_configuration("2", hash_config);
993    config.insert_hasher("age".to_string(), hasher);
994
995    let config = Arc::new(RwLock::new(Box::new(config)));
996    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
997    let expected_json = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":{"hashed_field":{"data":"ONSmub8QuVOyJSCaSLBPuG6AIvE/nzZ3QUhCrJ9bJKs=","version":"2"},"type":"number"},"email":"jonny.bravo@cn.com","empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
998
999    assert_eq!(expected_json, encrypted_json);
1000
1001    let query = r#"{"age": {"$ne": 25}}"#;
1002    let new_query = super::modify_find_query(&config, &query).unwrap();
1003
1004    assert_eq!(r#"{"age.hashed_field.data":{"$ne":"ONSmub8QuVOyJSCaSLBPuG6AIvE/nzZ3QUhCrJ9bJKs="}}"#, new_query);
1005  }
1006
1007  #[test]
1008  fn in_query_single_string_field_two_versions() {
1009    let mut config = Config::new();
1010    let mut hasher = Box::new(HasherData::new());
1011
1012    let salt = [10u8; 16].to_vec();
1013    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 10, salt));
1014    hasher.insert_configuration("1", hash_config);
1015
1016    let salt = [12u8; 16].to_vec();
1017    let hash_config = Box::new(HasherConfig::new("pbkdf2".to_string(), 5, salt));
1018    hasher.insert_configuration("2", hash_config);
1019
1020    config.insert_hasher("email".to_string(), hasher);
1021
1022    let config = Arc::new(RwLock::new(Box::new(config)));
1023    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
1024    let expected_json = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":25,"email":{"hashed_field":{"data":"S64dayjXpy3SBhgmirr9Umanb3VWT4u3JYkRKNamJAA=","version":"2"},"type":"string"},"empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
1025
1026    assert_eq!(expected_json, encrypted_json);
1027
1028    let query = r#"{"email": {"$in":["jonny.bravo@cn.com", "jonny.bravo@cn2.com"]}}"#;
1029    let new_query = super::modify_find_query(&config, &query).unwrap();
1030
1031    // {"email.hashed_field.data":{"$in":["zzzknrIcELaK5xDZnDWNnT4JSCseusMX0h2WdBdgTfE=","S64dayjXpy3SBhgmirr9Umanb3VWT4u3JYkRKNamJAA=","EXzdYiTBuBjW2bmiPlCBkQnmVUpzkKTbM4HN9SDSXsI=","WoGwQEvQWrIvdC0EfVSiyvdmcC5kKT+OzpeEI2wOb9U="]}}
1032    assert!(new_query.starts_with(r#"{"email.hashed_field.data":{"$in":["#));
1033    assert!(new_query.contains("zzzknrIcELaK5xDZnDWNnT4JSCseusMX0h2WdBdgTfE="));
1034    assert!(new_query.contains("S64dayjXpy3SBhgmirr9Umanb3VWT4u3JYkRKNamJAA="));
1035    assert!(new_query.contains("EXzdYiTBuBjW2bmiPlCBkQnmVUpzkKTbM4HN9SDSXsI="));
1036    assert!(new_query.contains("WoGwQEvQWrIvdC0EfVSiyvdmcC5kKT+OzpeEI2wOb9U="));
1037  }
1038
1039  #[test]
1040  fn eq_query_single_string_field_two_versions() {
1041    let mut config = Config::new();
1042    let mut hasher = Box::new(HasherData::new());
1043
1044    let salt = [10u8; 16].to_vec();
1045    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 10, salt));
1046    hasher.insert_configuration("1", hash_config);
1047
1048    let salt = [12u8; 16].to_vec();
1049    let hash_config = Box::new(HasherConfig::new("pbkdf2".to_string(), 5, salt));
1050    hasher.insert_configuration("2", hash_config);
1051
1052    config.insert_hasher("email".to_string(), hasher);
1053
1054    let config = Arc::new(RwLock::new(Box::new(config)));
1055    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
1056    let expected_json = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":25,"email":{"hashed_field":{"data":"S64dayjXpy3SBhgmirr9Umanb3VWT4u3JYkRKNamJAA=","version":"2"},"type":"string"},"empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
1057
1058    assert_eq!(expected_json, encrypted_json);
1059
1060    let query = r#"{"email": {"$eq":"jonny.bravo@cn.com"}}"#;
1061    let new_query = super::modify_find_query(&config, &query).unwrap();
1062
1063    assert!(new_query.starts_with(r#"{"email.hashed_field.data":{"$in":["#));
1064    assert!(new_query.contains("zzzknrIcELaK5xDZnDWNnT4JSCseusMX0h2WdBdgTfE="));
1065    assert!(new_query.contains("S64dayjXpy3SBhgmirr9Umanb3VWT4u3JYkRKNamJAA="));
1066  }
1067
1068  #[test]
1069  fn ne_query_single_string_field_two_versions() {
1070    let mut config = Config::new();
1071    let mut hasher = Box::new(HasherData::new());
1072
1073    let salt = [10u8; 16].to_vec();
1074    let hash_config = Box::new(HasherConfig::new("bcrypt".to_string(), 10, salt));
1075    hasher.insert_configuration("1", hash_config);
1076
1077    let salt = [12u8; 16].to_vec();
1078    let hash_config = Box::new(HasherConfig::new("pbkdf2".to_string(), 5, salt));
1079    hasher.insert_configuration("2", hash_config);
1080
1081    config.insert_hasher("email".to_string(), hasher);
1082
1083    let config = Arc::new(RwLock::new(Box::new(config)));
1084    let encrypted_json = super::encrypt_document(&config, JSON).unwrap();
1085    let expected_json = r#"{"active":true,"address":{"city":"New York","country":"USA"},"age":25,"email":{"hashed_field":{"data":"S64dayjXpy3SBhgmirr9Umanb3VWT4u3JYkRKNamJAA=","version":"2"},"type":"string"},"empty":null,"name":"John","series":[1,2,3],"surname":"Bravo"}"#;
1086
1087    assert_eq!(expected_json, encrypted_json);
1088
1089    let query = r#"{"email": {"$ne":"jonny.bravo@cn.com"}}"#;
1090    let new_query = super::modify_find_query(&config, &query).unwrap();
1091
1092    assert!(new_query.starts_with(r#"{"email.hashed_field.data":{"$nin":["#));
1093    assert!(new_query.contains("zzzknrIcELaK5xDZnDWNnT4JSCseusMX0h2WdBdgTfE="));
1094    assert!(new_query.contains("S64dayjXpy3SBhgmirr9Umanb3VWT4u3JYkRKNamJAA="));
1095  }
1096}