Restructure files and add kameo-actors package
This commit is contained in:
parent
50f8604290
commit
0438032f18
2
.gitignore
vendored
2
.gitignore
vendored
@ -1 +1 @@
|
||||
/target
|
||||
target/
|
291
Cargo.lock
generated
291
Cargo.lock
generated
@ -17,6 +17,13 @@ version = "2.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "512761e0bb2578dd7380c6baaa0f4ce03e84f95e960231d1dec8bf4d7d6e2627"
|
||||
|
||||
[[package]]
|
||||
name = "alpha"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"tokio",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "autocfg"
|
||||
version = "1.4.0"
|
||||
@ -56,12 +63,130 @@ version = "1.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
|
||||
|
||||
[[package]]
|
||||
name = "dyn-clone"
|
||||
version = "1.0.17"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0d6ef0072f8a535281e4876be788938b528e9a1d43900b82c2569af7da799125"
|
||||
|
||||
[[package]]
|
||||
name = "either"
|
||||
version = "1.13.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "60b1af1c220855b6ceac025d3f6ecdd2b7c4894bfe9cd9bda4fbb4bc7c0d4cf0"
|
||||
|
||||
[[package]]
|
||||
name = "futures"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "65bc07b1a8bc7c85c5f2e110c476c7389b4554ba72af57d8445ea63a576b0876"
|
||||
dependencies = [
|
||||
"futures-channel",
|
||||
"futures-core",
|
||||
"futures-executor",
|
||||
"futures-io",
|
||||
"futures-sink",
|
||||
"futures-task",
|
||||
"futures-util",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-channel"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2dff15bf788c671c1934e366d07e30c1814a8ef514e1af724a602e8a2fbe1b10"
|
||||
dependencies = [
|
||||
"futures-core",
|
||||
"futures-sink",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-core"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "05f29059c0c2090612e8d742178b0580d2dc940c837851ad723096f87af6663e"
|
||||
|
||||
[[package]]
|
||||
name = "futures-executor"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1e28d1d997f585e54aebc3f97d39e72338912123a67330d723fdbb564d646c9f"
|
||||
dependencies = [
|
||||
"futures-core",
|
||||
"futures-task",
|
||||
"futures-util",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-io"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9e5c1b78ca4aae1ac06c48a526a655760685149f0d465d21f37abfe57ce075c6"
|
||||
|
||||
[[package]]
|
||||
name = "futures-macro"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "162ee34ebcb7c64a8abebc059ce0fee27c2262618d7b60ed8faf72fef13c3650"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-sink"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e575fab7d1e0dcb8d0c7bcf9a63ee213816ab51902e6d244a95819acacf1d4f7"
|
||||
|
||||
[[package]]
|
||||
name = "futures-task"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f90f7dce0722e95104fcb095585910c0977252f286e354b5e3bd38902cd99988"
|
||||
|
||||
[[package]]
|
||||
name = "futures-util"
|
||||
version = "0.3.31"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9fa08315bb612088cc391249efdc3bc77536f16c91f6cf495e6fbe85b20a4a81"
|
||||
dependencies = [
|
||||
"futures-channel",
|
||||
"futures-core",
|
||||
"futures-io",
|
||||
"futures-macro",
|
||||
"futures-sink",
|
||||
"futures-task",
|
||||
"memchr",
|
||||
"pin-project-lite",
|
||||
"pin-utils",
|
||||
"slab",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "getrandom"
|
||||
version = "0.2.15"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c4567c8db10ae91089c99af84c68c38da3ec2f087c3f82960bcdbf3656b6f4d7"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"libc",
|
||||
"wasi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "gimli"
|
||||
version = "0.31.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "07e28edb80900c19c28f1072f2e8aeca7fa06b23cd4169cefe1af5aa3260783f"
|
||||
|
||||
[[package]]
|
||||
name = "heck"
|
||||
version = "0.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea"
|
||||
|
||||
[[package]]
|
||||
name = "hermit-abi"
|
||||
version = "0.3.9"
|
||||
@ -69,10 +194,57 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d231dfb89cfffdbc30e7fc41579ed6066ad03abda9e567ccafae602b97ec5024"
|
||||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.159"
|
||||
name = "itertools"
|
||||
version = "0.13.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "561d97a539a36e26a9a5fad1ea11a3039a67714694aaa379433e580854bc3dc5"
|
||||
checksum = "413ee7dfc52ee1a4949ceeb7dbc8a33f2d6c088194d9f922fb8318faf1f01186"
|
||||
dependencies = [
|
||||
"either",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "kameo"
|
||||
version = "0.12.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "94449a0728ce1ec7345496588007bec699c4b52c525159ede8830a6fc14dd4fa"
|
||||
dependencies = [
|
||||
"dyn-clone",
|
||||
"futures",
|
||||
"itertools",
|
||||
"kameo_macros",
|
||||
"once_cell",
|
||||
"serde",
|
||||
"tokio",
|
||||
"tokio-stream",
|
||||
"tracing",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "kameo-actors"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"kameo",
|
||||
"tokio",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "kameo_macros"
|
||||
version = "0.12.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ddec4971b183c643aa91d83f85effe39c7d27b2914a54b06a979cd87b13a79b7"
|
||||
dependencies = [
|
||||
"heck",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"uuid",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.161"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8e9489c2807c139ffd9c1794f4af0ebe86a828db53ecdc7fea2111d0fed085d1"
|
||||
|
||||
[[package]]
|
||||
name = "lock_api"
|
||||
@ -111,6 +283,13 @@ dependencies = [
|
||||
"windows-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "my-actors"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"tokio",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "object"
|
||||
version = "0.36.5"
|
||||
@ -120,6 +299,12 @@ dependencies = [
|
||||
"memchr",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "once_cell"
|
||||
version = "1.20.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1261fe7e33c73b354eab43b1273a57c8f967d0391e80353e51f764ac02cf6775"
|
||||
|
||||
[[package]]
|
||||
name = "parking_lot"
|
||||
version = "0.12.3"
|
||||
@ -150,10 +335,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bda66fc9667c18cb2758a2ac84d1167245054bcf85d5d1aaa6923f45801bdd02"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.86"
|
||||
name = "pin-utils"
|
||||
version = "0.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5e719e8df665df0d1c8fbfd238015744736151d4445ec0836b8e628aae103b77"
|
||||
checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.88"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7c3a7fc5db1e57d5a779a352c8cdb57b29aa4c40cc69c3a68a7fedc815fbf2f9"
|
||||
dependencies = [
|
||||
"unicode-ident",
|
||||
]
|
||||
@ -188,6 +379,26 @@ version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49"
|
||||
|
||||
[[package]]
|
||||
name = "serde"
|
||||
version = "1.0.210"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c8e3592472072e6e22e0a54d5904d9febf8508f65fb8552499a1abc7d1078c3a"
|
||||
dependencies = [
|
||||
"serde_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_derive"
|
||||
version = "1.0.210"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "243902eda00fad750862fc144cea25caca5e20d615af0a81bee94ca738f1df1f"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "signal-hook-registry"
|
||||
version = "1.4.2"
|
||||
@ -197,6 +408,15 @@ dependencies = [
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "slab"
|
||||
version = "0.4.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8f92a496fb766b417c996b9c5e57daf2f7ad3b0bebe1ccfca4856390e3d3bb67"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "smallvec"
|
||||
version = "1.13.2"
|
||||
@ -239,16 +459,10 @@ dependencies = [
|
||||
"signal-hook-registry",
|
||||
"socket2",
|
||||
"tokio-macros",
|
||||
"tracing",
|
||||
"windows-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tokio-fun"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"tokio",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tokio-macros"
|
||||
version = "2.4.0"
|
||||
@ -260,12 +474,63 @@ dependencies = [
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tokio-stream"
|
||||
version = "0.1.16"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4f4e6ce100d0eb49a2734f8c0812bcd324cf357d21810932c5df6b96ef2b86f1"
|
||||
dependencies = [
|
||||
"futures-core",
|
||||
"pin-project-lite",
|
||||
"tokio",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tracing"
|
||||
version = "0.1.40"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c3523ab5a71916ccf420eebdf5521fcef02141234bbc0b8a49f2fdc4544364ef"
|
||||
dependencies = [
|
||||
"pin-project-lite",
|
||||
"tracing-attributes",
|
||||
"tracing-core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tracing-attributes"
|
||||
version = "0.1.27"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "34704c8d6ebcbc939824180af020566b01a7c01f80641264eba0999f6c2b6be7"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tracing-core"
|
||||
version = "0.1.32"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c06d3da6113f116aaee68e4d601191614c9053067f9ab7f6edbcb161237daa54"
|
||||
dependencies = [
|
||||
"once_cell",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "unicode-ident"
|
||||
version = "1.0.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e91b56cd4cadaeb79bbf1a5645f6b4f8dc5bde8834ad5894a8db35fda9efa1fe"
|
||||
|
||||
[[package]]
|
||||
name = "uuid"
|
||||
version = "1.11.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f8c5f0a0af699448548ad1a2fbf920fb4bee257eae39953ba95cb84891a0446a"
|
||||
dependencies = [
|
||||
"getrandom",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasi"
|
||||
version = "0.11.0+wasi-snapshot-preview1"
|
||||
|
10
Cargo.toml
10
Cargo.toml
@ -1,7 +1,3 @@
|
||||
[package]
|
||||
name = "tokio-fun"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
tokio = { version = "1.40.0", features = ["full"] }
|
||||
[workspace]
|
||||
resolver = "2"
|
||||
members = ["alpha", "kameo-actors", "my-actors"]
|
||||
|
@ -4,5 +4,11 @@ Learning Tokio and testing its capabilities.
|
||||
To run an example use:
|
||||
|
||||
```sh
|
||||
cargo run --bin <name-of-file-in-src/bin>
|
||||
cargo run -p <name-of-directory>
|
||||
```
|
||||
|
||||
e.g.
|
||||
|
||||
```sh
|
||||
cargo run -p alpha
|
||||
```
|
1
alpha/.gitignore
vendored
Normal file
1
alpha/.gitignore
vendored
Normal file
@ -0,0 +1 @@
|
||||
/target
|
7
alpha/Cargo.toml
Normal file
7
alpha/Cargo.toml
Normal file
@ -0,0 +1,7 @@
|
||||
[package]
|
||||
name = "alpha"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
tokio = { version = "1.40.0", features = ["full"] }
|
@ -23,4 +23,4 @@ async fn main() {
|
||||
|
||||
let _ = t1.await;
|
||||
let _ = t2.await;
|
||||
}
|
||||
}
|
1
kameo-actors/.gitignore
vendored
Normal file
1
kameo-actors/.gitignore
vendored
Normal file
@ -0,0 +1 @@
|
||||
/target
|
8
kameo-actors/Cargo.toml
Normal file
8
kameo-actors/Cargo.toml
Normal file
@ -0,0 +1,8 @@
|
||||
[package]
|
||||
name = "kameo-actors"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
kameo = "0.12.2"
|
||||
tokio = { version = "1.40.0", features = ["full"] }
|
34
kameo-actors/src/main.rs
Normal file
34
kameo-actors/src/main.rs
Normal file
@ -0,0 +1,34 @@
|
||||
use std::error::Error;
|
||||
|
||||
use kameo::request::MessageSend;
|
||||
use kameo::{spawn, Actor};
|
||||
use kameo::message::{Message, Context};
|
||||
|
||||
#[derive(Actor)]
|
||||
pub struct HelloWorldActor;
|
||||
|
||||
pub struct Greet(String);
|
||||
|
||||
impl Message<Greet> for HelloWorldActor {
|
||||
type Reply = ();
|
||||
|
||||
async fn handle(
|
||||
&mut self,
|
||||
Greet(greeting): Greet,
|
||||
_: Context<'_, Self, Self::Reply>,
|
||||
) -> Self::Reply {
|
||||
println!("{greeting}");
|
||||
}
|
||||
}
|
||||
|
||||
#[tokio::main]
|
||||
async fn main() -> Result<(), Box<dyn Error>> {
|
||||
let actor_ref = spawn(HelloWorldActor);
|
||||
|
||||
actor_ref
|
||||
.tell(Greet("Hello world".to_string()))
|
||||
.send()
|
||||
.await?;
|
||||
|
||||
Ok(())
|
||||
}
|
1
my-actors/.gitignore
vendored
Normal file
1
my-actors/.gitignore
vendored
Normal file
@ -0,0 +1 @@
|
||||
/target
|
7
my-actors/Cargo.toml
Normal file
7
my-actors/Cargo.toml
Normal file
@ -0,0 +1,7 @@
|
||||
[package]
|
||||
name = "my-actors"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
tokio = { version = "1.40.0", features = ["full"] }
|
@ -1,4 +1,7 @@
|
||||
use tokio::sync::{mpsc::{Receiver, Sender}, oneshot};
|
||||
use tokio::sync::{
|
||||
mpsc::{Receiver, Sender},
|
||||
oneshot,
|
||||
};
|
||||
|
||||
struct DatabaseStore {
|
||||
counter: u64,
|
||||
@ -18,13 +21,13 @@ struct Database {
|
||||
}
|
||||
|
||||
enum DatabaseQuery {
|
||||
Increment{
|
||||
Increment {
|
||||
resp: oneshot::Sender<DatabaseResponse>,
|
||||
},
|
||||
Decrement{
|
||||
Decrement {
|
||||
resp: oneshot::Sender<DatabaseResponse>,
|
||||
},
|
||||
Get{
|
||||
Get {
|
||||
resp: oneshot::Sender<DatabaseResponse>,
|
||||
},
|
||||
}
|
||||
@ -62,15 +65,16 @@ async fn main() {
|
||||
impl Database {
|
||||
fn new(store_init: DatabaseStore) -> Database {
|
||||
let (tx, rx) = tokio::sync::mpsc::channel(32);
|
||||
let mut manager = DatabaseManager{ store: store_init, queries: rx };
|
||||
let mut manager = DatabaseManager {
|
||||
store: store_init,
|
||||
queries: rx,
|
||||
};
|
||||
tokio::spawn(async move {
|
||||
manager.run().await;
|
||||
manager.run().await;
|
||||
});
|
||||
|
||||
Database{
|
||||
client: DatabaseClient{
|
||||
queries: tx,
|
||||
},
|
||||
Database {
|
||||
client: DatabaseClient { queries: tx },
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -88,7 +92,7 @@ impl DatabaseManager {
|
||||
|
||||
fn handle_query(&mut self, query: DatabaseQuery) {
|
||||
match query {
|
||||
DatabaseQuery::Increment{ resp } => {
|
||||
DatabaseQuery::Increment { resp } => {
|
||||
self.store.counter += 1;
|
||||
let _ = resp.send(DatabaseResponse::Ok);
|
||||
}
|
||||
@ -105,30 +109,34 @@ impl DatabaseManager {
|
||||
|
||||
impl DatabaseStore {
|
||||
fn new() -> DatabaseStore {
|
||||
DatabaseStore{
|
||||
counter: 0,
|
||||
}
|
||||
DatabaseStore { counter: 0 }
|
||||
}
|
||||
}
|
||||
|
||||
impl DatabaseClient {
|
||||
async fn increment(&self) -> Result<(), ()> {
|
||||
let (tx, rx) = tokio::sync::oneshot::channel();
|
||||
let _ = self.queries.send(DatabaseQuery::Increment { resp: tx }).await;
|
||||
|
||||
let _ = self
|
||||
.queries
|
||||
.send(DatabaseQuery::Increment { resp: tx })
|
||||
.await;
|
||||
|
||||
match rx.await {
|
||||
Ok(_) => Ok(()),
|
||||
Err(_) => Err(())
|
||||
Err(_) => Err(()),
|
||||
}
|
||||
}
|
||||
|
||||
async fn decrement(&self) -> Result<(), ()> {
|
||||
let (tx, rx) = tokio::sync::oneshot::channel();
|
||||
let _ = self.queries.send(DatabaseQuery::Decrement { resp: tx }).await;
|
||||
let _ = self
|
||||
.queries
|
||||
.send(DatabaseQuery::Decrement { resp: tx })
|
||||
.await;
|
||||
|
||||
match rx.await {
|
||||
Ok(_) => Ok(()),
|
||||
Err(_) => Err(())
|
||||
Err(_) => Err(()),
|
||||
}
|
||||
}
|
||||
|
||||
@ -137,13 +145,11 @@ impl DatabaseClient {
|
||||
let _ = self.queries.send(DatabaseQuery::Get { resp: tx }).await;
|
||||
|
||||
match rx.await {
|
||||
Ok(db_resp) => {
|
||||
match db_resp {
|
||||
DatabaseResponse::Value(value) => Ok(value),
|
||||
_ => Err(())
|
||||
}
|
||||
}
|
||||
Err(_) => Err(())
|
||||
Ok(db_resp) => match db_resp {
|
||||
DatabaseResponse::Value(value) => Ok(value),
|
||||
_ => Err(()),
|
||||
},
|
||||
Err(_) => Err(()),
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user