1use crate::Kp;
33use async_trait::async_trait;
34use std::sync::Arc;
35
36#[cfg(feature = "tokio")]
38pub use tokio::sync::{Mutex as TokioMutex, RwLock as TokioRwLock};
39
40#[async_trait]
58pub trait AsyncLockLike<Lock, Inner>: Send + Sync {
59 async fn lock_read(&self, lock: &Lock) -> Option<Inner>;
61
62 async fn lock_write(&self, lock: &mut Lock) -> Option<Inner>;
64}
65
66pub trait SyncKeyPathLike<Root, Value, MutRoot, MutValue> {
69 fn sync_get(&self, root: Root) -> Option<Value>;
100
101 fn sync_get_mut(&self, root: MutRoot) -> Option<MutValue>;
132}
133
134impl<R, V, Root, Value, MutRoot, MutValue, G, S> SyncKeyPathLike<Root, Value, MutRoot, MutValue>
135 for crate::Kp<R, V, Root, Value, MutRoot, MutValue, G, S>
136where
137 Root: std::borrow::Borrow<R>,
138 Value: std::borrow::Borrow<V>,
139 MutRoot: std::borrow::BorrowMut<R>,
140 MutValue: std::borrow::BorrowMut<V>,
141 G: Fn(Root) -> Option<Value>,
142 S: Fn(MutRoot) -> Option<MutValue>,
143{
144 fn sync_get(&self, root: Root) -> Option<Value> {
145 self.get(root)
146 }
147 fn sync_get_mut(&self, root: MutRoot) -> Option<MutValue> {
148 self.get_mut(root)
149 }
150}
151
152impl<
153 R,
154 Lock,
155 Mid,
156 V,
157 Root,
158 LockValue,
159 MidValue,
160 Value,
161 MutRoot,
162 MutLock,
163 MutMid,
164 MutValue,
165 G1,
166 S1,
167 L,
168 G2,
169 S2,
170 >
171 SyncKeyPathLike<Root, Value, MutRoot, MutValue> for crate::lock::LockKp<
172 R,
173 Lock,
174 Mid,
175 V,
176 Root,
177 LockValue,
178 MidValue,
179 Value,
180 MutRoot,
181 MutLock,
182 MutMid,
183 MutValue,
184 G1,
185 S1,
186 L,
187 G2,
188 S2,
189 >
190where
191 Root: std::borrow::Borrow<R>,
192 LockValue: std::borrow::Borrow<Lock>,
193 MidValue: std::borrow::Borrow<Mid>,
194 Value: std::borrow::Borrow<V>,
195 MutRoot: std::borrow::BorrowMut<R>,
196 MutLock: std::borrow::BorrowMut<Lock>,
197 MutMid: std::borrow::BorrowMut<Mid>,
198 MutValue: std::borrow::BorrowMut<V>,
199 G1: Fn(Root) -> Option<LockValue>,
200 S1: Fn(MutRoot) -> Option<MutLock>,
201 L: crate::lock::LockAccess<Lock, MidValue> + crate::lock::LockAccess<Lock, MutMid>,
202 G2: Fn(MidValue) -> Option<Value>,
203 S2: Fn(MutMid) -> Option<MutValue>,
204 V: Clone,
205{
206 #[inline]
207 fn sync_get(&self, root: Root) -> Option<Value> {
208 self.get(root)
209 }
210 #[inline]
211 fn sync_get_mut(&self, root: MutRoot) -> Option<MutValue> {
212 self.get_mut(root)
213 }
214}
215
216#[async_trait(?Send)]
227pub trait AsyncKeyPathLike<Root, MutRoot> {
228 type Value;
230 type MutValue;
232 async fn get(&self, root: Root) -> Option<Self::Value>;
234 async fn get_mut(&self, root: MutRoot) -> Option<Self::MutValue>;
236}
237
238#[derive(Clone)] pub struct AsyncLockKp<
263 R,
264 Lock,
265 Mid,
266 V,
267 Root,
268 LockValue,
269 MidValue,
270 Value,
271 MutRoot,
272 MutLock,
273 MutMid,
274 MutValue,
275 G1,
276 S1,
277 L,
278 G2,
279 S2,
280> where
281 Root: std::borrow::Borrow<R>,
282 LockValue: std::borrow::Borrow<Lock>,
283 MidValue: std::borrow::Borrow<Mid>,
284 Value: std::borrow::Borrow<V>,
285 MutRoot: std::borrow::BorrowMut<R>,
286 MutLock: std::borrow::BorrowMut<Lock>,
287 MutMid: std::borrow::BorrowMut<Mid>,
288 MutValue: std::borrow::BorrowMut<V>,
289 G1: Fn(Root) -> Option<LockValue> + Clone,
290 S1: Fn(MutRoot) -> Option<MutLock> + Clone,
291 L: AsyncLockLike<Lock, MidValue> + AsyncLockLike<Lock, MutMid> + Clone,
292 G2: Fn(MidValue) -> Option<Value> + Clone,
293 S2: Fn(MutMid) -> Option<MutValue> + Clone,
294{
295 pub(crate) prev: Kp<R, Lock, Root, LockValue, MutRoot, MutLock, G1, S1>,
297
298 pub(crate) mid: L,
300
301 pub(crate) next: Kp<Mid, V, MidValue, Value, MutMid, MutValue, G2, S2>,
303}
304
305impl<
306 R,
307 Lock,
308 Mid,
309 V,
310 Root,
311 LockValue,
312 MidValue,
313 Value,
314 MutRoot,
315 MutLock,
316 MutMid,
317 MutValue,
318 G1,
319 S1,
320 L,
321 G2,
322 S2,
323>
324 AsyncLockKp<
325 R,
326 Lock,
327 Mid,
328 V,
329 Root,
330 LockValue,
331 MidValue,
332 Value,
333 MutRoot,
334 MutLock,
335 MutMid,
336 MutValue,
337 G1,
338 S1,
339 L,
340 G2,
341 S2,
342 >
343where
344 Root: std::borrow::Borrow<R>,
345 LockValue: std::borrow::Borrow<Lock>,
346 MidValue: std::borrow::Borrow<Mid>,
347 Value: std::borrow::Borrow<V>,
348 MutRoot: std::borrow::BorrowMut<R>,
349 MutLock: std::borrow::BorrowMut<Lock>,
350 MutMid: std::borrow::BorrowMut<Mid>,
351 MutValue: std::borrow::BorrowMut<V>,
352 G1: Fn(Root) -> Option<LockValue> + Clone,
353 S1: Fn(MutRoot) -> Option<MutLock> + Clone,
354 L: AsyncLockLike<Lock, MidValue> + AsyncLockLike<Lock, MutMid> + Clone,
355 G2: Fn(MidValue) -> Option<Value> + Clone,
356 S2: Fn(MutMid) -> Option<MutValue> + Clone,
357{
358 pub fn new(
360 prev: Kp<R, Lock, Root, LockValue, MutRoot, MutLock, G1, S1>,
361 mid: L,
362 next: Kp<Mid, V, MidValue, Value, MutMid, MutValue, G2, S2>,
363 ) -> Self {
364 Self { prev, mid, next }
365 }
366
367 #[inline]
381 pub async fn get(&self, root: Root) -> Option<Value>
382 where
383 Lock: Clone,
384 {
385 let lock_value = (self.prev.get)(root)?;
388 let lock: &Lock = lock_value.borrow();
389 let lock_clone = lock.clone(); let mid_value = self.mid.lock_read(&lock_clone).await?;
393
394 (self.next.get)(mid_value)
396 }
397
398 #[inline]
400 pub async fn get_mut(&self, root: MutRoot) -> Option<MutValue>
401 where
402 Lock: Clone,
403 {
404 let mut lock_value = (self.prev.set)(root)?;
406 let lock: &mut Lock = lock_value.borrow_mut();
407 let mut lock_clone = lock.clone(); let mid_value = self.mid.lock_write(&mut lock_clone).await?;
411
412 (self.next.set)(mid_value)
414 }
415
416 #[inline]
418 pub async fn get_optional(&self, root: Option<Root>) -> Option<Value>
419 where
420 Lock: Clone,
421 {
422 match root {
423 Some(r) => self.get(r).await,
424 None => None,
425 }
426 }
427
428 #[inline]
430 pub async fn get_mut_optional(&self, root: Option<MutRoot>) -> Option<MutValue>
431 where
432 Lock: Clone,
433 {
434 match root {
435 Some(r) => self.get_mut(r).await,
436 None => None,
437 }
438 }
439
440 #[inline]
442 pub async fn get_or_else<F>(&self, root: Option<Root>, f: F) -> Value
443 where
444 Lock: Clone,
445 F: FnOnce() -> Value,
446 {
447 self.get_optional(root).await.unwrap_or_else(f)
448 }
449
450 #[inline]
452 pub async fn get_mut_or_else<F>(&self, root: Option<MutRoot>, f: F) -> MutValue
453 where
454 Lock: Clone,
455 F: FnOnce() -> MutValue,
456 {
457 self.get_mut_optional(root).await.unwrap_or_else(f)
458 }
459
460 pub async fn set<F>(&self, root: Root, updater: F) -> Result<(), String>
467 where
468 Lock: Clone,
469 F: FnOnce(&mut V),
470 {
471 let lock_value = (self.prev.get)(root).ok_or("Failed to get lock from root")?;
473 let lock: &Lock = lock_value.borrow();
474 let lock_clone = lock.clone(); let mut mid_value = self
478 .mid
479 .lock_read(&lock_clone)
480 .await
481 .ok_or("Failed to lock")?;
482
483 let mut mut_value = (self.next.set)(mid_value).ok_or("Failed to navigate to value")?;
485 let v: &mut V = mut_value.borrow_mut();
486
487 updater(v);
489
490 Ok(())
491 }
492
493 pub fn then<V2, Value2, MutValue2, G3, S3>(
509 self,
510 next_kp: crate::Kp<V, V2, Value, Value2, MutValue, MutValue2, G3, S3>,
511 ) -> AsyncLockKp<
512 R,
513 Lock,
514 Mid,
515 V2,
516 Root,
517 LockValue,
518 MidValue,
519 Value2,
520 MutRoot,
521 MutLock,
522 MutMid,
523 MutValue2,
524 G1,
525 S1,
526 L,
527 impl Fn(MidValue) -> Option<Value2> + Clone + use<G1, G2, G3, L, Lock, LockValue, Mid, MidValue, MutLock, MutMid, MutRoot, MutValue, MutValue2, R, Root, S1, S2, S3, Value, Value2, V, V2>,
528 impl Fn(MutMid) -> Option<MutValue2> + Clone + use<G1, G2, G3, L, Lock, LockValue, Mid, MidValue, MutLock, MutMid, MutRoot, MutValue, MutValue2, R, Root, S1, S2, S3, Value, Value2, V, V2>,
529 >
530 where
531 V: 'static,
532 V2: 'static,
533 Value: std::borrow::Borrow<V>,
534 Value2: std::borrow::Borrow<V2>,
535 MutValue: std::borrow::BorrowMut<V>,
536 MutValue2: std::borrow::BorrowMut<V2>,
537 G3: Fn(Value) -> Option<Value2> + Clone,
538 S3: Fn(MutValue) -> Option<MutValue2> + Clone,
539 {
540 let next_get = self.next.get;
541 let next_set = self.next.set;
542 let chained_kp = crate::Kp::new(
543 move |mid_value: MidValue| next_get(mid_value).and_then(|v| (next_kp.get)(v)),
544 move |mid_value: MutMid| next_set(mid_value).and_then(|v| (next_kp.set)(v)),
545 );
546 AsyncLockKp::new(self.prev, self.mid, chained_kp)
547 }
548
549 pub fn then_lock<
552 Lock2,
553 Mid2,
554 V2,
555 LockValue2,
556 MidValue2,
557 Value2,
558 MutLock2,
559 MutMid2,
560 MutValue2,
561 G2_1,
562 S2_1,
563 L2,
564 G2_2,
565 S2_2,
566 >(
567 self,
568 lock_kp: crate::lock::LockKp<
569 V,
570 Lock2,
571 Mid2,
572 V2,
573 Value,
574 LockValue2,
575 MidValue2,
576 Value2,
577 MutValue,
578 MutLock2,
579 MutMid2,
580 MutValue2,
581 G2_1,
582 S2_1,
583 L2,
584 G2_2,
585 S2_2,
586 >,
587 ) -> AsyncLockKpThenLockKp<
588 R,
589 V2,
590 Root,
591 Value2,
592 MutRoot,
593 MutValue2,
594 Self,
595 crate::lock::LockKp<
596 V,
597 Lock2,
598 Mid2,
599 V2,
600 Value,
601 LockValue2,
602 MidValue2,
603 Value2,
604 MutValue,
605 MutLock2,
606 MutMid2,
607 MutValue2,
608 G2_1,
609 S2_1,
610 L2,
611 G2_2,
612 S2_2,
613 >,
614 >
615 where
616 V: 'static,
617 V2: 'static,
618 Value: std::borrow::Borrow<V>,
619 Value2: std::borrow::Borrow<V2>,
620 MutValue: std::borrow::BorrowMut<V>,
621 MutValue2: std::borrow::BorrowMut<V2>,
622 LockValue2: std::borrow::Borrow<Lock2>,
623 MidValue2: std::borrow::Borrow<Mid2>,
624 MutLock2: std::borrow::BorrowMut<Lock2>,
625 MutMid2: std::borrow::BorrowMut<Mid2>,
626 G2_1: Fn(Value) -> Option<LockValue2>,
627 S2_1: Fn(MutValue) -> Option<MutLock2>,
628 L2: crate::lock::LockAccess<Lock2, MidValue2> + crate::lock::LockAccess<Lock2, MutMid2>,
629 G2_2: Fn(MidValue2) -> Option<Value2>,
630 S2_2: Fn(MutMid2) -> Option<MutValue2>,
631 {
632 AsyncLockKpThenLockKp {
633 first: self,
634 second: lock_kp,
635 _p: std::marker::PhantomData,
636 }
637 }
638
639 pub fn then_async<
655 Lock2,
656 Mid2,
657 V2,
658 LockValue2,
659 MidValue2,
660 Value2,
661 MutLock2,
662 MutMid2,
663 MutValue2,
664 G2_1,
665 S2_1,
666 L2,
667 G2_2,
668 S2_2,
669 >(
670 self,
671 other: AsyncLockKp<
672 V,
673 Lock2,
674 Mid2,
675 V2,
676 Value,
677 LockValue2,
678 MidValue2,
679 Value2,
680 MutValue,
681 MutLock2,
682 MutMid2,
683 MutValue2,
684 G2_1,
685 S2_1,
686 L2,
687 G2_2,
688 S2_2,
689 >,
690 ) -> ComposedAsyncLockKp<
691 R,
692 V2,
693 Root,
694 Value2,
695 MutRoot,
696 MutValue2,
697 Self,
698 AsyncLockKp<
699 V,
700 Lock2,
701 Mid2,
702 V2,
703 Value,
704 LockValue2,
705 MidValue2,
706 Value2,
707 MutValue,
708 MutLock2,
709 MutMid2,
710 MutValue2,
711 G2_1,
712 S2_1,
713 L2,
714 G2_2,
715 S2_2,
716 >,
717 >
718 where
719 Lock: Clone,
720 Lock2: Clone,
721 V: 'static,
722 V2: 'static,
723 Value: std::borrow::Borrow<V>,
724 LockValue2: std::borrow::Borrow<Lock2>,
725 MidValue2: std::borrow::Borrow<Mid2>,
726 Value2: std::borrow::Borrow<V2>,
727 MutValue: std::borrow::BorrowMut<V>,
728 MutLock2: std::borrow::BorrowMut<Lock2>,
729 MutMid2: std::borrow::BorrowMut<Mid2>,
730 MutValue2: std::borrow::BorrowMut<V2>,
731 G2_1: Fn(Value) -> Option<LockValue2> + Clone,
732 S2_1: Fn(MutValue) -> Option<MutLock2> + Clone,
733 L2: AsyncLockLike<Lock2, MidValue2> + AsyncLockLike<Lock2, MutMid2> + Clone,
734 G2_2: Fn(MidValue2) -> Option<Value2> + Clone,
735 S2_2: Fn(MutMid2) -> Option<MutValue2> + Clone,
736 {
737 ComposedAsyncLockKp {
738 first: self,
739 second: other,
740 _p: std::marker::PhantomData,
741 }
742 }
743}
744
745#[async_trait(?Send)]
747impl<
748 R,
749 Lock,
750 Mid,
751 V,
752 Root,
753 LockValue,
754 MidValue,
755 Value,
756 MutRoot,
757 MutLock,
758 MutMid,
759 MutValue,
760 G1,
761 S1,
762 L,
763 G2,
764 S2,
765> AsyncKeyPathLike<Root, MutRoot>
766 for AsyncLockKp<R, Lock, Mid, V, Root, LockValue, MidValue, Value, MutRoot, MutLock, MutMid, MutValue, G1, S1, L, G2, S2>
767where
768 Root: std::borrow::Borrow<R>,
769 LockValue: std::borrow::Borrow<Lock>,
770 MidValue: std::borrow::Borrow<Mid>,
771 Value: std::borrow::Borrow<V>,
772 MutRoot: std::borrow::BorrowMut<R>,
773 MutLock: std::borrow::BorrowMut<Lock>,
774 MutMid: std::borrow::BorrowMut<Mid>,
775 MutValue: std::borrow::BorrowMut<V>,
776 G1: Fn(Root) -> Option<LockValue> + Clone,
777 S1: Fn(MutRoot) -> Option<MutLock> + Clone,
778 L: AsyncLockLike<Lock, MidValue> + AsyncLockLike<Lock, MutMid> + Clone,
779 G2: Fn(MidValue) -> Option<Value> + Clone,
780 S2: Fn(MutMid) -> Option<MutValue> + Clone,
781 Lock: Clone,
782{
783 type Value = Value;
784 type MutValue = MutValue;
785 async fn get(&self, root: Root) -> Option<Value> {
786 AsyncLockKp::get(self, root).await
787 }
788 async fn get_mut(&self, root: MutRoot) -> Option<MutValue> {
789 AsyncLockKp::get_mut(self, root).await
790 }
791}
792
793#[derive(Clone)]
800pub struct ComposedAsyncLockKp<R, V2, Root, Value2, MutRoot, MutValue2, First, Second> {
801 pub(crate) first: First,
802 pub(crate) second: Second,
803 _p: std::marker::PhantomData<(R, V2, Root, Value2, MutRoot, MutValue2)>,
804}
805
806impl<R, V2, Root, Value2, MutRoot, MutValue2, First, Second>
807 ComposedAsyncLockKp<R, V2, Root, Value2, MutRoot, MutValue2, First, Second>
808where
809 First: AsyncKeyPathLike<Root, MutRoot>,
810 Second: AsyncKeyPathLike<First::Value, First::MutValue, Value = Value2, MutValue = MutValue2>,
811{
812 pub async fn get(&self, root: Root) -> Option<Value2> {
814 let value = self.first.get(root).await?;
815 self.second.get(value).await
816 }
817
818 pub async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
820 let mut_value = self.first.get_mut(root).await?;
821 self.second.get_mut(mut_value).await
822 }
823
824 pub fn then_async<
826 Lock3,
827 Mid3,
828 V3,
829 LockValue3,
830 MidValue3,
831 Value3,
832 MutLock3,
833 MutMid3,
834 MutValue3,
835 G3_1,
836 S3_1,
837 L3,
838 G3_2,
839 S3_2,
840 >(
841 self,
842 other: AsyncLockKp<
843 V2,
844 Lock3,
845 Mid3,
846 V3,
847 Value2,
848 LockValue3,
849 MidValue3,
850 Value3,
851 MutValue2,
852 MutLock3,
853 MutMid3,
854 MutValue3,
855 G3_1,
856 S3_1,
857 L3,
858 G3_2,
859 S3_2,
860 >,
861 ) -> ComposedAsyncLockKp<
862 R,
863 V3,
864 Root,
865 Value3,
866 MutRoot,
867 MutValue3,
868 Self,
869 AsyncLockKp<
870 V2,
871 Lock3,
872 Mid3,
873 V3,
874 Value2,
875 LockValue3,
876 MidValue3,
877 Value3,
878 MutValue2,
879 MutLock3,
880 MutMid3,
881 MutValue3,
882 G3_1,
883 S3_1,
884 L3,
885 G3_2,
886 S3_2,
887 >,
888 >
889 where
890 V2: 'static,
891 V3: 'static,
892 Value2: std::borrow::Borrow<V2>,
893 Value3: std::borrow::Borrow<V3>,
894 MutValue2: std::borrow::BorrowMut<V2>,
895 MutValue3: std::borrow::BorrowMut<V3>,
896 LockValue3: std::borrow::Borrow<Lock3>,
897 MidValue3: std::borrow::Borrow<Mid3>,
898 MutLock3: std::borrow::BorrowMut<Lock3>,
899 MutMid3: std::borrow::BorrowMut<Mid3>,
900 G3_1: Fn(Value2) -> Option<LockValue3> + Clone,
901 S3_1: Fn(MutValue2) -> Option<MutLock3> + Clone,
902 L3: AsyncLockLike<Lock3, MidValue3> + AsyncLockLike<Lock3, MutMid3> + Clone,
903 G3_2: Fn(MidValue3) -> Option<Value3> + Clone,
904 S3_2: Fn(MutMid3) -> Option<MutValue3> + Clone,
905 Lock3: Clone,
906 {
907 ComposedAsyncLockKp {
908 first: self,
909 second: other,
910 _p: std::marker::PhantomData,
911 }
912 }
913
914 pub fn then<V3, Value3, MutValue3, G3, S3>(
916 self,
917 next_kp: crate::Kp<V2, V3, Value2, Value3, MutValue2, MutValue3, G3, S3>,
918 ) -> AsyncKeyPathThenKp<R, V3, Root, Value3, MutRoot, MutValue3, Self, crate::Kp<V2, V3, Value2, Value3, MutValue2, MutValue3, G3, S3>>
919 where
920 V2: 'static,
921 V3: 'static,
922 Value2: std::borrow::Borrow<V2>,
923 Value3: std::borrow::Borrow<V3>,
924 MutValue2: std::borrow::BorrowMut<V2>,
925 MutValue3: std::borrow::BorrowMut<V3>,
926 G3: Fn(Value2) -> Option<Value3> + Clone,
927 S3: Fn(MutValue2) -> Option<MutValue3> + Clone,
928 {
929 AsyncKeyPathThenKp {
930 first: self,
931 second: next_kp,
932 _p: std::marker::PhantomData,
933 }
934 }
935
936 pub fn then_lock<
938 Lock3,
939 Mid3,
940 V3,
941 LockValue3,
942 MidValue3,
943 Value3,
944 MutLock3,
945 MutMid3,
946 MutValue3,
947 G3_1,
948 S3_1,
949 L3,
950 G3_2,
951 S3_2,
952 >(
953 self,
954 lock_kp: crate::lock::LockKp<V2, Lock3, Mid3, V3, Value2, LockValue3, MidValue3, Value3, MutValue2, MutLock3, MutMid3, MutValue3, G3_1, S3_1, L3, G3_2, S3_2>,
955 ) -> AsyncLockKpThenLockKp<R, V3, Root, Value3, MutRoot, MutValue3, Self, crate::lock::LockKp<V2, Lock3, Mid3, V3, Value2, LockValue3, MidValue3, Value3, MutValue2, MutLock3, MutMid3, MutValue3, G3_1, S3_1, L3, G3_2, S3_2>>
956 where
957 V2: 'static,
958 V3: 'static,
959 Value2: std::borrow::Borrow<V2>,
960 Value3: std::borrow::Borrow<V3>,
961 MutValue2: std::borrow::BorrowMut<V2>,
962 MutValue3: std::borrow::BorrowMut<V3>,
963 LockValue3: std::borrow::Borrow<Lock3>,
964 MidValue3: std::borrow::Borrow<Mid3>,
965 MutLock3: std::borrow::BorrowMut<Lock3>,
966 MutMid3: std::borrow::BorrowMut<Mid3>,
967 G3_1: Fn(Value2) -> Option<LockValue3>,
968 S3_1: Fn(MutValue2) -> Option<MutLock3>,
969 L3: crate::lock::LockAccess<Lock3, MidValue3> + crate::lock::LockAccess<Lock3, MutMid3>,
970 G3_2: Fn(MidValue3) -> Option<Value3>,
971 S3_2: Fn(MutMid3) -> Option<MutValue3>,
972 {
973 AsyncLockKpThenLockKp {
974 first: self,
975 second: lock_kp,
976 _p: std::marker::PhantomData,
977 }
978 }
979}
980
981#[derive(Clone)]
983pub struct KpThenAsyncKeyPath<R, V, V2, Root, Value, Value2, MutRoot, MutValue, MutValue2, First, Second> {
984 pub(crate) first: First,
985 pub(crate) second: Second,
986 pub(crate) _p: std::marker::PhantomData<(R, V, V2, Root, Value, Value2, MutRoot, MutValue, MutValue2)>,
987}
988
989impl<R, V, V2, Root, Value, Value2, MutRoot, MutValue, MutValue2, First, Second>
990 KpThenAsyncKeyPath<R, V, V2, Root, Value, Value2, MutRoot, MutValue, MutValue2, First, Second>
991where
992 First: SyncKeyPathLike<Root, Value, MutRoot, MutValue>,
993 Second: AsyncKeyPathLike<Value, MutValue, Value = Value2, MutValue = MutValue2>,
994{
995 #[inline]
997 pub async fn get(&self, root: Root) -> Option<Value2> {
998 let v = self.first.sync_get(root)?;
999 self.second.get(v).await
1000 }
1001 #[inline]
1003 pub async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
1004 let mut_v = self.first.sync_get_mut(root)?;
1005 self.second.get_mut(mut_v).await
1006 }
1007}
1008
1009#[async_trait(?Send)]
1010impl<R, V, V2, Root, Value, Value2, MutRoot, MutValue, MutValue2, First, Second>
1011 AsyncKeyPathLike<Root, MutRoot> for KpThenAsyncKeyPath<R, V, V2, Root, Value, Value2, MutRoot, MutValue, MutValue2, First, Second>
1012where
1013 First: SyncKeyPathLike<Root, Value, MutRoot, MutValue>,
1014 Second: AsyncKeyPathLike<Value, MutValue, Value = Value2, MutValue = MutValue2>,
1015{
1016 type Value = Value2;
1017 type MutValue = MutValue2;
1018 async fn get(&self, root: Root) -> Option<Value2> {
1019 let v = self.first.sync_get(root)?;
1020 self.second.get(v).await
1021 }
1022 async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
1023 let mut_v = self.first.sync_get_mut(root)?;
1024 self.second.get_mut(mut_v).await
1025 }
1026}
1027
1028impl<R, V, V2, Root, Value, Value2, MutRoot, MutValue, MutValue2, First, Second>
1029 KpThenAsyncKeyPath<R, V, V2, Root, Value, Value2, MutRoot, MutValue, MutValue2, First, Second>
1030where
1031 First: SyncKeyPathLike<Root, Value, MutRoot, MutValue>,
1032 Second: AsyncKeyPathLike<Value, MutValue, Value = Value2, MutValue = MutValue2>,
1033{
1034 pub fn then<V3, Value3, MutValue3, G3, S3>(
1036 self,
1037 next_kp: crate::Kp<V2, V3, Value2, Value3, MutValue2, MutValue3, G3, S3>,
1038 ) -> AsyncKeyPathThenKp<R, V3, Root, Value3, MutRoot, MutValue3, Self, crate::Kp<V2, V3, Value2, Value3, MutValue2, MutValue3, G3, S3>>
1039 where
1040 V3: 'static,
1041 Value2: std::borrow::Borrow<V2>,
1042 MutValue2: std::borrow::BorrowMut<V2>,
1043 Value3: std::borrow::Borrow<V3>,
1044 MutValue3: std::borrow::BorrowMut<V3>,
1045 G3: Fn(Value2) -> Option<Value3> + Clone,
1046 S3: Fn(MutValue2) -> Option<MutValue3> + Clone,
1047 {
1048 AsyncKeyPathThenKp {
1049 first: self,
1050 second: next_kp,
1051 _p: std::marker::PhantomData,
1052 }
1053 }
1054}
1055
1056#[derive(Clone)]
1058pub struct AsyncKeyPathThenKp<R, V2, Root, Value2, MutRoot, MutValue2, First, Second> {
1059 pub(crate) first: First,
1060 pub(crate) second: Second,
1061 _p: std::marker::PhantomData<(R, V2, Root, Value2, MutRoot, MutValue2)>,
1062}
1063
1064impl<R, V2, Root, Value2, MutRoot, MutValue2, First, RKp, G, S>
1066 AsyncKeyPathThenKp<R, V2, Root, Value2, MutRoot, MutValue2, First, crate::Kp<RKp, V2, First::Value, Value2, First::MutValue, MutValue2, G, S>>
1067where
1068 First: AsyncKeyPathLike<Root, MutRoot>,
1069 First::Value: std::borrow::Borrow<RKp>,
1070 First::MutValue: std::borrow::BorrowMut<RKp>,
1071 Value2: std::borrow::Borrow<V2>,
1072 MutValue2: std::borrow::BorrowMut<V2>,
1073 G: Fn(First::Value) -> Option<Value2>,
1074 S: Fn(First::MutValue) -> Option<MutValue2>,
1075{
1076 #[inline]
1078 pub async fn get(&self, root: Root) -> Option<Value2> {
1079 let value = self.first.get(root).await?;
1080 (self.second.get)(value)
1081 }
1082 #[inline]
1084 pub async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
1085 let mut_value = self.first.get_mut(root).await?;
1086 (self.second.set)(mut_value)
1087 }
1088}
1089
1090#[async_trait(?Send)]
1091impl<R, V2, Root, Value2, MutRoot, MutValue2, First, Second>
1092 AsyncKeyPathLike<Root, MutRoot> for ComposedAsyncLockKp<R, V2, Root, Value2, MutRoot, MutValue2, First, Second>
1093where
1094 First: AsyncKeyPathLike<Root, MutRoot>,
1095 Second: AsyncKeyPathLike<First::Value, First::MutValue, Value = Value2, MutValue = MutValue2>,
1096{
1097 type Value = Value2;
1098 type MutValue = MutValue2;
1099 async fn get(&self, root: Root) -> Option<Value2> {
1100 ComposedAsyncLockKp::get(self, root).await
1101 }
1102 async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
1103 ComposedAsyncLockKp::get_mut(self, root).await
1104 }
1105}
1106
1107#[derive(Clone)]
1114pub struct AsyncLockKpThenLockKp<R, V2, Root, Value2, MutRoot, MutValue2, First, Second> {
1115 pub(crate) first: First,
1116 pub(crate) second: Second,
1117 _p: std::marker::PhantomData<(R, V2, Root, Value2, MutRoot, MutValue2)>,
1118}
1119
1120impl<
1121 R,
1122 V2,
1123 Root,
1124 Value2,
1125 MutRoot,
1126 MutValue2,
1127 Lock,
1128 Mid,
1129 V,
1130 LockValue,
1131 MidValue,
1132 Value,
1133 MutLock,
1134 MutMid,
1135 MutValue,
1136 G1,
1137 S1,
1138 L,
1139 G2,
1140 S2,
1141 Lock2,
1142 Mid2,
1143 LockValue2,
1144 MidValue2,
1145 MutLock2,
1146 MutMid2,
1147 G2_1,
1148 S2_1,
1149 L2,
1150 G2_2,
1151 S2_2,
1152 >
1153 AsyncLockKpThenLockKp<
1154 R,
1155 V2,
1156 Root,
1157 Value2,
1158 MutRoot,
1159 MutValue2,
1160 AsyncLockKp<R, Lock, Mid, V, Root, LockValue, MidValue, Value, MutRoot, MutLock, MutMid, MutValue, G1, S1, L, G2, S2>,
1161 crate::lock::LockKp<V, Lock2, Mid2, V2, Value, LockValue2, MidValue2, Value2, MutValue, MutLock2, MutMid2, MutValue2, G2_1, S2_1, L2, G2_2, S2_2>,
1162 >
1163where
1164 Root: std::borrow::Borrow<R>,
1165 LockValue: std::borrow::Borrow<Lock>,
1166 MidValue: std::borrow::Borrow<Mid>,
1167 Value: std::borrow::Borrow<V>,
1168 MutRoot: std::borrow::BorrowMut<R>,
1169 MutLock: std::borrow::BorrowMut<Lock>,
1170 MutMid: std::borrow::BorrowMut<Mid>,
1171 MutValue: std::borrow::BorrowMut<V>,
1172 Value2: std::borrow::Borrow<V2>,
1173 MutValue2: std::borrow::BorrowMut<V2>,
1174 G1: Fn(Root) -> Option<LockValue> + Clone,
1175 S1: Fn(MutRoot) -> Option<MutLock> + Clone,
1176 L: AsyncLockLike<Lock, MidValue> + AsyncLockLike<Lock, MutMid> + Clone,
1177 G2: Fn(MidValue) -> Option<Value> + Clone,
1178 S2: Fn(MutMid) -> Option<MutValue> + Clone,
1179 LockValue2: std::borrow::Borrow<Lock2>,
1180 MidValue2: std::borrow::Borrow<Mid2>,
1181 MutLock2: std::borrow::BorrowMut<Lock2>,
1182 MutMid2: std::borrow::BorrowMut<Mid2>,
1183 G2_1: Fn(Value) -> Option<LockValue2>,
1184 S2_1: Fn(MutValue) -> Option<MutLock2>,
1185 L2: crate::lock::LockAccess<Lock2, MidValue2> + crate::lock::LockAccess<Lock2, MutMid2>,
1186 G2_2: Fn(MidValue2) -> Option<Value2>,
1187 S2_2: Fn(MutMid2) -> Option<MutValue2>,
1188 Lock: Clone,
1189 V: Clone,
1190 V2: Clone,
1191{
1192 pub async fn get(&self, root: Root) -> Option<Value2> {
1194 let value = self.first.get(root).await?;
1195 self.second.get(value)
1196 }
1197
1198 pub async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
1200 let mut_value = self.first.get_mut(root).await?;
1201 self.second.get_mut(mut_value)
1202 }
1203}
1204
1205impl<
1207 R,
1208 V2,
1209 Root,
1210 Value2,
1211 MutRoot,
1212 MutValue2,
1213 Lock3,
1214 Mid3,
1215 LockValue3,
1216 MidValue3,
1217 MutLock3,
1218 MutMid3,
1219 G3_1,
1220 S3_1,
1221 L3,
1222 G3_2,
1223 S3_2,
1224 First,
1225 Second,
1226 >
1227 AsyncLockKpThenLockKp<
1228 R,
1229 V2,
1230 Root,
1231 Value2,
1232 MutRoot,
1233 MutValue2,
1234 ComposedAsyncLockKp<R, V2, Root, Value2, MutRoot, MutValue2, First, Second>,
1235 crate::lock::LockKp<Value2, Lock3, Mid3, V2, Value2, LockValue3, MidValue3, Value2, MutValue2, MutLock3, MutMid3, MutValue2, G3_1, S3_1, L3, G3_2, S3_2>,
1236 >
1237where
1238 First: AsyncKeyPathLike<Root, MutRoot>,
1239 Second: AsyncKeyPathLike<First::Value, First::MutValue, Value = Value2, MutValue = MutValue2>,
1240 Value2: std::borrow::Borrow<V2>,
1241 MutValue2: std::borrow::BorrowMut<Value2> + std::borrow::BorrowMut<V2>,
1242 LockValue3: std::borrow::Borrow<Lock3>,
1243 MidValue3: std::borrow::Borrow<Mid3>,
1244 MutLock3: std::borrow::BorrowMut<Lock3>,
1245 MutMid3: std::borrow::BorrowMut<Mid3>,
1246 G3_1: Fn(Value2) -> Option<LockValue3>,
1247 S3_1: Fn(MutValue2) -> Option<MutLock3>,
1248 L3: crate::lock::LockAccess<Lock3, MidValue3> + crate::lock::LockAccess<Lock3, MutMid3>,
1249 G3_2: Fn(MidValue3) -> Option<Value2>,
1250 S3_2: Fn(MutMid3) -> Option<MutValue2>,
1251 Value2: Clone,
1252 V2: Clone,
1253{
1254 pub async fn get(&self, root: Root) -> Option<Value2> {
1256 let value = self.first.get(root).await?;
1257 self.second.get(value)
1258 }
1259 pub async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
1261 let mut_value = self.first.get_mut(root).await?;
1262 self.second.get_mut(mut_value)
1263 }
1264}
1265
1266impl<
1268 R,
1269 V2,
1270 Root,
1271 Value2,
1272 MutRoot,
1273 MutValue2,
1274 Lock3,
1275 Mid3,
1276 LockValue3,
1277 MidValue3,
1278 MutLock3,
1279 MutMid3,
1280 G3_1,
1281 S3_1,
1282 L3,
1283 G3_2,
1284 S3_2,
1285 F,
1286 S,
1287 >
1288 AsyncLockKpThenLockKp<
1289 R,
1290 V2,
1291 Root,
1292 Value2,
1293 MutRoot,
1294 MutValue2,
1295 AsyncLockKpThenLockKp<R, V2, Root, Value2, MutRoot, MutValue2, F, S>,
1296 crate::lock::LockKp<Value2, Lock3, Mid3, V2, Value2, LockValue3, MidValue3, Value2, MutValue2, MutLock3, MutMid3, MutValue2, G3_1, S3_1, L3, G3_2, S3_2>,
1297 >
1298where
1299 F: AsyncKeyPathLike<Root, MutRoot, Value = Value2, MutValue = MutValue2>,
1300 S: SyncKeyPathLike<Value2, Value2, MutValue2, MutValue2>,
1301 Value2: std::borrow::Borrow<V2>,
1302 MutValue2: std::borrow::BorrowMut<Value2> + std::borrow::BorrowMut<V2>,
1303 LockValue3: std::borrow::Borrow<Lock3>,
1304 MidValue3: std::borrow::Borrow<Mid3>,
1305 MutLock3: std::borrow::BorrowMut<Lock3>,
1306 MutMid3: std::borrow::BorrowMut<Mid3>,
1307 G3_1: Fn(Value2) -> Option<LockValue3>,
1308 S3_1: Fn(MutValue2) -> Option<MutLock3>,
1309 L3: crate::lock::LockAccess<Lock3, MidValue3> + crate::lock::LockAccess<Lock3, MutMid3>,
1310 G3_2: Fn(MidValue3) -> Option<Value2>,
1311 S3_2: Fn(MutMid3) -> Option<MutValue2>,
1312 Value2: Clone,
1313 V2: Clone,
1314{
1315 pub async fn get(&self, root: Root) -> Option<Value2> {
1317 let value = AsyncKeyPathLike::get(&self.first, root).await?;
1318 self.second.get(value)
1319 }
1320 pub async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
1322 let mut_value = AsyncKeyPathLike::get_mut(&self.first, root).await?;
1323 self.second.get_mut(mut_value)
1324 }
1325}
1326
1327#[async_trait(?Send)]
1329impl<R, V2, Root, Value2, MutRoot, MutValue2, First, Second> AsyncKeyPathLike<Root, MutRoot>
1330 for AsyncLockKpThenLockKp<R, V2, Root, Value2, MutRoot, MutValue2, First, Second>
1331where
1332 First: AsyncKeyPathLike<Root, MutRoot>,
1333 Second: SyncKeyPathLike<First::Value, Value2, First::MutValue, MutValue2>,
1334{
1335 type Value = Value2;
1336 type MutValue = MutValue2;
1337 async fn get(&self, root: Root) -> Option<Value2> {
1338 let value = AsyncKeyPathLike::get(&self.first, root).await?;
1339 SyncKeyPathLike::sync_get(&self.second, value)
1340 }
1341 async fn get_mut(&self, root: MutRoot) -> Option<MutValue2> {
1342 let mut_value = AsyncKeyPathLike::get_mut(&self.first, root).await?;
1343 SyncKeyPathLike::sync_get_mut(&self.second, mut_value)
1344 }
1345}
1346
1347impl<R, V2, Root, Value2, MutRoot, MutValue2, First, Second> AsyncLockKpThenLockKp<R, V2, Root, Value2, MutRoot, MutValue2, First, Second>
1349where
1350 First: AsyncKeyPathLike<Root, MutRoot>,
1351{
1352 pub fn then_async<
1355 Lock3,
1356 Mid3,
1357 V3,
1358 LockValue3,
1359 MidValue3,
1360 Value3,
1361 MutLock3,
1362 MutMid3,
1363 MutValue3,
1364 G3_1,
1365 S3_1,
1366 L3,
1367 G3_2,
1368 S3_2,
1369 >(
1370 self,
1371 other: AsyncLockKp<
1372 Value2,
1373 Lock3,
1374 Mid3,
1375 V3,
1376 Value2,
1377 LockValue3,
1378 MidValue3,
1379 Value3,
1380 MutValue2,
1381 MutLock3,
1382 MutMid3,
1383 MutValue3,
1384 G3_1,
1385 S3_1,
1386 L3,
1387 G3_2,
1388 S3_2,
1389 >,
1390 ) -> ComposedAsyncLockKp<
1391 Root,
1392 V3,
1393 Root,
1394 Value3,
1395 MutRoot,
1396 MutValue3,
1397 Self,
1398 AsyncLockKp<
1399 Value2,
1400 Lock3,
1401 Mid3,
1402 V3,
1403 Value2,
1404 LockValue3,
1405 MidValue3,
1406 Value3,
1407 MutValue2,
1408 MutLock3,
1409 MutMid3,
1410 MutValue3,
1411 G3_1,
1412 S3_1,
1413 L3,
1414 G3_2,
1415 S3_2,
1416 >,
1417 >
1418 where
1419 V2: 'static,
1420 V3: 'static,
1421 Value2: std::borrow::Borrow<V2>,
1422 Value3: std::borrow::Borrow<V3>,
1423 MutValue2: std::borrow::BorrowMut<V2> + std::borrow::BorrowMut<Value2>,
1424 MutValue3: std::borrow::BorrowMut<V3>,
1425 LockValue3: std::borrow::Borrow<Lock3>,
1426 MidValue3: std::borrow::Borrow<Mid3>,
1427 MutLock3: std::borrow::BorrowMut<Lock3>,
1428 MutMid3: std::borrow::BorrowMut<Mid3>,
1429 G3_1: Fn(Value2) -> Option<LockValue3> + Clone,
1430 S3_1: Fn(MutValue2) -> Option<MutLock3> + Clone,
1431 L3: AsyncLockLike<Lock3, MidValue3> + AsyncLockLike<Lock3, MutMid3> + Clone,
1432 G3_2: Fn(MidValue3) -> Option<Value3> + Clone,
1433 S3_2: Fn(MutMid3) -> Option<MutValue3> + Clone,
1434 Lock3: Clone,
1435 {
1436 ComposedAsyncLockKp {
1437 first: self,
1438 second: other,
1439 _p: std::marker::PhantomData,
1440 }
1441 }
1442
1443 pub fn then_lock<
1445 Lock3,
1446 Mid3,
1447 V3,
1448 LockValue3,
1449 MidValue3,
1450 Value3,
1451 MutLock3,
1452 MutMid3,
1453 MutValue3,
1454 G3_1,
1455 S3_1,
1456 L3,
1457 G3_2,
1458 S3_2,
1459 >(
1460 self,
1461 lock_kp: crate::lock::LockKp<Value2, Lock3, Mid3, V3, Value2, LockValue3, MidValue3, Value3, MutValue2, MutLock3, MutMid3, MutValue3, G3_1, S3_1, L3, G3_2, S3_2>,
1462 ) -> AsyncLockKpThenLockKp<R, V3, Root, Value3, MutRoot, MutValue3, Self, crate::lock::LockKp<Value2, Lock3, Mid3, V3, Value2, LockValue3, MidValue3, Value3, MutValue2, MutLock3, MutMid3, MutValue3, G3_1, S3_1, L3, G3_2, S3_2>>
1463 where
1464 V3: 'static,
1465 Value2: std::borrow::Borrow<V2>,
1466 Value3: std::borrow::Borrow<V3>,
1467 MutValue2: std::borrow::BorrowMut<Value2>,
1468 MutValue3: std::borrow::BorrowMut<V3>,
1469 LockValue3: std::borrow::Borrow<Lock3>,
1470 MidValue3: std::borrow::Borrow<Mid3>,
1471 MutLock3: std::borrow::BorrowMut<Lock3>,
1472 MutMid3: std::borrow::BorrowMut<Mid3>,
1473 G3_1: Fn(Value2) -> Option<LockValue3>,
1474 S3_1: Fn(MutValue2) -> Option<MutLock3>,
1475 L3: crate::lock::LockAccess<Lock3, MidValue3> + crate::lock::LockAccess<Lock3, MutMid3>,
1476 G3_2: Fn(MidValue3) -> Option<Value3>,
1477 S3_2: Fn(MutMid3) -> Option<MutValue3>,
1478 {
1479 AsyncLockKpThenLockKp {
1480 first: self,
1481 second: lock_kp,
1482 _p: std::marker::PhantomData,
1483 }
1484 }
1485
1486 pub fn then<V3, Value3, MutValue3, G3, S3>(
1488 self,
1489 next_kp: crate::Kp<Value2, V3, Value2, Value3, MutValue2, MutValue3, G3, S3>,
1490 ) -> AsyncKeyPathThenKp<R, V3, Root, Value3, MutRoot, MutValue3, Self, crate::Kp<Value2, V3, Value2, Value3, MutValue2, MutValue3, G3, S3>>
1491 where
1492 V3: 'static,
1493 Value2: std::borrow::Borrow<V2>,
1494 Value3: std::borrow::Borrow<V3>,
1495 MutValue2: std::borrow::BorrowMut<Value2>,
1496 MutValue3: std::borrow::BorrowMut<V3>,
1497 G3: Fn(Value2) -> Option<Value3> + Clone,
1498 S3: Fn(MutValue2) -> Option<MutValue3> + Clone,
1499 {
1500 AsyncKeyPathThenKp {
1501 first: self,
1502 second: next_kp,
1503 _p: std::marker::PhantomData,
1504 }
1505 }
1506}
1507
1508#[cfg(feature = "tokio")]
1513#[derive(Clone)] pub struct TokioMutexAccess<T> {
1521 _phantom: std::marker::PhantomData<T>,
1522}
1523
1524#[cfg(feature = "tokio")]
1525impl<T> TokioMutexAccess<T> {
1526 pub fn new() -> Self {
1527 Self {
1528 _phantom: std::marker::PhantomData,
1529 }
1530 }
1531}
1532
1533#[cfg(feature = "tokio")]
1534impl<T> Default for TokioMutexAccess<T> {
1535 fn default() -> Self {
1536 Self::new()
1537 }
1538}
1539
1540#[cfg(feature = "tokio")]
1542#[async_trait]
1543impl<'a, T: 'static + Send + Sync> AsyncLockLike<Arc<tokio::sync::Mutex<T>>, &'a T>
1544 for TokioMutexAccess<T>
1545{
1546 #[inline]
1547 async fn lock_read(&self, lock: &Arc<tokio::sync::Mutex<T>>) -> Option<&'a T> {
1548 let guard = lock.lock().await;
1550 let ptr = &*guard as *const T;
1551 unsafe { Some(&*ptr) }
1552 }
1553
1554 #[inline]
1555 async fn lock_write(&self, lock: &mut Arc<tokio::sync::Mutex<T>>) -> Option<&'a T> {
1556 let guard = lock.lock().await;
1557 let ptr = &*guard as *const T;
1558 unsafe { Some(&*ptr) }
1559 }
1560}
1561
1562#[cfg(feature = "tokio")]
1564#[async_trait]
1565impl<'a, T: 'static + Send + Sync> AsyncLockLike<Arc<tokio::sync::Mutex<T>>, &'a mut T>
1566 for TokioMutexAccess<T>
1567{
1568 #[inline]
1569 async fn lock_read(&self, lock: &Arc<tokio::sync::Mutex<T>>) -> Option<&'a mut T> {
1570 let mut guard = lock.lock().await;
1572 let ptr = &mut *guard as *mut T;
1573 unsafe { Some(&mut *ptr) }
1574 }
1575
1576 #[inline]
1577 async fn lock_write(&self, lock: &mut Arc<tokio::sync::Mutex<T>>) -> Option<&'a mut T> {
1578 let mut guard = lock.lock().await;
1579 let ptr = &mut *guard as *mut T;
1580 unsafe { Some(&mut *ptr) }
1581 }
1582}
1583
1584#[cfg(feature = "tokio")]
1589pub struct TokioRwLockAccess<T> {
1597 _phantom: std::marker::PhantomData<T>,
1598}
1599
1600#[cfg(feature = "tokio")]
1601impl<T> TokioRwLockAccess<T> {
1602 pub fn new() -> Self {
1603 Self {
1604 _phantom: std::marker::PhantomData,
1605 }
1606 }
1607}
1608
1609#[cfg(feature = "tokio")]
1610impl<T> Default for TokioRwLockAccess<T> {
1611 fn default() -> Self {
1612 Self::new()
1613 }
1614}
1615
1616#[cfg(feature = "tokio")]
1617impl<T> Clone for TokioRwLockAccess<T> {
1618 fn clone(&self) -> Self {
1619 Self {
1620 _phantom: self._phantom,
1621 }
1622 }
1623}
1624
1625#[cfg(feature = "tokio")]
1627#[async_trait]
1628impl<'a, T: 'static + Send + Sync> AsyncLockLike<Arc<tokio::sync::RwLock<T>>, &'a T>
1629 for TokioRwLockAccess<T>
1630{
1631 async fn lock_read(&self, lock: &Arc<tokio::sync::RwLock<T>>) -> Option<&'a T> {
1632 let guard = lock.read().await;
1634 let ptr = &*guard as *const T;
1635 unsafe { Some(&*ptr) }
1636 }
1637
1638 async fn lock_write(&self, lock: &mut Arc<tokio::sync::RwLock<T>>) -> Option<&'a T> {
1639 let guard = lock.read().await;
1641 let ptr = &*guard as *const T;
1642 unsafe { Some(&*ptr) }
1643 }
1644}
1645
1646#[cfg(feature = "tokio")]
1648#[async_trait]
1649impl<'a, T: 'static + Send + Sync> AsyncLockLike<Arc<tokio::sync::RwLock<T>>, &'a mut T>
1650 for TokioRwLockAccess<T>
1651{
1652 async fn lock_read(&self, lock: &Arc<tokio::sync::RwLock<T>>) -> Option<&'a mut T> {
1653 let mut guard = lock.write().await;
1655 let ptr = &mut *guard as *mut T;
1656 unsafe { Some(&mut *ptr) }
1657 }
1658
1659 async fn lock_write(&self, lock: &mut Arc<tokio::sync::RwLock<T>>) -> Option<&'a mut T> {
1660 let mut guard = lock.write().await;
1662 let ptr = &mut *guard as *mut T;
1663 unsafe { Some(&mut *ptr) }
1664 }
1665}
1666
1667#[cfg(feature = "tokio")]
1675pub type AsyncLockKpMutexFor<Root, Lock, Inner> = AsyncLockKp<
1677 Root,
1678 Lock,
1679 Inner,
1680 Inner,
1681 &'static Root,
1682 &'static Lock,
1683 &'static Inner,
1684 &'static Inner,
1685 &'static mut Root,
1686 &'static mut Lock,
1687 &'static mut Inner,
1688 &'static mut Inner,
1689 for<'b> fn(&'b Root) -> Option<&'b Lock>,
1690 for<'b> fn(&'b mut Root) -> Option<&'b mut Lock>,
1691 TokioMutexAccess<Inner>,
1692 for<'b> fn(&'b Inner) -> Option<&'b Inner>,
1693 for<'b> fn(&'b mut Inner) -> Option<&'b mut Inner>,
1694>;
1695
1696#[cfg(feature = "tokio")]
1697pub type AsyncLockKpRwLockFor<Root, Lock, Inner> = AsyncLockKp<
1699 Root,
1700 Lock,
1701 Inner,
1702 Inner,
1703 &'static Root,
1704 &'static Lock,
1705 &'static Inner,
1706 &'static Inner,
1707 &'static mut Root,
1708 &'static mut Lock,
1709 &'static mut Inner,
1710 &'static mut Inner,
1711 for<'b> fn(&'b Root) -> Option<&'b Lock>,
1712 for<'b> fn(&'b mut Root) -> Option<&'b mut Lock>,
1713 TokioRwLockAccess<Inner>,
1714 for<'b> fn(&'b Inner) -> Option<&'b Inner>,
1715 for<'b> fn(&'b mut Inner) -> Option<&'b mut Inner>,
1716>;
1717
1718#[cfg(all(test, feature = "tokio"))]
1723mod tests {
1724 use super::*;
1725 use crate::KpType;
1726
1727 #[tokio::test]
1728 async fn test_async_lock_kp_tokio_mutex_basic() {
1729 use tokio::sync::Mutex;
1730
1731 #[derive(Clone)]
1732 struct Root {
1733 data: Arc<Mutex<String>>,
1734 }
1735
1736 let root = Root {
1737 data: Arc::new(Mutex::new("hello".to_string())),
1738 };
1739
1740 let lock_kp = {
1742 let prev: KpType<Root, Arc<Mutex<String>>> =
1743 Kp::new(|r: &Root| Some(&r.data), |r: &mut Root| Some(&mut r.data));
1744 let next: KpType<String, String> =
1745 Kp::new(|s: &String| Some(s), |s: &mut String| Some(s));
1746 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
1747 };
1748
1749 let value = lock_kp.get(&root).await;
1751 assert!(value.is_some());
1752 assert_eq!(value.unwrap(), &"hello".to_string());
1753 }
1754
1755 #[tokio::test]
1756 async fn test_async_lock_kp_get_optional_or_else() {
1757 use tokio::sync::Mutex;
1758
1759 #[derive(Clone)]
1760 struct Root {
1761 data: Arc<Mutex<i32>>,
1762 }
1763
1764 let mut root = Root {
1765 data: Arc::new(Mutex::new(42)),
1766 };
1767
1768 let lock_kp = {
1769 let prev: KpType<Root, Arc<Mutex<i32>>> =
1770 Kp::new(|r: &Root| Some(&r.data), |r: &mut Root| Some(&mut r.data));
1771 let next: KpType<i32, i32> = Kp::new(|n: &i32| Some(n), |n: &mut i32| Some(n));
1772 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
1773 };
1774
1775 assert!(lock_kp.get_optional(None).await.is_none());
1777 assert_eq!(lock_kp.get_optional(Some(&root)).await, Some(&42));
1778
1779 assert!(lock_kp.get_mut_optional(None).await.is_none());
1781 if let Some(m) = lock_kp.get_mut_optional(Some(&mut root)).await {
1782 *m = 99;
1783 }
1784 assert_eq!(lock_kp.get(&root).await, Some(&99));
1785
1786 assert_eq!(*lock_kp.get_or_else(None, || &0).await, 0);
1788 assert_eq!(*lock_kp.get_or_else(Some(&root), || &0).await, 99);
1789
1790 let m = lock_kp.get_mut_or_else(Some(&mut root), || panic!("unexpected")).await;
1792 *m = 100;
1793 assert_eq!(lock_kp.get(&root).await, Some(&100));
1794 }
1795
1796 #[tokio::test]
1797 async fn test_async_lock_kp_tokio_rwlock_basic() {
1798 use tokio::sync::RwLock;
1799
1800 #[derive(Clone)]
1801 struct Root {
1802 data: Arc<RwLock<Vec<i32>>>,
1803 }
1804
1805 let root = Root {
1806 data: Arc::new(RwLock::new(vec![1, 2, 3, 4, 5])),
1807 };
1808
1809 let lock_kp = {
1811 let prev: KpType<Root, Arc<RwLock<Vec<i32>>>> =
1812 Kp::new(|r: &Root| Some(&r.data), |r: &mut Root| Some(&mut r.data));
1813 let next: KpType<Vec<i32>, Vec<i32>> =
1814 Kp::new(|v: &Vec<i32>| Some(v), |v: &mut Vec<i32>| Some(v));
1815 AsyncLockKp::new(prev, TokioRwLockAccess::new(), next)
1816 };
1817
1818 let value = lock_kp.get(&root).await;
1820 assert!(value.is_some());
1821 assert_eq!(value.unwrap().len(), 5);
1822 }
1823
1824 #[tokio::test]
1825 async fn test_async_lock_kp_concurrent_reads() {
1826 use tokio::sync::RwLock;
1827
1828 #[derive(Clone)]
1829 struct Root {
1830 data: Arc<RwLock<i32>>,
1831 }
1832
1833 let root = Root {
1834 data: Arc::new(RwLock::new(42)),
1835 };
1836
1837 let lock_kp = {
1839 let prev: KpType<Root, Arc<RwLock<i32>>> =
1840 Kp::new(|r: &Root| Some(&r.data), |r: &mut Root| Some(&mut r.data));
1841 let next: KpType<i32, i32> = Kp::new(|n: &i32| Some(n), |n: &mut i32| Some(n));
1842 AsyncLockKp::new(prev, TokioRwLockAccess::new(), next)
1843 };
1844
1845 let lock_kp2 = {
1848 let prev: KpType<Root, Arc<RwLock<i32>>> =
1849 Kp::new(|r: &Root| Some(&r.data), |r: &mut Root| Some(&mut r.data));
1850 let next: KpType<i32, i32> = Kp::new(|n: &i32| Some(n), |n: &mut i32| Some(n));
1851 AsyncLockKp::new(prev, TokioRwLockAccess::new(), next)
1852 };
1853 let (a, b) = tokio::join!(lock_kp.get(&root), lock_kp2.get(&root));
1854 assert_eq!(a, Some(&42));
1855 assert_eq!(b, Some(&42));
1856
1857 let value = lock_kp.get(&root).await;
1859 assert_eq!(value, Some(&42));
1860 }
1861
1862 #[tokio::test]
1863 async fn test_async_lock_kp_panic_on_clone_proof() {
1864 use tokio::sync::Mutex;
1865
1866 struct PanicOnClone {
1868 data: String,
1869 }
1870
1871 impl Clone for PanicOnClone {
1872 fn clone(&self) -> Self {
1873 panic!("❌ ASYNC DEEP CLONE DETECTED! PanicOnClone was cloned!");
1874 }
1875 }
1876
1877 #[derive(Clone)]
1878 struct Root {
1879 level1: Arc<Mutex<Level1>>,
1880 }
1881
1882 struct Level1 {
1883 panic_data: PanicOnClone,
1884 value: i32,
1885 }
1886
1887 impl Clone for Level1 {
1888 fn clone(&self) -> Self {
1889 panic!("❌ Level1 was deeply cloned in async context!");
1890 }
1891 }
1892
1893 let root = Root {
1895 level1: Arc::new(Mutex::new(Level1 {
1896 panic_data: PanicOnClone {
1897 data: "test".to_string(),
1898 },
1899 value: 123,
1900 })),
1901 };
1902
1903 let lock_kp = {
1905 let prev: KpType<Root, Arc<Mutex<Level1>>> = Kp::new(
1906 |r: &Root| Some(&r.level1),
1907 |r: &mut Root| Some(&mut r.level1),
1908 );
1909 let next: KpType<Level1, i32> = Kp::new(
1910 |l: &Level1| Some(&l.value),
1911 |l: &mut Level1| Some(&mut l.value),
1912 );
1913 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
1914 };
1915
1916 let value = lock_kp.get(&root).await;
1918
1919 assert_eq!(value, Some(&123));
1921 }
1922
1923 #[tokio::test]
1924 async fn test_async_lock_kp_structure() {
1925 use tokio::sync::Mutex;
1926
1927 #[derive(Clone)]
1928 struct Root {
1929 data: Arc<Mutex<String>>,
1930 }
1931
1932 let lock_kp = {
1933 let prev: KpType<Root, Arc<Mutex<String>>> =
1934 Kp::new(|r: &Root| Some(&r.data), |r: &mut Root| Some(&mut r.data));
1935 let next: KpType<String, String> =
1936 Kp::new(|s: &String| Some(s), |s: &mut String| Some(s));
1937 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
1938 };
1939
1940 let _ = &lock_kp.prev;
1942 let _ = &lock_kp.mid;
1943 let _ = &lock_kp.next;
1944 }
1945
1946 #[tokio::test]
1947 async fn test_async_kp_then() {
1948 use tokio::sync::Mutex;
1949
1950 #[derive(Clone)]
1951 struct Root {
1952 data: Arc<Mutex<Inner>>,
1953 }
1954
1955 #[derive(Clone)]
1956 struct Inner {
1957 value: i32,
1958 }
1959
1960 let root = Root {
1961 data: Arc::new(Mutex::new(Inner { value: 42 })),
1962 };
1963
1964 let async_kp = {
1966 let prev: KpType<Root, Arc<Mutex<Inner>>> =
1967 Kp::new(|r: &Root| Some(&r.data), |r: &mut Root| Some(&mut r.data));
1968 let next: KpType<Inner, Inner> = Kp::new(|i: &Inner| Some(i), |i: &mut Inner| Some(i));
1969 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
1970 };
1971
1972 let value_kp: KpType<Inner, i32> = Kp::new(
1974 |i: &Inner| Some(&i.value),
1975 |i: &mut Inner| Some(&mut i.value),
1976 );
1977
1978 let chained = async_kp.then(value_kp);
1979 let result = chained.get(&root).await;
1980 assert_eq!(result, Some(&42));
1981 }
1982
1983 #[tokio::test]
1984 async fn test_async_kp_later_then() {
1985 use tokio::sync::Mutex;
1986
1987 #[derive(Clone)]
1988 struct Root {
1989 lock1: Arc<Mutex<Container>>,
1990 }
1991
1992 #[derive(Clone)]
1993 struct Container {
1994 lock2: Arc<Mutex<i32>>,
1995 }
1996
1997 let root = Root {
1998 lock1: Arc::new(Mutex::new(Container {
1999 lock2: Arc::new(Mutex::new(999)),
2000 })),
2001 };
2002
2003 let async_kp1 = {
2005 let prev: KpType<Root, Arc<Mutex<Container>>> =
2006 Kp::new(|r: &Root| Some(&r.lock1), |r: &mut Root| Some(&mut r.lock1));
2007 let next: KpType<Container, Container> =
2008 Kp::new(|c: &Container| Some(c), |c: &mut Container| Some(c));
2009 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
2010 };
2011
2012 let async_kp2 = {
2014 let prev: KpType<Container, Arc<Mutex<i32>>> = Kp::new(
2015 |c: &Container| Some(&c.lock2),
2016 |c: &mut Container| Some(&mut c.lock2),
2017 );
2018 let next: KpType<i32, i32> = Kp::new(|n: &i32| Some(n), |n: &mut i32| Some(n));
2019 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
2020 };
2021
2022 let chained = async_kp1.then_async(async_kp2);
2024 let result = chained.get(&root).await;
2025 assert_eq!(result, Some(&999));
2026 }
2027
2028 #[tokio::test]
2029 async fn test_async_kp_then_async_three_levels() {
2030 use tokio::sync::Mutex;
2031
2032 #[derive(Clone)]
2033 struct Root {
2034 a: Arc<Mutex<Level1>>,
2035 }
2036 #[derive(Clone)]
2037 struct Level1 {
2038 b: Arc<Mutex<Level2>>,
2039 }
2040 #[derive(Clone)]
2041 struct Level2 {
2042 c: Arc<Mutex<i32>>,
2043 }
2044
2045 let root = Root {
2046 a: Arc::new(Mutex::new(Level1 {
2047 b: Arc::new(Mutex::new(Level2 {
2048 c: Arc::new(Mutex::new(42)),
2049 })),
2050 })),
2051 };
2052
2053 let kp1 = {
2054 let prev: KpType<Root, Arc<Mutex<Level1>>> =
2055 Kp::new(|r: &Root| Some(&r.a), |r: &mut Root| Some(&mut r.a));
2056 let next: KpType<Level1, Level1> =
2057 Kp::new(|l: &Level1| Some(l), |l: &mut Level1| Some(l));
2058 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
2059 };
2060 let kp2 = {
2061 let prev: KpType<Level1, Arc<Mutex<Level2>>> =
2062 Kp::new(|l: &Level1| Some(&l.b), |l: &mut Level1| Some(&mut l.b));
2063 let next: KpType<Level2, Level2> =
2064 Kp::new(|l: &Level2| Some(l), |l: &mut Level2| Some(l));
2065 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
2066 };
2067 let kp3 = {
2068 let prev: KpType<Level2, Arc<Mutex<i32>>> =
2069 Kp::new(|l: &Level2| Some(&l.c), |l: &mut Level2| Some(&mut l.c));
2070 let next: KpType<i32, i32> = Kp::new(|n: &i32| Some(n), |n: &mut i32| Some(n));
2071 AsyncLockKp::new(prev, TokioMutexAccess::new(), next)
2072 };
2073
2074 let chained = kp1.then_async(kp2).then_async(kp3);
2075 let result = chained.get(&root).await;
2076 assert_eq!(result, Some(&42));
2077 }
2078}