416 lines
19 KiB
Rust
416 lines
19 KiB
Rust
// Exact Rust translations of the CompositeCurrentOutfitPolicyTests fixture in
|
|
// LibreMetaverse.Tests/CurrentOutfitFolderTests.cs.
|
|
// Source SHA-256: 07177fff27fbee0d0714286c652253985add3a9401a50e8d7a829ce6c2b3b7a86
|
|
|
|
use libremetaverse::appearance::{CompositeCurrentOutfitPolicy, ICurrentOutfitPolicy};
|
|
use libremetaverse::{InventoryItem, InventoryWearable};
|
|
use libremetaverse_compat_tests::block_on;
|
|
use libremetaverse_types::compat::{CancellationToken, CancellationTokenSource};
|
|
use libremetaverse_types::{AssetType, Error, UUID};
|
|
use std::future::Future;
|
|
use std::pin::Pin;
|
|
use std::sync::atomic::{AtomicBool, AtomicUsize, Ordering};
|
|
use std::sync::{Arc, Mutex};
|
|
|
|
struct TestPolicy {
|
|
allow_attach: AtomicBool,
|
|
allow_detach: AtomicBool,
|
|
attach_calls: AtomicUsize,
|
|
detach_calls: AtomicUsize,
|
|
report_calls: AtomicUsize,
|
|
last_added: Mutex<Option<Arc<Vec<InventoryItem>>>>,
|
|
last_removed: Mutex<Option<Arc<Vec<InventoryItem>>>>,
|
|
}
|
|
|
|
impl TestPolicy {
|
|
fn new() -> Self {
|
|
Self {
|
|
allow_attach: AtomicBool::new(true),
|
|
allow_detach: AtomicBool::new(true),
|
|
attach_calls: AtomicUsize::new(0),
|
|
detach_calls: AtomicUsize::new(0),
|
|
report_calls: AtomicUsize::new(0),
|
|
last_added: Mutex::new(None),
|
|
last_removed: Mutex::new(None),
|
|
}
|
|
}
|
|
}
|
|
|
|
impl ICurrentOutfitPolicy for TestPolicy {
|
|
fn can_attach(&self, _item: Option<Arc<InventoryItem>>) -> Result<bool, Error> {
|
|
self.attach_calls.fetch_add(1, Ordering::SeqCst);
|
|
Ok(self.allow_attach.load(Ordering::SeqCst))
|
|
}
|
|
|
|
fn can_detach(&self, _item: Option<Arc<InventoryItem>>) -> Result<bool, Error> {
|
|
self.detach_calls.fetch_add(1, Ordering::SeqCst);
|
|
Ok(self.allow_detach.load(Ordering::SeqCst))
|
|
}
|
|
|
|
fn report_item_change(
|
|
&self,
|
|
added: Option<Arc<Vec<InventoryItem>>>,
|
|
removed: Option<Arc<Vec<InventoryItem>>>,
|
|
_cancellation_token: Option<CancellationToken>,
|
|
) -> Pin<Box<dyn Future<Output = Result<(), Error>> + Send + '_>> {
|
|
self.report_calls.fetch_add(1, Ordering::SeqCst);
|
|
*self.last_added.lock().unwrap() = added;
|
|
*self.last_removed.lock().unwrap() = removed;
|
|
Box::pin(async { Ok(()) })
|
|
}
|
|
}
|
|
|
|
fn item() -> Arc<InventoryItem> {
|
|
let mut wearable = InventoryWearable::new(UUID::random().unwrap()).unwrap();
|
|
wearable.base.set_asset_type(AssetType::Clothing);
|
|
wearable.base.base.set_name("Test Item".into());
|
|
Arc::new(wearable.base)
|
|
}
|
|
|
|
fn as_policy(policy: &Arc<TestPolicy>) -> Arc<dyn ICurrentOutfitPolicy> {
|
|
policy.clone()
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.AddPolicy_WithValidPolicy_ReturnsThis::test 31c1829eaa2b82b498cc1eaea131d2e34d1a0b5620be24f4da853c62c49807cc translated
|
|
#[test]
|
|
fn add_policy_with_valid_policy_returns_this() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let policy = Arc::new(TestPolicy::new());
|
|
let result = composite.add_policy(Some(as_policy(&policy))).unwrap();
|
|
assert!(std::ptr::eq(
|
|
std::ptr::from_ref(result),
|
|
std::ptr::from_ref(&composite)
|
|
));
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.AddPolicy_WithNullPolicy_ThrowsArgumentNullException::test 6a111f0ad2e91c8566b5459939e3ecc76282cd033bb8d6483e1672c36891e597 translated
|
|
#[test]
|
|
fn add_policy_with_null_policy_throws_argument_null_exception() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
assert!(matches!(
|
|
composite.add_policy(None),
|
|
Err(Error::ArgumentNull)
|
|
));
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.AddPolicy_MultiplePolicies_AllAreConsulted::test 1767ee3dee6b07e71f10b52613962e211fcf9906a45d12188f517cf751896f24 translated
|
|
#[test]
|
|
fn add_policy_multiple_policies_all_are_consulted() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let first = Arc::new(TestPolicy::new());
|
|
let second = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&first))).unwrap();
|
|
composite.add_policy(Some(as_policy(&second))).unwrap();
|
|
first.allow_attach.store(true, Ordering::SeqCst);
|
|
second.allow_attach.store(true, Ordering::SeqCst);
|
|
let result = composite.can_attach(Some(item())).unwrap();
|
|
assert_eq!(first.attach_calls.load(Ordering::SeqCst), 1);
|
|
assert_eq!(second.attach_calls.load(Ordering::SeqCst), 1);
|
|
assert!(result);
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.AddPolicy_SamePolicyTwice_OnlyAddsOnce::test e3d1340780680bfc46267194ddb3c47e4ae24299cf532d92dd71d9770f1955fa translated
|
|
#[test]
|
|
fn add_policy_same_policy_twice_only_adds_once() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let policy = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&policy))).unwrap();
|
|
composite.add_policy(Some(as_policy(&policy))).unwrap();
|
|
policy.allow_attach.store(true, Ordering::SeqCst);
|
|
composite.can_attach(Some(item())).unwrap();
|
|
assert_eq!(policy.attach_calls.load(Ordering::SeqCst), 1);
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.RemovePolicy_WithAddedPolicy_RemovesPolicy::test 9dd407dceeacdcc60fccb0d9869ad261d90acd74ae4257331e0cf8d4be2ee603 translated
|
|
#[test]
|
|
fn remove_policy_with_added_policy_removes_policy() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let policy = Arc::new(TestPolicy::new());
|
|
let policy_dyn = as_policy(&policy);
|
|
composite.add_policy(Some(Arc::clone(&policy_dyn))).unwrap();
|
|
composite.remove_policy(Some(policy_dyn)).unwrap();
|
|
policy.allow_attach.store(false, Ordering::SeqCst);
|
|
assert!(composite.can_attach(Some(item())).unwrap());
|
|
assert_eq!(policy.attach_calls.load(Ordering::SeqCst), 0);
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.RemovePolicy_WithNonAddedPolicy_DoesNotThrow::test 9fa18bd628f6f02912168309e8e2afb6346a73a235dcc16cc81bc35e2dcf766f translated
|
|
#[test]
|
|
fn remove_policy_with_non_added_policy_does_not_throw() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
composite
|
|
.remove_policy(Some(Arc::new(TestPolicy::new())))
|
|
.unwrap();
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.RemovePolicy_WithNull_DoesNotThrow::test 28075d5f7c5458f1ccdf9981970e212e1663a9e5ebee65fce636a11a22390bfb translated
|
|
#[test]
|
|
fn remove_policy_with_null_does_not_throw() {
|
|
CompositeCurrentOutfitPolicy::new()
|
|
.unwrap()
|
|
.remove_policy(None)
|
|
.unwrap();
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanAttach_WithNoPolicies_ReturnsTrue::test 74bc06bb6cedfe84a3cd7e5b4c32b251ee6eff81c272c7d899436dbd7f21886b translated
|
|
#[test]
|
|
fn can_attach_with_no_policies_returns_true() {
|
|
assert!(
|
|
CompositeCurrentOutfitPolicy::new()
|
|
.unwrap()
|
|
.can_attach(Some(item()))
|
|
.unwrap()
|
|
);
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanAttach_WithNullItem_ThrowsArgumentNullException::test a47ebf9c89b603c10109c6e643de5043ba13cd2eaf5f04d73ab1fd5f40e9b332 translated
|
|
#[test]
|
|
fn can_attach_with_null_item_throws_argument_null_exception() {
|
|
assert!(matches!(
|
|
CompositeCurrentOutfitPolicy::new()
|
|
.unwrap()
|
|
.can_attach(None),
|
|
Err(Error::ArgumentNull)
|
|
));
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanAttach_WithAllPoliciesAllowing_ReturnsTrue::test 32c2f5dcc5cbdf24e4205c25c833aaa3c0f203aeb8ff20c30fdac1264f12f6bd translated
|
|
#[test]
|
|
fn can_attach_with_all_policies_allowing_returns_true() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let first = Arc::new(TestPolicy::new());
|
|
let second = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&first))).unwrap();
|
|
composite.add_policy(Some(as_policy(&second))).unwrap();
|
|
first.allow_attach.store(true, Ordering::SeqCst);
|
|
second.allow_attach.store(true, Ordering::SeqCst);
|
|
assert!(composite.can_attach(Some(item())).unwrap());
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanAttach_WithOnePolicyDenying_ReturnsFalse::test f38d910142a563bded6d35b969c0c560ffa072fd8df073a15fbbbed745681d0d translated
|
|
#[test]
|
|
fn can_attach_with_one_policy_denying_returns_false() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let first = Arc::new(TestPolicy::new());
|
|
let second = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&first))).unwrap();
|
|
composite.add_policy(Some(as_policy(&second))).unwrap();
|
|
first.allow_attach.store(true, Ordering::SeqCst);
|
|
second.allow_attach.store(false, Ordering::SeqCst);
|
|
assert!(!composite.can_attach(Some(item())).unwrap());
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanAttach_WithAllPoliciesDenying_ReturnsFalse::test 6cdda22d59a3cd690a187b597a7c8a2474e43c27902e737f15f0c71adc5bcf7c translated
|
|
#[test]
|
|
fn can_attach_with_all_policies_denying_returns_false() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let first = Arc::new(TestPolicy::new());
|
|
let second = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&first))).unwrap();
|
|
composite.add_policy(Some(as_policy(&second))).unwrap();
|
|
first.allow_attach.store(false, Ordering::SeqCst);
|
|
second.allow_attach.store(false, Ordering::SeqCst);
|
|
assert!(!composite.can_attach(Some(item())).unwrap());
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanDetach_WithNoPolicies_ReturnsTrue::test fe53b90f59fd9a73c4af1b7071f04cae0a7b623d6a50a3d8eb2fcae82e6872e9 translated
|
|
#[test]
|
|
fn can_detach_with_no_policies_returns_true() {
|
|
assert!(
|
|
CompositeCurrentOutfitPolicy::new()
|
|
.unwrap()
|
|
.can_detach(Some(item()))
|
|
.unwrap()
|
|
);
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanDetach_WithNullItem_ThrowsArgumentNullException::test 8a39f9c6e26f3a136de641f38507db144f731aed0861edbeafcfdb70306ecffb translated
|
|
#[test]
|
|
fn can_detach_with_null_item_throws_argument_null_exception() {
|
|
assert!(matches!(
|
|
CompositeCurrentOutfitPolicy::new()
|
|
.unwrap()
|
|
.can_detach(None),
|
|
Err(Error::ArgumentNull)
|
|
));
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanDetach_WithAllPoliciesAllowing_ReturnsTrue::test 2cbe1f0a5907c1dfa01af4329fa64177463798ec6caa357c8da8f5d3291901bf translated
|
|
#[test]
|
|
fn can_detach_with_all_policies_allowing_returns_true() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let first = Arc::new(TestPolicy::new());
|
|
let second = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&first))).unwrap();
|
|
composite.add_policy(Some(as_policy(&second))).unwrap();
|
|
first.allow_detach.store(true, Ordering::SeqCst);
|
|
second.allow_detach.store(true, Ordering::SeqCst);
|
|
assert!(composite.can_detach(Some(item())).unwrap());
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanDetach_WithOnePolicyDenying_ReturnsFalse::test 11896040dd8e4b5bbd7d85a1da126c648ad77eb349a73edf1e18fa5710cde1c9 translated
|
|
#[test]
|
|
fn can_detach_with_one_policy_denying_returns_false() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let first = Arc::new(TestPolicy::new());
|
|
let second = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&first))).unwrap();
|
|
composite.add_policy(Some(as_policy(&second))).unwrap();
|
|
first.allow_detach.store(true, Ordering::SeqCst);
|
|
second.allow_detach.store(false, Ordering::SeqCst);
|
|
assert!(!composite.can_detach(Some(item())).unwrap());
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanDetach_WithAllPoliciesDenying_ReturnsFalse::test 62b8478f593f2bf16b44267d80668e327a245d0b5c0386e7229a5857d669ae6c translated
|
|
#[test]
|
|
fn can_detach_with_all_policies_denying_returns_false() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let first = Arc::new(TestPolicy::new());
|
|
let second = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&first))).unwrap();
|
|
composite.add_policy(Some(as_policy(&second))).unwrap();
|
|
first.allow_detach.store(false, Ordering::SeqCst);
|
|
second.allow_detach.store(false, Ordering::SeqCst);
|
|
assert!(!composite.can_detach(Some(item())).unwrap());
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.ReportItemChangeAsync_WithNoPolicies_CompletesSuccessfully::test e3f6824512503bea532826b9a9e4f7bb5abdea53f962fbbc6fdae299a6fe44a0 translated
|
|
#[test]
|
|
fn report_item_change_with_no_policies_completes_successfully() {
|
|
let added = Arc::new(vec![Arc::try_unwrap(item()).ok().unwrap()]);
|
|
let removed = Arc::new(Vec::new());
|
|
block_on(
|
|
CompositeCurrentOutfitPolicy::new()
|
|
.unwrap()
|
|
.report_item_change(Some(added), Some(removed), None),
|
|
)
|
|
.unwrap();
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.ReportItemChangeAsync_WithMultiplePolicies_CallsAllPolicies::test 4797cc1851d78364553dac59a6f9a894107fa04fb3fddfb52ed0e4fb5b4bcd1a translated
|
|
#[test]
|
|
fn report_item_change_with_multiple_policies_calls_all_policies() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let first = Arc::new(TestPolicy::new());
|
|
let second = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&first))).unwrap();
|
|
composite.add_policy(Some(as_policy(&second))).unwrap();
|
|
let added = Arc::new(vec![Arc::try_unwrap(item()).ok().unwrap()]);
|
|
let removed = Arc::new(Vec::new());
|
|
block_on(composite.report_item_change(
|
|
Some(Arc::clone(&added)),
|
|
Some(Arc::clone(&removed)),
|
|
None,
|
|
))
|
|
.unwrap();
|
|
assert_eq!(first.report_calls.load(Ordering::SeqCst), 1);
|
|
assert_eq!(second.report_calls.load(Ordering::SeqCst), 1);
|
|
assert!(Arc::ptr_eq(
|
|
first.last_added.lock().unwrap().as_ref().unwrap(),
|
|
&added
|
|
));
|
|
assert!(Arc::ptr_eq(
|
|
second.last_added.lock().unwrap().as_ref().unwrap(),
|
|
&added
|
|
));
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.ReportItemChangeAsync_WithCancelledToken_ThrowsOperationCanceledException::test e4eaf9c1ee2d55a3e6c7bca634ff1af2a0e19b7560ea616984d258df46ec89fd translated
|
|
#[test]
|
|
fn report_item_change_with_cancelled_token_throws_operation_cancelled_exception() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
composite
|
|
.add_policy(Some(Arc::new(TestPolicy::new())))
|
|
.unwrap();
|
|
let source = CancellationTokenSource::new();
|
|
source.cancel();
|
|
let added = Arc::new(vec![Arc::try_unwrap(item()).ok().unwrap()]);
|
|
let error = block_on(composite.report_item_change(
|
|
Some(added),
|
|
Some(Arc::new(Vec::new())),
|
|
Some(source.token()),
|
|
))
|
|
.unwrap_err();
|
|
assert_eq!(error, Error::Cancelled);
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.ReportItemChangeAsync_WithEmptyLists_DoesNotThrow::test 6ba7e22fb7425e523f301612f7d7f6aed88e7d422050a70137d93b4a8004ae50 translated
|
|
#[test]
|
|
fn report_item_change_with_empty_lists_does_not_throw() {
|
|
let composite = CompositeCurrentOutfitPolicy::new().unwrap();
|
|
let policy = Arc::new(TestPolicy::new());
|
|
composite.add_policy(Some(as_policy(&policy))).unwrap();
|
|
block_on(composite.report_item_change(
|
|
Some(Arc::new(Vec::new())),
|
|
Some(Arc::new(Vec::new())),
|
|
None,
|
|
))
|
|
.unwrap();
|
|
assert_eq!(policy.report_calls.load(Ordering::SeqCst), 1);
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.ReportItemChangeAsync_WithNullLists_DoesNotThrowFromComposite::test c512c54f78c46fb4774d9b5c9c1057627592e1c25267811cddf3d687d3d1ec4d translated
|
|
#[test]
|
|
fn report_item_change_with_null_lists_does_not_throw_from_composite() {
|
|
block_on(
|
|
CompositeCurrentOutfitPolicy::new()
|
|
.unwrap()
|
|
.report_item_change(None, None, None),
|
|
)
|
|
.unwrap();
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.AddRemovePolicy_ConcurrentAccess_DoesNotThrow::test a73a01065867d90305f491e41d9ea61bc27b80c026672ed920368877bfb0fe14 translated
|
|
#[test]
|
|
fn add_remove_policy_concurrent_access_does_not_throw() {
|
|
let composite = Arc::new(CompositeCurrentOutfitPolicy::new().unwrap());
|
|
let policies: Vec<Arc<dyn ICurrentOutfitPolicy>> = (0..10)
|
|
.map(|_| Arc::new(TestPolicy::new()) as Arc<dyn ICurrentOutfitPolicy>)
|
|
.collect();
|
|
let mut threads = Vec::new();
|
|
for policy in &policies {
|
|
let composite = Arc::clone(&composite);
|
|
let policy = Arc::clone(policy);
|
|
threads.push(std::thread::spawn(move || {
|
|
composite.add_policy(Some(policy)).map(|_| ())
|
|
}));
|
|
}
|
|
for policy in policies {
|
|
let composite = Arc::clone(&composite);
|
|
threads.push(std::thread::spawn(move || {
|
|
composite.remove_policy(Some(policy))
|
|
}));
|
|
}
|
|
for thread in threads {
|
|
thread.join().unwrap().unwrap();
|
|
}
|
|
}
|
|
|
|
// parity-case: LibreMetaverse.Tests/CurrentOutfitFolderTests.cs::CompositeCurrentOutfitPolicyTests.CanAttach_WhileModifyingPolicies_DoesNotThrow::test 697999feeb776fae9a47cb9678c0ae0234d3b3831ce40c0e6f50fe622a5cc2b7 translated
|
|
#[test]
|
|
fn can_attach_while_modifying_policies_does_not_throw() {
|
|
let composite = Arc::new(CompositeCurrentOutfitPolicy::new().unwrap());
|
|
let stop = Arc::new(AtomicBool::new(false));
|
|
let read_composite = Arc::clone(&composite);
|
|
let read_stop = Arc::clone(&stop);
|
|
let test_item = item();
|
|
let reader = std::thread::spawn(move || {
|
|
while !read_stop.load(Ordering::SeqCst) {
|
|
let _ = read_composite.can_attach(Some(Arc::clone(&test_item)));
|
|
}
|
|
});
|
|
let write_composite = Arc::clone(&composite);
|
|
let writer = std::thread::spawn(move || {
|
|
for _ in 0..100 {
|
|
let policy: Arc<dyn ICurrentOutfitPolicy> = Arc::new(TestPolicy::new());
|
|
write_composite
|
|
.add_policy(Some(Arc::clone(&policy)))
|
|
.unwrap();
|
|
write_composite.remove_policy(Some(policy)).unwrap();
|
|
}
|
|
});
|
|
writer.join().unwrap();
|
|
stop.store(true, Ordering::SeqCst);
|
|
reader.join().unwrap();
|
|
}
|