cache_any/lib.rs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131
#![cfg_attr(docsrs, feature(doc_auto_cfg))]
#![cfg_attr(feature = "redis", allow(dependency_on_unit_never_type_fallback))]
#![forbid(unsafe_code)]
//! A cache library for Rust.
//!
//! This library provides a trait [`Cache`] and some
//! implementations of it.
//!
//! It defines the basic operations of a cache, for
//! example, [`caches::Cache::get`], [`caches::Cache::set`].
//! All functions are async, because we may use async storage backends.
//!
//! All caches are key-value based.
//!
//! By default, it provides a simple memory cache as example. See [`caches::MemoryCache`].
//! But it's not recommended to use [`caches::MemoryCache`] directly in production.
//!
//! Other caches are available in below features:
//!
//! * `redis`: Use redis as storage backend. See [`caches::RedisCache`].
//! * `mysql`: Use mysql as storage backend. See [`caches::MySqlCache`].
//!
//! ## Usage
//!
//! Add `cache-any` to your `Cargo.toml`:
//!
//! ```toml
//! [dependencies]
//! cache-any = { version = "1", features = ["full"] }
//! ```
//!
//! ## Concepts
//!
//! * **Key**: Specified by the cache implementation. Usually it is a string-like type (&str, String, ...).
//! * **Value**: The value of a cache is a [`Cacheable`] value.
//!
//! [`Cacheable`] is a trait that describes how to convert a `value` to bytes and vice versa.
//!
//! A cache can store any value that implements [`Cacheable`].
//! That is, you can store usize and string (or any other types) at the same time.
//! But you need to know the exact type when you retrieve the value.
//!
//! ## Basic Usage
//!
//! We use [`caches::MemoryCache`] as example.
//!
//! ```rust
//! let cache = MemoryCache::default();
//!
//! // The cache is empty, so `get` returns None.
//! assert!(cache.get::<()>("non-existent-key").await.unwrap().is_none());
//!
//! // [SET a -> 1]
//! cache.set("a", 1).await.unwrap();
//!
//! // [GET a] -> Some(1)
//! let a_value: u8 = cache.get("a").await.unwrap().unwrap();
//! assert_eq!(a_value, 1);
//!
//! // you can do type casting, using u16 instead of u8 as an example.
//! let a_value: u16 = cache.get("a").await.unwrap().unwrap();
//! assert_eq!(a_value, 1);
//!
//! // you can also store [`String`] in the same cache:
//! cache.set("b", String::from("hello")).await.unwrap();
//! let b_value: String = cache.get("b").await.unwrap().unwrap();
//! assert_eq!(b_value, String::from("hello"));
//! ```
//!
//! ## Extend Cacheable
//!
//! You can extend [`Cacheable`] for your own types.
//! For example, you can define a struct and implement [`Cacheable`] for it.
//!
//! ```rust
//! #[derive(serde::Serialize, serde::Deserialize)] // for json
//! struct MyStruct {
//! a: u8,
//! b: String,
//! }
//! ```
//!
//! In this case, we use `serde_json` to convert the struct to bytes and vice versa.
//!
//! ```rust,ignore
//! impl Cacheable for MyStruct {
//! fn to_bytes(&self) -> Vec<u8> {
//! serde_json::to_vec(self).unwrap()
//! }
//!
//! fn from_bytes(bytes: &[u8]) -> anyhow::Result<Self> {
//! let ret = serde_json::from_slice(bytes)?;
//! Ok(ret)
//! }
//! }
//! ```
//!
//! Then you can store `MyStruct` in the cache:
//!
//! ```rust
//! cache.set("my-struct", MyStruct { a: 1, b: String::from("hello") }).await.unwrap();
//! ```
//!
//! ## Work in Progress
//!
//! * Add examples for each cache implementation.
//!
//! ## Contributing
//!
//! Any contributions are welcome.
//!
//! If you find any useful cache implementation,
//! feel free to open an issue or a pull request at [Github](https://github.com/caojen/cache-any).
//!
//! If bugs are found, just file an issue at [Github](https://github.com/caojen/cache-any), and I will fix it **ASAP**.
//!
//! ## License
//!
//! This project is licensed under the MIT License.
mod cacheable;
pub use cacheable::*;
mod caches;
pub use caches::*;
#[test]
fn it_works() {
println!("it works")
}