Polishing and optimizing `retryWhen`.
This commit is contained in:
parent
56a094fa69
commit
ce983c44d0
|
|
@ -564,6 +564,26 @@
|
|||
C8F0C0441BBBFBB9001B112F /* _RXSwizzling.h in Headers */ = {isa = PBXBuildFile; fileRef = C8093E881B8A732E0088E94D /* _RXSwizzling.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
C8F0C0451BBBFBB9001B112F /* _RXKVOObserver.h in Headers */ = {isa = PBXBuildFile; fileRef = C8093E861B8A732E0088E94D /* _RXKVOObserver.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
C8F0C04F1BBBFBCE001B112F /* ObservableConvertibleType+Blocking.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8093F581B8A73A20088E94D /* ObservableConvertibleType+Blocking.swift */; };
|
||||
C8F6A0EF1BEE2CB6007DF367 /* ScheduledItemType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0EE1BEE2CB6007DF367 /* ScheduledItemType.swift */; };
|
||||
C8F6A0F01BEE2CB6007DF367 /* ScheduledItemType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0EE1BEE2CB6007DF367 /* ScheduledItemType.swift */; };
|
||||
C8F6A0F11BEE2CB6007DF367 /* ScheduledItemType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0EE1BEE2CB6007DF367 /* ScheduledItemType.swift */; };
|
||||
C8F6A0F21BEE2CB6007DF367 /* ScheduledItemType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0EE1BEE2CB6007DF367 /* ScheduledItemType.swift */; };
|
||||
C8F6A0F41BEE3395007DF367 /* InvocableType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0F31BEE3395007DF367 /* InvocableType.swift */; };
|
||||
C8F6A0F51BEE3395007DF367 /* InvocableType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0F31BEE3395007DF367 /* InvocableType.swift */; };
|
||||
C8F6A0F61BEE3395007DF367 /* InvocableType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0F31BEE3395007DF367 /* InvocableType.swift */; };
|
||||
C8F6A0F71BEE3395007DF367 /* InvocableType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0F31BEE3395007DF367 /* InvocableType.swift */; };
|
||||
C8F6A0F91BEE33C1007DF367 /* InvocableScheduledItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0F81BEE33C1007DF367 /* InvocableScheduledItem.swift */; };
|
||||
C8F6A0FA1BEE33C1007DF367 /* InvocableScheduledItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0F81BEE33C1007DF367 /* InvocableScheduledItem.swift */; };
|
||||
C8F6A0FB1BEE33C1007DF367 /* InvocableScheduledItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0F81BEE33C1007DF367 /* InvocableScheduledItem.swift */; };
|
||||
C8F6A0FC1BEE33C1007DF367 /* InvocableScheduledItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0F81BEE33C1007DF367 /* InvocableScheduledItem.swift */; };
|
||||
C8F6A0FE1BEE42DD007DF367 /* AnonymousInvocable.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0FD1BEE42DD007DF367 /* AnonymousInvocable.swift */; };
|
||||
C8F6A0FF1BEE42DD007DF367 /* AnonymousInvocable.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0FD1BEE42DD007DF367 /* AnonymousInvocable.swift */; };
|
||||
C8F6A1001BEE42DD007DF367 /* AnonymousInvocable.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0FD1BEE42DD007DF367 /* AnonymousInvocable.swift */; };
|
||||
C8F6A1011BEE42DD007DF367 /* AnonymousInvocable.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A0FD1BEE42DD007DF367 /* AnonymousInvocable.swift */; };
|
||||
CB255BD71BC46A9C00798A4C /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB255BD61BC46A9C00798A4C /* RetryWhen.swift */; };
|
||||
CB255BD81BC46A9C00798A4C /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB255BD61BC46A9C00798A4C /* RetryWhen.swift */; };
|
||||
CB255BD91BC46A9C00798A4C /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB255BD61BC46A9C00798A4C /* RetryWhen.swift */; };
|
||||
CB255BDA1BC46A9C00798A4C /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB255BD61BC46A9C00798A4C /* RetryWhen.swift */; };
|
||||
CB883B3B1BE24355000AC2EE /* Window.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB883B3A1BE24355000AC2EE /* Window.swift */; };
|
||||
CB883B3C1BE24355000AC2EE /* Window.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB883B3A1BE24355000AC2EE /* Window.swift */; };
|
||||
CB883B3D1BE24355000AC2EE /* Window.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB883B3A1BE24355000AC2EE /* Window.swift */; };
|
||||
|
|
@ -584,10 +604,6 @@
|
|||
CBEE77201BD649A000AD584C /* ToArray.swift in Sources */ = {isa = PBXBuildFile; fileRef = CBEE771E1BD649A000AD584C /* ToArray.swift */; };
|
||||
CBEE77211BD649A000AD584C /* ToArray.swift in Sources */ = {isa = PBXBuildFile; fileRef = CBEE771E1BD649A000AD584C /* ToArray.swift */; };
|
||||
CBEE77221BD649A000AD584C /* ToArray.swift in Sources */ = {isa = PBXBuildFile; fileRef = CBEE771E1BD649A000AD584C /* ToArray.swift */; };
|
||||
CB255BD71BC46A9C00798A4C /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB255BD61BC46A9C00798A4C /* RetryWhen.swift */; settings = {ASSET_TAGS = (); }; };
|
||||
CB255BD81BC46A9C00798A4C /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB255BD61BC46A9C00798A4C /* RetryWhen.swift */; settings = {ASSET_TAGS = (); }; };
|
||||
CB255BD91BC46A9C00798A4C /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB255BD61BC46A9C00798A4C /* RetryWhen.swift */; settings = {ASSET_TAGS = (); }; };
|
||||
CB255BDA1BC46A9C00798A4C /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB255BD61BC46A9C00798A4C /* RetryWhen.swift */; settings = {ASSET_TAGS = (); }; };
|
||||
D203C4F31BB9C4CA00D02D00 /* RxCollectionViewReactiveArrayDataSource.swift in Sources */ = {isa = PBXBuildFile; fileRef = C88253F11B8A752B00B02D69 /* RxCollectionViewReactiveArrayDataSource.swift */; };
|
||||
D203C4F41BB9C52400D02D00 /* RxTableViewReactiveArrayDataSource.swift in Sources */ = {isa = PBXBuildFile; fileRef = C88253F21B8A752B00B02D69 /* RxTableViewReactiveArrayDataSource.swift */; };
|
||||
D203C4F51BB9C52900D02D00 /* ItemEvents.swift in Sources */ = {isa = PBXBuildFile; fileRef = C88253F41B8A752B00B02D69 /* ItemEvents.swift */; };
|
||||
|
|
@ -1042,12 +1058,16 @@
|
|||
C8F0C0021BBBFB8B001B112F /* RxSwift.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = RxSwift.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
C8F0C04B1BBBFBB9001B112F /* RxCocoa.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = RxCocoa.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
C8F0C0581BBBFBCE001B112F /* RxBlocking.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = RxBlocking.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
C8F6A0EE1BEE2CB6007DF367 /* ScheduledItemType.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ScheduledItemType.swift; sourceTree = "<group>"; };
|
||||
C8F6A0F31BEE3395007DF367 /* InvocableType.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = InvocableType.swift; sourceTree = "<group>"; };
|
||||
C8F6A0F81BEE33C1007DF367 /* InvocableScheduledItem.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = InvocableScheduledItem.swift; sourceTree = "<group>"; };
|
||||
C8F6A0FD1BEE42DD007DF367 /* AnonymousInvocable.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AnonymousInvocable.swift; sourceTree = "<group>"; };
|
||||
CB255BD61BC46A9C00798A4C /* RetryWhen.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = RetryWhen.swift; sourceTree = "<group>"; };
|
||||
CB883B3A1BE24355000AC2EE /* Window.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Window.swift; sourceTree = "<group>"; };
|
||||
CB883B3F1BE24C15000AC2EE /* RefCountDisposable.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = RefCountDisposable.swift; sourceTree = "<group>"; };
|
||||
CB883B441BE256D4000AC2EE /* BooleanDisposable.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BooleanDisposable.swift; sourceTree = "<group>"; };
|
||||
CB883B491BE369AA000AC2EE /* AddRef.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AddRef.swift; sourceTree = "<group>"; };
|
||||
CBEE771E1BD649A000AD584C /* ToArray.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ToArray.swift; sourceTree = "<group>"; };
|
||||
CB255BD61BC46A9C00798A4C /* RetryWhen.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = RetryWhen.swift; sourceTree = "<group>"; };
|
||||
D2138C751BB9BE9800339B5C /* RxCocoa.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = RxCocoa.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
D2245A1A1BD5657300E7146F /* WithLatestFrom.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = WithLatestFrom.swift; sourceTree = "<group>"; };
|
||||
D22B6D251BC8504A00BCE0AB /* SkipWhile.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SkipWhile.swift; sourceTree = "<group>"; };
|
||||
|
|
@ -1331,6 +1351,10 @@
|
|||
C84B38E71BA43380001B7D88 /* ScheduledItem.swift */,
|
||||
C8093CBB1B8A72BE0088E94D /* SchedulerServices+Emulation.swift */,
|
||||
C8093CBC1B8A72BE0088E94D /* SerialDispatchQueueScheduler.swift */,
|
||||
C8F6A0EE1BEE2CB6007DF367 /* ScheduledItemType.swift */,
|
||||
C8F6A0F31BEE3395007DF367 /* InvocableType.swift */,
|
||||
C8F6A0F81BEE33C1007DF367 /* InvocableScheduledItem.swift */,
|
||||
C8F6A0FD1BEE42DD007DF367 /* AnonymousInvocable.swift */,
|
||||
);
|
||||
path = Schedulers;
|
||||
sourceTree = "<group>";
|
||||
|
|
@ -2212,8 +2236,10 @@
|
|||
C8093D4A1B8A72BE0088E94D /* Throttle.swift in Sources */,
|
||||
C8B145011BD2D80100267DCE /* ImmediateScheduler.swift in Sources */,
|
||||
C8093D061B8A72BE0088E94D /* Catch.swift in Sources */,
|
||||
C8F6A0FA1BEE33C1007DF367 /* InvocableScheduledItem.swift in Sources */,
|
||||
C8093D0C1B8A72BE0088E94D /* CombineLatest.swift in Sources */,
|
||||
D2FC15B31BCB95E5007361FF /* SkipWhile.swift in Sources */,
|
||||
C8F6A0F51BEE3395007DF367 /* InvocableType.swift in Sources */,
|
||||
C8093D5E1B8A72BE0088E94D /* Observable+Multiple.swift in Sources */,
|
||||
C8093D741B8A72BE0088E94D /* ObserverBase.swift in Sources */,
|
||||
C8093D121B8A72BE0088E94D /* ConnectableObservable.swift in Sources */,
|
||||
|
|
@ -2230,6 +2256,7 @@
|
|||
C8093D361B8A72BE0088E94D /* Sample.swift in Sources */,
|
||||
C84CC54F1BDCF48200E06A64 /* LockOwnerType.swift in Sources */,
|
||||
D2752D621BC5551A0070C418 /* SkipUntil.swift in Sources */,
|
||||
C8F6A0FF1BEE42DD007DF367 /* AnonymousInvocable.swift in Sources */,
|
||||
C84CC5541BDCF49300E06A64 /* SynchronizedOnType.swift in Sources */,
|
||||
C8093CEA1B8A72BE0088E94D /* ScopedDisposable.swift in Sources */,
|
||||
C8093D261B8A72BE0088E94D /* Multicast.swift in Sources */,
|
||||
|
|
@ -2284,6 +2311,7 @@
|
|||
C8640A041BA5B12A00D3C4E8 /* Repeat.swift in Sources */,
|
||||
C8093CF41B8A72BE0088E94D /* Error.swift in Sources */,
|
||||
C8093D141B8A72BE0088E94D /* Debug.swift in Sources */,
|
||||
C8F6A0F01BEE2CB6007DF367 /* ScheduledItemType.swift in Sources */,
|
||||
CB883B4B1BE369AA000AC2EE /* AddRef.swift in Sources */,
|
||||
C8093CCE1B8A72BE0088E94D /* Bag.swift in Sources */,
|
||||
C8093D301B8A72BE0088E94D /* Producer.swift in Sources */,
|
||||
|
|
@ -2345,8 +2373,10 @@
|
|||
C8093D491B8A72BE0088E94D /* Throttle.swift in Sources */,
|
||||
C8B145001BD2D80100267DCE /* ImmediateScheduler.swift in Sources */,
|
||||
C8093D051B8A72BE0088E94D /* Catch.swift in Sources */,
|
||||
C8F6A0F91BEE33C1007DF367 /* InvocableScheduledItem.swift in Sources */,
|
||||
C8093D0B1B8A72BE0088E94D /* CombineLatest.swift in Sources */,
|
||||
D22B6D261BC8504A00BCE0AB /* SkipWhile.swift in Sources */,
|
||||
C8F6A0F41BEE3395007DF367 /* InvocableType.swift in Sources */,
|
||||
C8093D5D1B8A72BE0088E94D /* Observable+Multiple.swift in Sources */,
|
||||
C8093D731B8A72BE0088E94D /* ObserverBase.swift in Sources */,
|
||||
C8093D111B8A72BE0088E94D /* ConnectableObservable.swift in Sources */,
|
||||
|
|
@ -2363,6 +2393,7 @@
|
|||
C8093D351B8A72BE0088E94D /* Sample.swift in Sources */,
|
||||
C84CC54E1BDCF48200E06A64 /* LockOwnerType.swift in Sources */,
|
||||
D285BAC41BC0231000B3F602 /* SkipUntil.swift in Sources */,
|
||||
C8F6A0FE1BEE42DD007DF367 /* AnonymousInvocable.swift in Sources */,
|
||||
C84CC5531BDCF49300E06A64 /* SynchronizedOnType.swift in Sources */,
|
||||
C8093CE91B8A72BE0088E94D /* ScopedDisposable.swift in Sources */,
|
||||
C8093D251B8A72BE0088E94D /* Multicast.swift in Sources */,
|
||||
|
|
@ -2417,6 +2448,7 @@
|
|||
C8640A031BA5B12A00D3C4E8 /* Repeat.swift in Sources */,
|
||||
C8093CF31B8A72BE0088E94D /* Error.swift in Sources */,
|
||||
C8093D131B8A72BE0088E94D /* Debug.swift in Sources */,
|
||||
C8F6A0EF1BEE2CB6007DF367 /* ScheduledItemType.swift in Sources */,
|
||||
CB883B4A1BE369AA000AC2EE /* AddRef.swift in Sources */,
|
||||
C8093CCD1B8A72BE0088E94D /* Bag.swift in Sources */,
|
||||
C8093D2F1B8A72BE0088E94D /* Producer.swift in Sources */,
|
||||
|
|
@ -2478,8 +2510,10 @@
|
|||
C8F0BFAA1BBBFB8B001B112F /* Throttle.swift in Sources */,
|
||||
C8B145031BD2D80100267DCE /* ImmediateScheduler.swift in Sources */,
|
||||
C8F0BFAC1BBBFB8B001B112F /* Catch.swift in Sources */,
|
||||
C8F6A0FC1BEE33C1007DF367 /* InvocableScheduledItem.swift in Sources */,
|
||||
C8F0BFAD1BBBFB8B001B112F /* CombineLatest.swift in Sources */,
|
||||
D2FC15B51BCB95E8007361FF /* SkipWhile.swift in Sources */,
|
||||
C8F6A0F71BEE3395007DF367 /* InvocableType.swift in Sources */,
|
||||
C8F0BFAE1BBBFB8B001B112F /* Observable+Multiple.swift in Sources */,
|
||||
C8F0BFAF1BBBFB8B001B112F /* ObserverBase.swift in Sources */,
|
||||
C8F0BFB01BBBFB8B001B112F /* ConnectableObservable.swift in Sources */,
|
||||
|
|
@ -2496,6 +2530,7 @@
|
|||
C8F0BFB81BBBFB8B001B112F /* Sample.swift in Sources */,
|
||||
C84CC5511BDCF48200E06A64 /* LockOwnerType.swift in Sources */,
|
||||
D21C29311BC6A1C300448E70 /* SkipUntil.swift in Sources */,
|
||||
C8F6A1011BEE42DD007DF367 /* AnonymousInvocable.swift in Sources */,
|
||||
C84CC5561BDCF49300E06A64 /* SynchronizedOnType.swift in Sources */,
|
||||
C8F0BFB91BBBFB8B001B112F /* ScopedDisposable.swift in Sources */,
|
||||
C8F0BFBA1BBBFB8B001B112F /* Multicast.swift in Sources */,
|
||||
|
|
@ -2550,6 +2585,7 @@
|
|||
C8F0BFE71BBBFB8B001B112F /* Repeat.swift in Sources */,
|
||||
C8F0BFE81BBBFB8B001B112F /* Error.swift in Sources */,
|
||||
C8F0BFE91BBBFB8B001B112F /* Debug.swift in Sources */,
|
||||
C8F6A0F21BEE2CB6007DF367 /* ScheduledItemType.swift in Sources */,
|
||||
CB883B4D1BE369AA000AC2EE /* AddRef.swift in Sources */,
|
||||
C8F0BFEA1BBBFB8B001B112F /* Bag.swift in Sources */,
|
||||
C8F0BFEB1BBBFB8B001B112F /* Producer.swift in Sources */,
|
||||
|
|
@ -2762,8 +2798,10 @@
|
|||
D2EBEB2D1BB9B6CA003A27DC /* Observable+Concurrency.swift in Sources */,
|
||||
D2EBEB381BB9B6D8003A27DC /* ConcurrentDispatchQueueScheduler.swift in Sources */,
|
||||
C8B145021BD2D80100267DCE /* ImmediateScheduler.swift in Sources */,
|
||||
C8F6A0FB1BEE33C1007DF367 /* InvocableScheduledItem.swift in Sources */,
|
||||
D2EBEB131BB9B6C1003A27DC /* Multicast.swift in Sources */,
|
||||
D2EBEB111BB9B6C1003A27DC /* Map.swift in Sources */,
|
||||
C8F6A0F61BEE3395007DF367 /* InvocableType.swift in Sources */,
|
||||
D2FC15B41BCB95E7007361FF /* SkipWhile.swift in Sources */,
|
||||
D2EBEB071BB9B6C1003A27DC /* Deferred.swift in Sources */,
|
||||
D2EBEB2C1BB9B6CA003A27DC /* Observable+Binding.swift in Sources */,
|
||||
|
|
@ -2780,6 +2818,7 @@
|
|||
D2EBEB401BB9B6DE003A27DC /* BehaviorSubject.swift in Sources */,
|
||||
C84CC5501BDCF48200E06A64 /* LockOwnerType.swift in Sources */,
|
||||
D2EBEB271BB9B6C1003A27DC /* Timer.swift in Sources */,
|
||||
C8F6A1001BEE42DD007DF367 /* AnonymousInvocable.swift in Sources */,
|
||||
C84CC5551BDCF49300E06A64 /* SynchronizedOnType.swift in Sources */,
|
||||
D2752D631BC5551B0070C418 /* SkipUntil.swift in Sources */,
|
||||
D2EBEB351BB9B6D2003A27DC /* ObserverBase.swift in Sources */,
|
||||
|
|
@ -2834,6 +2873,7 @@
|
|||
D2EBEB3D1BB9B6D8003A27DC /* SchedulerServices+Emulation.swift in Sources */,
|
||||
D2EBEB1C1BB9B6C1003A27DC /* Sample.swift in Sources */,
|
||||
D2EBEAFD1BB9B6BA003A27DC /* AnonymousObservable.swift in Sources */,
|
||||
C8F6A0F11BEE2CB6007DF367 /* ScheduledItemType.swift in Sources */,
|
||||
CB883B4C1BE369AA000AC2EE /* AddRef.swift in Sources */,
|
||||
D2EBEAFA1BB9B6B2003A27DC /* SingleAssignmentDisposable.swift in Sources */,
|
||||
D2EBEAF31BB9B6AE003A27DC /* DisposeBag.swift in Sources */,
|
||||
|
|
|
|||
|
|
@ -239,15 +239,6 @@
|
|||
C89464FA1BC6C2B00055219D /* ObserverType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C894648A1BC6C2B00055219D /* ObserverType.swift */; };
|
||||
C89464FB1BC6C2B00055219D /* Rx.swift in Sources */ = {isa = PBXBuildFile; fileRef = C894648B1BC6C2B00055219D /* Rx.swift */; };
|
||||
C89464FC1BC6C2B00055219D /* RxBox.swift in Sources */ = {isa = PBXBuildFile; fileRef = C894648C1BC6C2B00055219D /* RxBox.swift */; };
|
||||
C89464FD1BC6C2B00055219D /* ConcurrentDispatchQueueScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C894648E1BC6C2B00055219D /* ConcurrentDispatchQueueScheduler.swift */; };
|
||||
C89464FE1BC6C2B00055219D /* CurrentThreadScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C894648F1BC6C2B00055219D /* CurrentThreadScheduler.swift */; };
|
||||
C89464FF1BC6C2B00055219D /* DispatchQueueSchedulerPriority.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464901BC6C2B00055219D /* DispatchQueueSchedulerPriority.swift */; };
|
||||
C89465001BC6C2B00055219D /* MainScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464911BC6C2B00055219D /* MainScheduler.swift */; };
|
||||
C89465011BC6C2B00055219D /* OperationQueueScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464921BC6C2B00055219D /* OperationQueueScheduler.swift */; };
|
||||
C89465021BC6C2B00055219D /* RecursiveScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464931BC6C2B00055219D /* RecursiveScheduler.swift */; };
|
||||
C89465031BC6C2B00055219D /* ScheduledItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464941BC6C2B00055219D /* ScheduledItem.swift */; };
|
||||
C89465041BC6C2B00055219D /* SchedulerServices+Emulation.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464951BC6C2B00055219D /* SchedulerServices+Emulation.swift */; };
|
||||
C89465051BC6C2B00055219D /* SerialDispatchQueueScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464961BC6C2B00055219D /* SerialDispatchQueueScheduler.swift */; };
|
||||
C89465061BC6C2B00055219D /* SchedulerType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464971BC6C2B00055219D /* SchedulerType.swift */; };
|
||||
C89465071BC6C2B00055219D /* BehaviorSubject.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464991BC6C2B00055219D /* BehaviorSubject.swift */; };
|
||||
C89465081BC6C2B00055219D /* PublishSubject.swift in Sources */ = {isa = PBXBuildFile; fileRef = C894649A1BC6C2B00055219D /* PublishSubject.swift */; };
|
||||
|
|
@ -326,8 +317,6 @@
|
|||
C8A468F31B8A8C2600BF917B /* RxSwift.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C8A468EB1B8A8BC900BF917B /* RxSwift.framework */; };
|
||||
C8A7501F1B94E77C00D8D046 /* RxDataSourceStarterKit.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8A7501E1B94E77C00D8D046 /* RxDataSourceStarterKit.swift */; };
|
||||
C8A750201B94E78200D8D046 /* RxDataSourceStarterKit.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8A7501E1B94E77C00D8D046 /* RxDataSourceStarterKit.swift */; };
|
||||
C8B145141BD2E4D000267DCE /* ConcurrentMainScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8B145051BD2E45200267DCE /* ConcurrentMainScheduler.swift */; };
|
||||
C8B145161BD2E4D500267DCE /* ImmediateScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8B145041BD2E45200267DCE /* ImmediateScheduler.swift */; };
|
||||
C8C46DA81B47F7110020D71E /* CollectionViewImageCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8C46DA31B47F7110020D71E /* CollectionViewImageCell.swift */; };
|
||||
C8C46DA91B47F7110020D71E /* WikipediaImageCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = C8C46DA41B47F7110020D71E /* WikipediaImageCell.xib */; };
|
||||
C8C46DAA1B47F7110020D71E /* WikipediaSearchCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8C46DA51B47F7110020D71E /* WikipediaSearchCell.swift */; };
|
||||
|
|
@ -343,6 +332,22 @@
|
|||
C8DF92EB1B0B38C0009BCF9A /* Images.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = C8DF92E91B0B38C0009BCF9A /* Images.xcassets */; };
|
||||
C8DF92F61B0B43A4009BCF9A /* IntroductionExampleViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8DF92F51B0B43A4009BCF9A /* IntroductionExampleViewController.swift */; };
|
||||
C8E9D2AF1BD3FD960079D0DB /* ActivityIndicator.swift in Sources */ = {isa = PBXBuildFile; fileRef = C80397391BD3E17D009D8B26 /* ActivityIndicator.swift */; };
|
||||
C8F6A1271BEF9DA3007DF367 /* AnonymousInvocable.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A1041BEF9D83007DF367 /* AnonymousInvocable.swift */; };
|
||||
C8F6A1281BEF9DA3007DF367 /* InvocableScheduledItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A1051BEF9D83007DF367 /* InvocableScheduledItem.swift */; };
|
||||
C8F6A1291BEF9DA3007DF367 /* InvocableType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A1061BEF9D83007DF367 /* InvocableType.swift */; };
|
||||
C8F6A12A1BEF9DA3007DF367 /* ScheduledItemType.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A1071BEF9D83007DF367 /* ScheduledItemType.swift */; };
|
||||
C8F6A12B1BEF9DA3007DF367 /* ConcurrentDispatchQueueScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C894648E1BC6C2B00055219D /* ConcurrentDispatchQueueScheduler.swift */; };
|
||||
C8F6A12C1BEF9DA3007DF367 /* ConcurrentMainScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8B145051BD2E45200267DCE /* ConcurrentMainScheduler.swift */; };
|
||||
C8F6A12D1BEF9DA3007DF367 /* CurrentThreadScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C894648F1BC6C2B00055219D /* CurrentThreadScheduler.swift */; };
|
||||
C8F6A12E1BEF9DA3007DF367 /* DispatchQueueSchedulerPriority.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464901BC6C2B00055219D /* DispatchQueueSchedulerPriority.swift */; };
|
||||
C8F6A12F1BEF9DA3007DF367 /* ImmediateScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8B145041BD2E45200267DCE /* ImmediateScheduler.swift */; };
|
||||
C8F6A1301BEF9DA3007DF367 /* MainScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464911BC6C2B00055219D /* MainScheduler.swift */; };
|
||||
C8F6A1311BEF9DA3007DF367 /* OperationQueueScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464921BC6C2B00055219D /* OperationQueueScheduler.swift */; };
|
||||
C8F6A1321BEF9DA3007DF367 /* RecursiveScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464931BC6C2B00055219D /* RecursiveScheduler.swift */; };
|
||||
C8F6A1331BEF9DA3007DF367 /* ScheduledItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464941BC6C2B00055219D /* ScheduledItem.swift */; };
|
||||
C8F6A1341BEF9DA3007DF367 /* SchedulerServices+Emulation.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464951BC6C2B00055219D /* SchedulerServices+Emulation.swift */; };
|
||||
C8F6A1351BEF9DA3007DF367 /* SerialDispatchQueueScheduler.swift in Sources */ = {isa = PBXBuildFile; fileRef = C89464961BC6C2B00055219D /* SerialDispatchQueueScheduler.swift */; };
|
||||
C8F6A1381BEF9DF6007DF367 /* RetryWhen.swift in Sources */ = {isa = PBXBuildFile; fileRef = C8F6A1361BEF9DD4007DF367 /* RetryWhen.swift */; };
|
||||
CB883B501BE3AC54000AC2EE /* BooleanDisposable.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB883B4E1BE3AC54000AC2EE /* BooleanDisposable.swift */; };
|
||||
CB883B511BE3AC54000AC2EE /* RefCountDisposable.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB883B4F1BE3AC54000AC2EE /* RefCountDisposable.swift */; };
|
||||
CB883B601BE3AC72000AC2EE /* Window.swift in Sources */ = {isa = PBXBuildFile; fileRef = CB883B5E1BE3AC72000AC2EE /* Window.swift */; };
|
||||
|
|
@ -737,6 +742,11 @@
|
|||
C8DF92F01B0B3E67009BCF9A /* Info-OSX.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = "Info-OSX.plist"; sourceTree = "<group>"; };
|
||||
C8DF92F21B0B3E71009BCF9A /* Info-iOS.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = "Info-iOS.plist"; sourceTree = "<group>"; };
|
||||
C8DF92F51B0B43A4009BCF9A /* IntroductionExampleViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; lineEnding = 0; path = IntroductionExampleViewController.swift; sourceTree = "<group>"; xcLanguageSpecificationIdentifier = xcode.lang.swift; };
|
||||
C8F6A1041BEF9D83007DF367 /* AnonymousInvocable.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AnonymousInvocable.swift; sourceTree = "<group>"; };
|
||||
C8F6A1051BEF9D83007DF367 /* InvocableScheduledItem.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = InvocableScheduledItem.swift; sourceTree = "<group>"; };
|
||||
C8F6A1061BEF9D83007DF367 /* InvocableType.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = InvocableType.swift; sourceTree = "<group>"; };
|
||||
C8F6A1071BEF9D83007DF367 /* ScheduledItemType.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ScheduledItemType.swift; sourceTree = "<group>"; };
|
||||
C8F6A1361BEF9DD4007DF367 /* RetryWhen.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = RetryWhen.swift; sourceTree = "<group>"; };
|
||||
CB883B4E1BE3AC54000AC2EE /* BooleanDisposable.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BooleanDisposable.swift; sourceTree = "<group>"; };
|
||||
CB883B4F1BE3AC54000AC2EE /* RefCountDisposable.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = RefCountDisposable.swift; sourceTree = "<group>"; };
|
||||
CB883B5E1BE3AC72000AC2EE /* Window.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Window.swift; sourceTree = "<group>"; };
|
||||
|
|
@ -1150,6 +1160,7 @@
|
|||
C89464481BC6C2B00055219D /* Implementations */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
C8F6A1361BEF9DD4007DF367 /* RetryWhen.swift */,
|
||||
CB883B5F1BE3AC72000AC2EE /* AddRef.swift */,
|
||||
C89464491BC6C2B00055219D /* Amb.swift */,
|
||||
C894644A1BC6C2B00055219D /* AnonymousObservable.swift */,
|
||||
|
|
@ -1225,6 +1236,10 @@
|
|||
C894648D1BC6C2B00055219D /* Schedulers */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
C8F6A1041BEF9D83007DF367 /* AnonymousInvocable.swift */,
|
||||
C8F6A1051BEF9D83007DF367 /* InvocableScheduledItem.swift */,
|
||||
C8F6A1061BEF9D83007DF367 /* InvocableType.swift */,
|
||||
C8F6A1071BEF9D83007DF367 /* ScheduledItemType.swift */,
|
||||
C894648E1BC6C2B00055219D /* ConcurrentDispatchQueueScheduler.swift */,
|
||||
C8B145051BD2E45200267DCE /* ConcurrentMainScheduler.swift */,
|
||||
C894648F1BC6C2B00055219D /* CurrentThreadScheduler.swift */,
|
||||
|
|
@ -1677,19 +1692,21 @@
|
|||
C84CC58B1BDD486300E06A64 /* LockOwnerType.swift in Sources */,
|
||||
C89465971BC6C2BC0055219D /* UIScrollView+Rx.swift in Sources */,
|
||||
C8297E2F1B6CF905000589EA /* RxTableViewSectionedAnimatedDataSource.swift in Sources */,
|
||||
C89464FF1BC6C2B00055219D /* DispatchQueueSchedulerPriority.swift in Sources */,
|
||||
C89464D41BC6C2B00055219D /* ObserveOn.swift in Sources */,
|
||||
C894659B1BC6C2BC0055219D /* UIStepper+Rx.swift in Sources */,
|
||||
C8A7501F1B94E77C00D8D046 /* RxDataSourceStarterKit.swift in Sources */,
|
||||
C89464F61BC6C2B00055219D /* AnonymousObserver.swift in Sources */,
|
||||
C89464C81BC6C2B00055219D /* DistinctUntilChanged.swift in Sources */,
|
||||
C89464CF1BC6C2B00055219D /* Just.swift in Sources */,
|
||||
C8F6A1381BEF9DF6007DF367 /* RetryWhen.swift in Sources */,
|
||||
C8297E301B6CF905000589EA /* RandomUserAPI.swift in Sources */,
|
||||
C89465921BC6C2BC0055219D /* UIControl+Rx.swift in Sources */,
|
||||
C894650B1BC6C2B00055219D /* Variable.swift in Sources */,
|
||||
C8297E311B6CF905000589EA /* SearchResultViewModel.swift in Sources */,
|
||||
C8F6A12D1BEF9DA3007DF367 /* CurrentThreadScheduler.swift in Sources */,
|
||||
C89464D91BC6C2B00055219D /* RefCount.swift in Sources */,
|
||||
C89465731BC6C2BC0055219D /* Deallocating.swift in Sources */,
|
||||
C8F6A1271BEF9DA3007DF367 /* AnonymousInvocable.swift in Sources */,
|
||||
C89464A51BC6C2B00055219D /* Disposable.swift in Sources */,
|
||||
C89464F91BC6C2B00055219D /* ObserverType+Extensions.swift in Sources */,
|
||||
C84CC58D1BDD486300E06A64 /* SynchronizedOnType.swift in Sources */,
|
||||
|
|
@ -1709,6 +1726,7 @@
|
|||
C89465651BC6C2BC0055219D /* CLLocationManager+Rx.swift in Sources */,
|
||||
C80DDED81BCE9046006A1832 /* Driver.swift in Sources */,
|
||||
C80DDED71BCE9046006A1832 /* Driver+Subscription.swift in Sources */,
|
||||
C8F6A1321BEF9DA3007DF367 /* RecursiveScheduler.swift in Sources */,
|
||||
07A5C3DC1B70B703001EFE5C /* CalculatorViewController.swift in Sources */,
|
||||
C89465961BC6C2BC0055219D /* UILabel+Rx.swift in Sources */,
|
||||
C894659C1BC6C2BC0055219D /* UISwitch+Rx.swift in Sources */,
|
||||
|
|
@ -1720,9 +1738,7 @@
|
|||
C8297E341B6CF905000589EA /* UIImageView+Extensions.swift in Sources */,
|
||||
B1604CC41BE5B8CE002E1279 /* DownloadableImage.swift in Sources */,
|
||||
C80DDED61BCE9046006A1832 /* Driver+Operators.swift in Sources */,
|
||||
C89465051BC6C2B00055219D /* SerialDispatchQueueScheduler.swift in Sources */,
|
||||
C89464B81BC6C2B00055219D /* Observable.swift in Sources */,
|
||||
C89465001BC6C2B00055219D /* MainScheduler.swift in Sources */,
|
||||
C8297E351B6CF905000589EA /* NumberSectionView.swift in Sources */,
|
||||
C894659E1BC6C2BC0055219D /* UITextField+Rx.swift in Sources */,
|
||||
C89464D11BC6C2B00055219D /* Merge.swift in Sources */,
|
||||
|
|
@ -1738,7 +1754,6 @@
|
|||
C8297E391B6CF905000589EA /* CollectionViewImageCell.swift in Sources */,
|
||||
C894649E1BC6C2B00055219D /* Cancelable.swift in Sources */,
|
||||
C89464E01BC6C2B00055219D /* SubscribeOn.swift in Sources */,
|
||||
C89465031BC6C2B00055219D /* ScheduledItem.swift in Sources */,
|
||||
C89465801BC6C2BC0055219D /* RxTableViewReactiveArrayDataSource.swift in Sources */,
|
||||
C89464AF1BC6C2B00055219D /* ScopedDisposable.swift in Sources */,
|
||||
C89464FA1BC6C2B00055219D /* ObserverType.swift in Sources */,
|
||||
|
|
@ -1762,7 +1777,7 @@
|
|||
C89464F21BC6C2B00055219D /* Observable+StandardSequenceOperators.swift in Sources */,
|
||||
C89464CC1BC6C2B00055219D /* Filter.swift in Sources */,
|
||||
C80DDED31BCE9046006A1832 /* ControlProperty+Driver.swift in Sources */,
|
||||
C89465021BC6C2B00055219D /* RecursiveScheduler.swift in Sources */,
|
||||
C8F6A12E1BEF9DA3007DF367 /* DispatchQueueSchedulerPriority.swift in Sources */,
|
||||
C89464C11BC6C2B00055219D /* CombineLatest+CollectionType.swift in Sources */,
|
||||
C89465671BC6C2BC0055219D /* ControlEvent.swift in Sources */,
|
||||
C8297E3B1B6CF905000589EA /* String+extensions.swift in Sources */,
|
||||
|
|
@ -1777,7 +1792,6 @@
|
|||
B1604CC21BE5B895002E1279 /* ReachabilityService.swift in Sources */,
|
||||
C89464DE1BC6C2B00055219D /* Skip.swift in Sources */,
|
||||
C89464DB1BC6C2B00055219D /* Sample.swift in Sources */,
|
||||
C89465011BC6C2B00055219D /* OperationQueueScheduler.swift in Sources */,
|
||||
C89465791BC6C2BC0055219D /* NSObject+Rx.swift in Sources */,
|
||||
C89464F31BC6C2B00055219D /* Observable+Time.swift in Sources */,
|
||||
C89464F11BC6C2B00055219D /* Observable+Single.swift in Sources */,
|
||||
|
|
@ -1796,18 +1810,20 @@
|
|||
C8297E401B6CF905000589EA /* ImageService.swift in Sources */,
|
||||
C89464AD1BC6C2B00055219D /* NopDisposable.swift in Sources */,
|
||||
C84CC5901BDD486300E06A64 /* AsyncLock.swift in Sources */,
|
||||
C8F6A1311BEF9DA3007DF367 /* OperationQueueScheduler.swift in Sources */,
|
||||
CBEE77541BD8C7B700AD584C /* ToArray.swift in Sources */,
|
||||
C89465771BC6C2BC0055219D /* NSNotificationCenter+Rx.swift in Sources */,
|
||||
C89465091BC6C2B00055219D /* ReplaySubject.swift in Sources */,
|
||||
C8F6A1281BEF9DA3007DF367 /* InvocableScheduledItem.swift in Sources */,
|
||||
C8297E411B6CF905000589EA /* RxCollectionViewSectionedReloadDataSource.swift in Sources */,
|
||||
C84CC58E1BDD486300E06A64 /* SynchronizedSubscribeType.swift in Sources */,
|
||||
C8F6A12F1BEF9DA3007DF367 /* ImmediateScheduler.swift in Sources */,
|
||||
C89464A81BC6C2B00055219D /* CompositeDisposable.swift in Sources */,
|
||||
C89464D21BC6C2B00055219D /* Multicast.swift in Sources */,
|
||||
C89465821BC6C2BC0055219D /* RxCollectionViewDataSourceType.swift in Sources */,
|
||||
C8297E421B6CF905000589EA /* WikipediaSearchResult.swift in Sources */,
|
||||
C89465701BC6C2BC0055219D /* Logging.swift in Sources */,
|
||||
C89464A31BC6C2B00055219D /* InfiniteSequence.swift in Sources */,
|
||||
C89465041BC6C2B00055219D /* SchedulerServices+Emulation.swift in Sources */,
|
||||
C89465611BC6C2BC0055219D /* _RX.m in Sources */,
|
||||
C80DDED41BCE9046006A1832 /* Driver+Operators+arity.swift in Sources */,
|
||||
C89465841BC6C2BC0055219D /* RxActionSheetDelegateProxy.swift in Sources */,
|
||||
|
|
@ -1816,12 +1832,12 @@
|
|||
C803974A1BD3E9A6009D8B26 /* GitHubSearchRepositoriesAPI.swift in Sources */,
|
||||
C84CC52E1BDC344100E06A64 /* ElementAt.swift in Sources */,
|
||||
C8297E431B6CF905000589EA /* GitHubAPI.swift in Sources */,
|
||||
C8F6A1331BEF9DA3007DF367 /* ScheduledItem.swift in Sources */,
|
||||
C89464EB1BC6C2B00055219D /* Observable+Aggregate.swift in Sources */,
|
||||
C8297E441B6CF905000589EA /* PseudoRandomGenerator.swift in Sources */,
|
||||
C8297E451B6CF905000589EA /* SectionedViewType.swift in Sources */,
|
||||
C89464D51BC6C2B00055219D /* ObserveOnSerialDispatchQueue.swift in Sources */,
|
||||
C894658E1BC6C2BC0055219D /* UIAlertView+Rx.swift in Sources */,
|
||||
C8B145161BD2E4D500267DCE /* ImmediateScheduler.swift in Sources */,
|
||||
C8297E461B6CF905000589EA /* Example.swift in Sources */,
|
||||
C89465081BC6C2B00055219D /* PublishSubject.swift in Sources */,
|
||||
C89464FC1BC6C2B00055219D /* RxBox.swift in Sources */,
|
||||
|
|
@ -1833,7 +1849,6 @@
|
|||
B18F3BC11BD93E00000AAC79 /* Reachability.swift in Sources */,
|
||||
C89465901BC6C2BC0055219D /* UIButton+Rx.swift in Sources */,
|
||||
C89464DD1BC6C2B00055219D /* Sink.swift in Sources */,
|
||||
C89464FE1BC6C2B00055219D /* CurrentThreadScheduler.swift in Sources */,
|
||||
C89464BE1BC6C2B00055219D /* Catch.swift in Sources */,
|
||||
C89CDB721BCC45EE002063D9 /* SkipUntil.swift in Sources */,
|
||||
B1604CCB1BE5BC45002E1279 /* UIImageView+DownloadableImage.swift in Sources */,
|
||||
|
|
@ -1843,8 +1858,8 @@
|
|||
C89465951BC6C2BC0055219D /* UIImageView+Rx.swift in Sources */,
|
||||
C89464E31BC6C2B00055219D /* TakeUntil.swift in Sources */,
|
||||
C89464FB1BC6C2B00055219D /* Rx.swift in Sources */,
|
||||
C89464FD1BC6C2B00055219D /* ConcurrentDispatchQueueScheduler.swift in Sources */,
|
||||
C84CC5911BDD48B800E06A64 /* SubscriptionDisposable.swift in Sources */,
|
||||
C8F6A1341BEF9DA3007DF367 /* SchedulerServices+Emulation.swift in Sources */,
|
||||
C89464C71BC6C2B00055219D /* DelaySubscription.swift in Sources */,
|
||||
C8297E481B6CF905000589EA /* Differentiator.swift in Sources */,
|
||||
C8297E491B6CF905000589EA /* WikipediaSearchCell.swift in Sources */,
|
||||
|
|
@ -1855,6 +1870,8 @@
|
|||
C8297E4C1B6CF905000589EA /* APIWrappersViewController.swift in Sources */,
|
||||
C89465621BC6C2BC0055219D /* _RXDelegateProxy.m in Sources */,
|
||||
C89464D31BC6C2B00055219D /* Never.swift in Sources */,
|
||||
C8F6A12A1BEF9DA3007DF367 /* ScheduledItemType.swift in Sources */,
|
||||
C8F6A1351BEF9DA3007DF367 /* SerialDispatchQueueScheduler.swift in Sources */,
|
||||
C8297E4D1B6CF905000589EA /* RxTableViewSectionedReloadDataSource.swift in Sources */,
|
||||
C89465931BC6C2BC0055219D /* UIDatePicker+Rx.swift in Sources */,
|
||||
C84CC58F1BDD486300E06A64 /* SynchronizedUnsubscribeType.swift in Sources */,
|
||||
|
|
@ -1862,9 +1879,11 @@
|
|||
C89CDB711BCC45E5002063D9 /* ShareReplay1.swift in Sources */,
|
||||
C89464BD1BC6C2B00055219D /* Buffer.swift in Sources */,
|
||||
C89464B31BC6C2B00055219D /* Error.swift in Sources */,
|
||||
C8F6A1301BEF9DA3007DF367 /* MainScheduler.swift in Sources */,
|
||||
C89464C51BC6C2B00055219D /* Debug.swift in Sources */,
|
||||
C89464AB1BC6C2B00055219D /* NAryDisposable.swift in Sources */,
|
||||
C89465631BC6C2BC0055219D /* _RXKVOObserver.m in Sources */,
|
||||
C8F6A12B1BEF9DA3007DF367 /* ConcurrentDispatchQueueScheduler.swift in Sources */,
|
||||
C894656E1BC6C2BC0055219D /* DelegateProxy.swift in Sources */,
|
||||
C89464EF1BC6C2B00055219D /* Observable+Debug.swift in Sources */,
|
||||
C89464E91BC6C2B00055219D /* Zip+CollectionType.swift in Sources */,
|
||||
|
|
@ -1878,7 +1897,6 @@
|
|||
D2AF91981BD3D95900A008C1 /* Using.swift in Sources */,
|
||||
C8297E501B6CF905000589EA /* TableViewController.swift in Sources */,
|
||||
C8297E511B6CF905000589EA /* PartialUpdatesViewController.swift in Sources */,
|
||||
C8B145141BD2E4D000267DCE /* ConcurrentMainScheduler.swift in Sources */,
|
||||
C8297E521B6CF905000589EA /* Dependencies.swift in Sources */,
|
||||
C80DDED91BCE9046006A1832 /* ObservableConvertibleType+Driver.swift in Sources */,
|
||||
C89464E11BC6C2B00055219D /* Switch.swift in Sources */,
|
||||
|
|
@ -1888,11 +1906,13 @@
|
|||
C894658B1BC6C2BC0055219D /* RxTableViewDelegateProxy.swift in Sources */,
|
||||
C8297E531B6CF905000589EA /* WikipediaAPI.swift in Sources */,
|
||||
C89465071BC6C2B00055219D /* BehaviorSubject.swift in Sources */,
|
||||
C8F6A1291BEF9DA3007DF367 /* InvocableType.swift in Sources */,
|
||||
C89465911BC6C2BC0055219D /* UICollectionView+Rx.swift in Sources */,
|
||||
C89465781BC6C2BC0055219D /* NSObject+Rx+CoreGraphics.swift in Sources */,
|
||||
C89464D01BC6C2B00055219D /* Map.swift in Sources */,
|
||||
C8297E541B6CF905000589EA /* AppDelegate.swift in Sources */,
|
||||
C894659D1BC6C2BC0055219D /* UITableView+Rx.swift in Sources */,
|
||||
C8F6A12C1BEF9DA3007DF367 /* ConcurrentMainScheduler.swift in Sources */,
|
||||
C894657F1BC6C2BC0055219D /* RxCollectionViewReactiveArrayDataSource.swift in Sources */,
|
||||
C8297E551B6CF905000589EA /* RxTableViewSectionedDataSource.swift in Sources */,
|
||||
C8297E561B6CF905000589EA /* WikipediaPage.swift in Sources */,
|
||||
|
|
|
|||
|
|
@ -41,9 +41,7 @@ public struct AnyObserver<Element> : ObserverType {
|
|||
- parameter observer: Observer that receives sequence events.
|
||||
*/
|
||||
public init<O : ObserverType where O.E == Element>(_ observer: O) {
|
||||
self.observer = { e in
|
||||
return observer.on(e)
|
||||
}
|
||||
self.observer = observer.on
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -54,6 +52,15 @@ public struct AnyObserver<Element> : ObserverType {
|
|||
public func on(event: Event<Element>) {
|
||||
return self.observer(event)
|
||||
}
|
||||
|
||||
/**
|
||||
Erases type of observer and returns canonical observer.
|
||||
|
||||
- returns: type erased observer.
|
||||
*/
|
||||
func asObserver() -> AnyObserver<E> {
|
||||
return self
|
||||
}
|
||||
}
|
||||
|
||||
extension ObserverType {
|
||||
|
|
|
|||
|
|
@ -18,50 +18,74 @@ and pending work.
|
|||
|
||||
That means that enqueued work could possibly be executed later on a different thread.
|
||||
*/
|
||||
class AsyncLock : Disposable {
|
||||
class AsyncLock<I: InvocableType>
|
||||
: Disposable
|
||||
, Lock
|
||||
, SynchronizedDisposeType {
|
||||
typealias Action = () -> Void
|
||||
|
||||
private let _lock = NSRecursiveLock()
|
||||
var _lock = SpinLock()
|
||||
|
||||
private var _queue: Queue<Action> = Queue(capacity: 2)
|
||||
private var _queue: Queue<I> = Queue(capacity: 0)
|
||||
|
||||
private var _isAcquired: Bool = false
|
||||
private var _isExecuting: Bool = false
|
||||
private var _hasFaulted: Bool = false
|
||||
|
||||
init() {
|
||||
|
||||
|
||||
// lock {
|
||||
func lock() {
|
||||
_lock.lock()
|
||||
}
|
||||
|
||||
func wait(action: Action) {
|
||||
let isOwner = _lock.calculateLocked { () -> Bool in
|
||||
|
||||
func unlock() {
|
||||
_lock.unlock()
|
||||
}
|
||||
// }
|
||||
|
||||
private func enqueue(action: I) -> I? {
|
||||
_lock.lock(); defer { _lock.unlock() } // {
|
||||
if _hasFaulted {
|
||||
return false
|
||||
return nil
|
||||
}
|
||||
|
||||
_queue.enqueue(action)
|
||||
let isOwner = !_isAcquired
|
||||
_isAcquired = true
|
||||
|
||||
return isOwner
|
||||
}
|
||||
|
||||
if _isExecuting {
|
||||
_queue.enqueue(action)
|
||||
return nil
|
||||
}
|
||||
|
||||
_isExecuting = true
|
||||
|
||||
return action
|
||||
// }
|
||||
}
|
||||
|
||||
private func dequeue() -> I? {
|
||||
_lock.lock(); defer { _lock.unlock() } // {
|
||||
if _queue.count > 0 {
|
||||
return _queue.dequeue()
|
||||
}
|
||||
else {
|
||||
_isExecuting = false
|
||||
return nil
|
||||
}
|
||||
// }
|
||||
}
|
||||
|
||||
func invoke(action: I) {
|
||||
let firstEnqueuedAction = enqueue(action)
|
||||
|
||||
if !isOwner {
|
||||
if let firstEnqueuedAction = firstEnqueuedAction {
|
||||
firstEnqueuedAction.invoke()
|
||||
}
|
||||
else {
|
||||
// action is enqueued, it's somebody else's concern now
|
||||
return
|
||||
}
|
||||
|
||||
while true {
|
||||
let nextAction = _lock.calculateLocked { () -> Action? in
|
||||
if _queue.count > 0 {
|
||||
return _queue.dequeue()
|
||||
}
|
||||
else {
|
||||
_isAcquired = false
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
let nextAction = dequeue()
|
||||
|
||||
if let nextAction = nextAction {
|
||||
nextAction()
|
||||
nextAction.invoke()
|
||||
}
|
||||
else {
|
||||
return
|
||||
|
|
@ -70,9 +94,11 @@ class AsyncLock : Disposable {
|
|||
}
|
||||
|
||||
func dispose() {
|
||||
_lock.performLocked { oldState in
|
||||
_queue = Queue(capacity: 0)
|
||||
_hasFaulted = true
|
||||
}
|
||||
synchronizedDispose()
|
||||
}
|
||||
|
||||
func _synchronized_dispose() {
|
||||
_queue = Queue(capacity: 0)
|
||||
_hasFaulted = true
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -29,8 +29,8 @@ class AnonymousObservableSink<O: ObserverType> : Sink<O>, ObserverType {
|
|||
forwardOn(event)
|
||||
case .Error, .Completed:
|
||||
if OSAtomicCompareAndSwap32(0, 1, &_isStopped) {
|
||||
self.forwardOn(event)
|
||||
self.dispose()
|
||||
forwardOn(event)
|
||||
dispose()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -95,7 +95,9 @@ class Catch<Element> : Producer<Element> {
|
|||
|
||||
// catch enumerable
|
||||
|
||||
class CatchSequenceSink<S: SequenceType, O: ObserverType where S.Generator.Element : ObservableConvertibleType, S.Generator.Element.E == O.E> : TailRecursiveSink<S, O> {
|
||||
class CatchSequenceSink<S: SequenceType, O: ObserverType where S.Generator.Element : ObservableConvertibleType, S.Generator.Element.E == O.E>
|
||||
: TailRecursiveSink<S, O>
|
||||
, ObserverType {
|
||||
typealias Element = O.E
|
||||
typealias Parent = CatchSequence<S>
|
||||
|
||||
|
|
@ -105,18 +107,22 @@ class CatchSequenceSink<S: SequenceType, O: ObserverType where S.Generator.Eleme
|
|||
super.init(observer: observer)
|
||||
}
|
||||
|
||||
override func on(event: Event<Element>) {
|
||||
func on(event: Event<Element>) {
|
||||
switch event {
|
||||
case .Next:
|
||||
forwardOn(event)
|
||||
case .Error(let error):
|
||||
_lastError = error
|
||||
scheduleMoveNext()
|
||||
schedule(.MoveNext)
|
||||
case .Completed:
|
||||
forwardOn(event)
|
||||
dispose()
|
||||
}
|
||||
}
|
||||
|
||||
override func subscribeToNext(source: Observable<E>) -> Disposable {
|
||||
return source.subscribe(self)
|
||||
}
|
||||
|
||||
override func done() {
|
||||
if let lastError = _lastError {
|
||||
|
|
|
|||
|
|
@ -9,14 +9,16 @@
|
|||
import Foundation
|
||||
|
||||
|
||||
class ConcatSink<S: SequenceType, O: ObserverType where S.Generator.Element : ObservableConvertibleType, S.Generator.Element.E == O.E> : TailRecursiveSink<S, O> {
|
||||
class ConcatSink<S: SequenceType, O: ObserverType where S.Generator.Element : ObservableConvertibleType, S.Generator.Element.E == O.E>
|
||||
: TailRecursiveSink<S, O>
|
||||
, ObserverType {
|
||||
typealias Element = O.E
|
||||
|
||||
override init(observer: O) {
|
||||
super.init(observer: observer)
|
||||
}
|
||||
|
||||
override func on(event: Event<Element>){
|
||||
func on(event: Event<Element>){
|
||||
switch event {
|
||||
case .Next:
|
||||
forwardOn(event)
|
||||
|
|
@ -24,9 +26,13 @@ class ConcatSink<S: SequenceType, O: ObserverType where S.Generator.Element : Ob
|
|||
forwardOn(event)
|
||||
dispose()
|
||||
case .Completed:
|
||||
scheduleMoveNext()
|
||||
schedule(.MoveNext)
|
||||
}
|
||||
}
|
||||
|
||||
override func subscribeToNext(source: Observable<E>) -> Disposable {
|
||||
return source.subscribe(self)
|
||||
}
|
||||
|
||||
override func extract(observable: Observable<E>) -> S.Generator? {
|
||||
if let source = observable as? Concat<S> {
|
||||
|
|
|
|||
|
|
@ -8,126 +8,145 @@
|
|||
|
||||
import Foundation
|
||||
|
||||
class RetryTriggerSink<S: SequenceType, O: ObserverType, RetryTriggerType, Error: ErrorType where S.Generator.Element : ObservableType, S.Generator.Element.E == O.E> : ObserverType {
|
||||
typealias E = RetryTriggerType
|
||||
class RetryTriggerSink<S: SequenceType, O: ObserverType, TriggerObservable: ObservableType, Error where S.Generator.Element : ObservableType, S.Generator.Element.E == O.E>
|
||||
: ObserverType {
|
||||
typealias E = TriggerObservable.E
|
||||
|
||||
typealias Parent = RetryWhenSequenceSink<S, O, RetryTriggerType, Error>
|
||||
|
||||
let parent: Parent
|
||||
typealias Parent = RetryWhenSequenceSinkIter<S, O, TriggerObservable, Error>
|
||||
|
||||
private let _parent: Parent
|
||||
|
||||
init(parent: Parent) {
|
||||
self.parent = parent
|
||||
_parent = parent
|
||||
}
|
||||
|
||||
|
||||
func on(event: Event<E>) {
|
||||
switch event {
|
||||
case .Next:
|
||||
parent.lock.performLocked() {
|
||||
parent.handlerSubscription.dispose()
|
||||
parent.lastError = nil
|
||||
parent.scheduleMoveNext()
|
||||
}
|
||||
case .Error(_):
|
||||
parent.lock.performLocked() {
|
||||
parent.done()
|
||||
}
|
||||
case .Completed:
|
||||
parent.lock.performLocked() {
|
||||
parent.lastError = nil
|
||||
parent.done()
|
||||
}
|
||||
}
|
||||
switch event {
|
||||
case .Next:
|
||||
_parent._parent._lastError = nil
|
||||
_parent._parent.schedule(.MoveNext)
|
||||
case .Error(let e):
|
||||
_parent._parent.forwardOn(.Error(e))
|
||||
_parent._parent.dispose()
|
||||
case .Completed:
|
||||
_parent._parent.forwardOn(.Completed)
|
||||
_parent._parent.dispose()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class RetryWhenSequenceSink<S: SequenceType, O: ObserverType, RetryTriggerType, Error: ErrorType where S.Generator.Element : ObservableType, S.Generator.Element.E == O.E> : TailRecursiveSink<S, O> {
|
||||
typealias Element = O.E
|
||||
typealias Parent = RetryWhenSequence<S, RetryTriggerType, Error>
|
||||
|
||||
let lock = NSRecursiveLock()
|
||||
|
||||
let parent: Parent
|
||||
|
||||
var lastError: ErrorType?
|
||||
let errorSubject = PublishSubject<Error>()
|
||||
let handler: Observable<RetryTriggerType>
|
||||
let handlerSubscription = SerialDisposable()
|
||||
|
||||
init(parent: Parent, observer: O, cancel: Disposable) {
|
||||
self.parent = parent
|
||||
self.handler = parent.notificationHandler(errorSubject.asObservable())
|
||||
super.init(observer: observer, cancel: cancel)
|
||||
class RetryWhenSequenceSinkIter<S: SequenceType, O: ObserverType, TriggerObservable: ObservableType, Error where S.Generator.Element : ObservableType, S.Generator.Element.E == O.E>
|
||||
: SingleAssignmentDisposable
|
||||
, ObserverType {
|
||||
typealias E = O.E
|
||||
typealias Parent = RetryWhenSequenceSink<S, O, TriggerObservable, Error>
|
||||
|
||||
private let _parent: Parent
|
||||
private let _errorHandlerSubscription = SingleAssignmentDisposable()
|
||||
|
||||
init(parent: Parent) {
|
||||
_parent = parent
|
||||
}
|
||||
|
||||
override func on(event: Event<E>) {
|
||||
guard lastError == nil else {
|
||||
return
|
||||
}
|
||||
|
||||
|
||||
func on(event: Event<E>) {
|
||||
switch event {
|
||||
case .Next:
|
||||
observer?.on(event)
|
||||
_parent.forwardOn(event)
|
||||
case .Error(let error):
|
||||
lock.performLocked() {
|
||||
self.lastError = error
|
||||
handlerSubscription.disposable = handler.subscribeSafe(RetryTriggerSink(parent: self))
|
||||
errorSubject.on(.Next(error as! Error))
|
||||
_parent._lastError = error
|
||||
|
||||
if let failedWith = error as? Error {
|
||||
// dispose current subscription
|
||||
super.dispose()
|
||||
|
||||
let errorHandlerSubscription = _parent._notifier.subscribe(RetryTriggerSink(parent: self))
|
||||
_errorHandlerSubscription.disposable = errorHandlerSubscription
|
||||
_parent._errorSubject.on(.Next(failedWith))
|
||||
}
|
||||
else {
|
||||
_parent.forwardOn(.Error(error))
|
||||
_parent.dispose()
|
||||
}
|
||||
case .Completed:
|
||||
observer?.on(event)
|
||||
handlerSubscription.dispose()
|
||||
dispose()
|
||||
_parent.forwardOn(event)
|
||||
_parent.dispose()
|
||||
}
|
||||
}
|
||||
|
||||
override func dispose() {
|
||||
super.dispose()
|
||||
_errorHandlerSubscription.dispose()
|
||||
}
|
||||
}
|
||||
|
||||
class RetryWhenSequenceSink<S: SequenceType, O: ObserverType, TriggerObservable: ObservableType, Error where S.Generator.Element : ObservableType, S.Generator.Element.E == O.E>
|
||||
: TailRecursiveSink<S, O> {
|
||||
typealias Element = O.E
|
||||
typealias Parent = RetryWhenSequence<S, TriggerObservable, Error>
|
||||
|
||||
let _lock = NSRecursiveLock()
|
||||
|
||||
private let _parent: Parent
|
||||
|
||||
private var _lastError: ErrorType?
|
||||
private let _errorSubject = PublishSubject<Error>()
|
||||
private let _handler: Observable<TriggerObservable.E>
|
||||
private let _notifier = PublishSubject<TriggerObservable.E>()
|
||||
|
||||
init(parent: Parent, observer: O) {
|
||||
_parent = parent
|
||||
_handler = parent._notificationHandler(_errorSubject).asObservable()
|
||||
super.init(observer: observer)
|
||||
}
|
||||
|
||||
override func done() {
|
||||
if let lastError = self.lastError {
|
||||
observer?.on(.Error(lastError))
|
||||
self.lastError = nil
|
||||
if let lastError = _lastError {
|
||||
forwardOn(.Error(lastError))
|
||||
_lastError = nil
|
||||
}
|
||||
else {
|
||||
observer?.on(.Completed)
|
||||
forwardOn(.Completed)
|
||||
}
|
||||
self.dispose()
|
||||
}
|
||||
|
||||
override func dispose() {
|
||||
|
||||
super.dispose()
|
||||
|
||||
dispose()
|
||||
}
|
||||
|
||||
override func extract(observable: Observable<E>) -> S.Generator? {
|
||||
if let onError = observable as? RetryWhenSequence<S, RetryTriggerType, Error> {
|
||||
return onError.sources.generate()
|
||||
if let onError = observable as? RetryWhenSequence<S, TriggerObservable, Error> {
|
||||
return onError._sources.generate()
|
||||
}
|
||||
else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
override func subscribeToNext(source: Observable<E>) -> Disposable {
|
||||
let iter = RetryWhenSequenceSinkIter(parent: self)
|
||||
iter.disposable = source.subscribe(iter)
|
||||
return iter
|
||||
}
|
||||
|
||||
override func run(sources: S.Generator) -> Disposable {
|
||||
_generators.append(sources)
|
||||
|
||||
scheduleMoveNext()
|
||||
|
||||
return handlerSubscription
|
||||
let triggerSubscription = _handler.subscribe(_notifier.asObserver())
|
||||
let superSubscription = super.run(sources)
|
||||
return StableCompositeDisposable.create(superSubscription, triggerSubscription)
|
||||
}
|
||||
}
|
||||
|
||||
class RetryWhenSequence<S: SequenceType, RetryTriggerType, Error: ErrorType where S.Generator.Element : ObservableType> : Producer<S.Generator.Element.E> {
|
||||
class RetryWhenSequence<S: SequenceType, TriggerObservable: ObservableType, Error where S.Generator.Element : ObservableType> : Producer<S.Generator.Element.E> {
|
||||
typealias Element = S.Generator.Element.E
|
||||
|
||||
let sources: S
|
||||
let notificationHandler: Observable<Error> -> Observable<RetryTriggerType>
|
||||
private let _sources: S
|
||||
private let _notificationHandler: Observable<Error> -> TriggerObservable
|
||||
|
||||
init(sources: S, notificationHandler: Observable<Error> -> Observable<RetryTriggerType>) {
|
||||
self.sources = sources
|
||||
self.notificationHandler = notificationHandler
|
||||
init(sources: S, notificationHandler: Observable<Error> -> TriggerObservable) {
|
||||
_sources = sources
|
||||
_notificationHandler = notificationHandler
|
||||
}
|
||||
|
||||
override func run<O : ObserverType where O.E == Element>(observer: O, cancel: Disposable, setSink: (Disposable) -> Void) -> Disposable {
|
||||
let sink = RetryWhenSequenceSink<S, O, RetryTriggerType, Error>(parent: self, observer: observer, cancel: cancel)
|
||||
setSink(sink)
|
||||
return sink.run(self.sources.generate())
|
||||
override func run<O : ObserverType where O.E == Element>(observer: O) -> Disposable {
|
||||
let sink = RetryWhenSequenceSink<S, O, TriggerObservable, Error>(parent: self, observer: observer)
|
||||
sink.disposable = sink.run(self._sources.generate())
|
||||
return sink
|
||||
}
|
||||
}
|
||||
|
|
@ -11,7 +11,7 @@ import Foundation
|
|||
class Sink<O : ObserverType> : SingleAssignmentDisposable {
|
||||
private let _observer: O
|
||||
|
||||
func forwardOn(event: Event<O.E>) {
|
||||
final func forwardOn(event: Event<O.E>) {
|
||||
if disposed {
|
||||
return
|
||||
}
|
||||
|
|
|
|||
|
|
@ -157,7 +157,21 @@ extension ObservableType {
|
|||
- parameter notificationHandler: A handler that is passed an observable sequence of errors raised by the source observable and returns and observable that either continues, completes or errors. This behavior is then applied to the source observable.
|
||||
- returns: An observable sequence producing the elements of the given sequence repeatedly until it terminates successfully or is notified to error or complete.
|
||||
*/
|
||||
public func retryWhen<U, Error: ErrorType>(notificationHandler: Observable<Error> -> Observable<U>)
|
||||
@warn_unused_result(message="http://git.io/rxs.uo")
|
||||
public func retryWhen<TriggerObservable: ObservableType, Error: ErrorType>(notificationHandler: Observable<Error> -> TriggerObservable)
|
||||
-> Observable<E> {
|
||||
return RetryWhenSequence(sources: InfiniteSequence(repeatedValue: self.asObservable()), notificationHandler: notificationHandler)
|
||||
}
|
||||
|
||||
/**
|
||||
Repeats the source observable sequence on error when the notifier emits a next value.
|
||||
If the source observable errors and the notifier completes, it will complete the source sequence.
|
||||
|
||||
- parameter notificationHandler: A handler that is passed an observable sequence of errors raised by the source observable and returns and observable that either continues, completes or errors. This behavior is then applied to the source observable.
|
||||
- returns: An observable sequence producing the elements of the given sequence repeatedly until it terminates successfully or is notified to error or complete.
|
||||
*/
|
||||
@warn_unused_result(message="http://git.io/rxs.uo")
|
||||
public func retryWhen<TriggerObservable: ObservableType>(notificationHandler: Observable<ErrorType> -> TriggerObservable)
|
||||
-> Observable<E> {
|
||||
return RetryWhenSequence(sources: InfiniteSequence(repeatedValue: self.asObservable()), notificationHandler: notificationHandler)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -8,8 +8,16 @@
|
|||
|
||||
import Foundation
|
||||
|
||||
enum TailRecursiveSinkCommand {
|
||||
case MoveNext
|
||||
case Dispose
|
||||
}
|
||||
|
||||
/// This class is usually used with `Generator` version of the operators.
|
||||
class TailRecursiveSink<S: SequenceType, O: ObserverType where S.Generator.Element: ObservableConvertibleType, S.Generator.Element.E == O.E> : Sink<O>, ObserverType {
|
||||
class TailRecursiveSink<S: SequenceType, O: ObserverType where S.Generator.Element: ObservableConvertibleType, S.Generator.Element.E == O.E>
|
||||
: Sink<O>
|
||||
, InvocableWithValueType {
|
||||
typealias Value = TailRecursiveSinkCommand
|
||||
typealias E = O.E
|
||||
|
||||
var _generators:[S.Generator] = []
|
||||
|
|
@ -17,7 +25,7 @@ class TailRecursiveSink<S: SequenceType, O: ObserverType where S.Generator.Eleme
|
|||
var _subscription = SerialDisposable()
|
||||
|
||||
// this is thread safe object
|
||||
var _gate = AsyncLock()
|
||||
var _gate = AsyncLock<InvocableScheduledItem<TailRecursiveSink<S, O>>>()
|
||||
|
||||
override init(observer: O) {
|
||||
super.init(observer: observer)
|
||||
|
|
@ -25,27 +33,24 @@ class TailRecursiveSink<S: SequenceType, O: ObserverType where S.Generator.Eleme
|
|||
|
||||
func run(sources: S.Generator) -> Disposable {
|
||||
_generators.append(sources)
|
||||
|
||||
schedule(.MoveNext)
|
||||
|
||||
scheduleMoveNext()
|
||||
|
||||
let disposeSinkStack = AnonymousDisposable {
|
||||
self.schedule {
|
||||
self.disposePrivate()
|
||||
}
|
||||
}
|
||||
|
||||
return StableCompositeDisposable.create(_subscription, disposeSinkStack)
|
||||
return _subscription
|
||||
}
|
||||
|
||||
func scheduleMoveNext() {
|
||||
return schedule {
|
||||
self.moveNext()
|
||||
|
||||
func invoke(command: TailRecursiveSinkCommand) {
|
||||
switch command {
|
||||
case .Dispose:
|
||||
disposeCommand()
|
||||
case .MoveNext:
|
||||
moveNextCommand()
|
||||
}
|
||||
}
|
||||
|
||||
// simple implementation for now
|
||||
func schedule(action: () -> Void) {
|
||||
_gate.wait(action)
|
||||
func schedule(command: TailRecursiveSinkCommand) {
|
||||
_gate.invoke(InvocableScheduledItem(invocable: self, state: command))
|
||||
}
|
||||
|
||||
func done() {
|
||||
|
|
@ -57,13 +62,9 @@ class TailRecursiveSink<S: SequenceType, O: ObserverType where S.Generator.Eleme
|
|||
abstractMethod()
|
||||
}
|
||||
|
||||
func on(event: Event<E>) {
|
||||
abstractMethod()
|
||||
}
|
||||
|
||||
// should be done on gate locked
|
||||
|
||||
private func moveNext() {
|
||||
private func moveNextCommand() {
|
||||
var next: Observable<E>? = nil
|
||||
|
||||
repeat {
|
||||
|
|
@ -101,13 +102,24 @@ class TailRecursiveSink<S: SequenceType, O: ObserverType where S.Generator.Eleme
|
|||
return
|
||||
}
|
||||
|
||||
let subscription2 = next!.subscribe(self)
|
||||
let subscription2 = subscribeToNext(next!)
|
||||
_subscription.disposable = subscription2
|
||||
}
|
||||
|
||||
private func disposePrivate() {
|
||||
|
||||
func subscribeToNext(source: Observable<E>) -> Disposable {
|
||||
abstractMethod()
|
||||
}
|
||||
|
||||
func disposeCommand() {
|
||||
_disposed = true
|
||||
_generators.removeAll(keepCapacity: false)
|
||||
}
|
||||
|
||||
|
||||
override func dispose() {
|
||||
super.dispose()
|
||||
|
||||
_subscription.dispose()
|
||||
|
||||
schedule(.Dispose)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,21 @@
|
|||
//
|
||||
// AnonymousInvocable.swift
|
||||
// Rx
|
||||
//
|
||||
// Created by Krunoslav Zaher on 11/7/15.
|
||||
// Copyright © 2015 Krunoslav Zaher. All rights reserved.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
|
||||
struct AnonymousInvocable : InvocableType {
|
||||
private let _action: () -> ()
|
||||
|
||||
init(_ action: () -> ()) {
|
||||
_action = action
|
||||
}
|
||||
|
||||
func invoke() {
|
||||
_action()
|
||||
}
|
||||
}
|
||||
|
|
@ -136,7 +136,7 @@ public class CurrentThreadScheduler : ImmediateSchedulerType {
|
|||
CurrentThreadScheduler.queue = queue
|
||||
}
|
||||
|
||||
let scheduledItem = ScheduledItem(action: action, state: state, time: 0)
|
||||
let scheduledItem = ScheduledItem(action: action, state: state)
|
||||
queue.value.enqueue(scheduledItem)
|
||||
return scheduledItem
|
||||
}
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ Represents an object that schedules units of work to run immediately on the curr
|
|||
*/
|
||||
private class ImmediateScheduler : ImmediateSchedulerType {
|
||||
|
||||
private let _asyncLock = AsyncLock()
|
||||
private let _asyncLock = AsyncLock<AnonymousInvocable>()
|
||||
|
||||
/**
|
||||
Schedules an action to be executed immediatelly.
|
||||
|
|
@ -27,12 +27,12 @@ private class ImmediateScheduler : ImmediateSchedulerType {
|
|||
*/
|
||||
func schedule<StateType>(state: StateType, action: (StateType) -> Disposable) -> Disposable {
|
||||
let disposable = SingleAssignmentDisposable()
|
||||
_asyncLock.wait {
|
||||
_asyncLock.invoke(AnonymousInvocable {
|
||||
if disposable.disposed {
|
||||
return
|
||||
}
|
||||
disposable.disposable = action(state)
|
||||
}
|
||||
})
|
||||
|
||||
return disposable
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,24 @@
|
|||
//
|
||||
// InvocableScheduledItem.swift
|
||||
// Rx
|
||||
//
|
||||
// Created by Krunoslav Zaher on 11/7/15.
|
||||
// Copyright © 2015 Krunoslav Zaher. All rights reserved.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
|
||||
struct InvocableScheduledItem<I: InvocableWithValueType> : InvocableType {
|
||||
|
||||
let _invocable: I
|
||||
let _state: I.Value
|
||||
|
||||
init(invocable: I, state: I.Value) {
|
||||
_invocable = invocable
|
||||
_state = state
|
||||
}
|
||||
|
||||
func invoke() {
|
||||
_invocable.invoke(_state)
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,19 @@
|
|||
//
|
||||
// InvocableType.swift
|
||||
// Rx
|
||||
//
|
||||
// Created by Krunoslav Zaher on 11/7/15.
|
||||
// Copyright © 2015 Krunoslav Zaher. All rights reserved.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
|
||||
protocol InvocableType {
|
||||
func invoke()
|
||||
}
|
||||
|
||||
protocol InvocableWithValueType {
|
||||
typealias Value
|
||||
|
||||
func invoke(value: Value)
|
||||
}
|
||||
|
|
@ -8,40 +8,32 @@
|
|||
|
||||
import Foundation
|
||||
|
||||
protocol ScheduledItemType : Cancelable {
|
||||
var time: Int {
|
||||
get
|
||||
}
|
||||
|
||||
func invoke()
|
||||
}
|
||||
|
||||
class ScheduledItem<T> : ScheduledItemType {
|
||||
struct ScheduledItem<T>
|
||||
: ScheduledItemType
|
||||
, InvocableType {
|
||||
typealias Action = T -> Disposable
|
||||
|
||||
let action: Action
|
||||
let state: T
|
||||
let time: Int
|
||||
|
||||
private let _action: Action
|
||||
private let _state: T
|
||||
|
||||
private let _disposable = SingleAssignmentDisposable()
|
||||
|
||||
var disposed: Bool {
|
||||
get {
|
||||
return disposable.disposed
|
||||
return _disposable.disposed
|
||||
}
|
||||
}
|
||||
|
||||
var disposable = SingleAssignmentDisposable()
|
||||
|
||||
init(action: Action, state: T, time: Int) {
|
||||
self.action = action
|
||||
self.state = state
|
||||
self.time = time
|
||||
init(action: Action, state: T) {
|
||||
_action = action
|
||||
_state = state
|
||||
}
|
||||
|
||||
func invoke() {
|
||||
self.disposable.disposable = action(state)
|
||||
_disposable.disposable = _action(_state)
|
||||
}
|
||||
|
||||
func dispose() {
|
||||
self.disposable.dispose()
|
||||
_disposable.dispose()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,15 @@
|
|||
//
|
||||
// ScheduledItemType.swift
|
||||
// Rx
|
||||
//
|
||||
// Created by Krunoslav Zaher on 11/7/15.
|
||||
// Copyright © 2015 Krunoslav Zaher. All rights reserved.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
|
||||
protocol ScheduledItemType
|
||||
: Cancelable
|
||||
, InvocableType {
|
||||
func invoke()
|
||||
}
|
||||
|
|
@ -18,36 +18,29 @@ class ColdObservable<Element: Equatable> : ObservableType, ObservableConvertible
|
|||
|
||||
var subscriptions: [Subscription]
|
||||
var recordedEvents: [Events]
|
||||
var observers: Bag<Observer>
|
||||
|
||||
init(testScheduler: TestScheduler, recordedEvents: [Events]) {
|
||||
self.testScheduler = testScheduler
|
||||
|
||||
self.recordedEvents = recordedEvents
|
||||
self.subscriptions = []
|
||||
self.observers = Bag()
|
||||
}
|
||||
|
||||
func subscribe<O : ObserverType where O.E == E>(observer: O) -> Disposable {
|
||||
let key = observers.insert(AnyObserver(observer))
|
||||
subscriptions.append(Subscription(self.testScheduler.now))
|
||||
|
||||
let i = self.subscriptions.count - 1
|
||||
|
||||
for recordedEvent in recordedEvents {
|
||||
testScheduler.scheduleRelative((), dueTime: recordedEvent.time, action: { (Int) in
|
||||
self.observers.forEach { $0.on(recordedEvent.event) }
|
||||
testScheduler.scheduleRelative((), dueTime: recordedEvent.time, action: { (_) in
|
||||
observer.on(recordedEvent.event)
|
||||
return NopDisposable.instance
|
||||
})
|
||||
}
|
||||
|
||||
return AnonymousDisposable {
|
||||
let removed = self.observers.removeKey(key)
|
||||
assert(removed != nil);
|
||||
|
||||
let existing = self.subscriptions[i]
|
||||
self.subscriptions[i] = Subscription(existing.subscribe, self.testScheduler.now)
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -766,8 +766,39 @@ extension ObservableSingleTest {
|
|||
Subscription(200, 450),
|
||||
])
|
||||
}
|
||||
|
||||
|
||||
|
||||
func testRetry_tailRecursiveOptimizationsTest() {
|
||||
var count = 1
|
||||
let sequenceSendingImmediateError: Observable<Int> = create { observer in
|
||||
observer.on(.Next(0))
|
||||
observer.on(.Next(1))
|
||||
observer.on(.Next(2))
|
||||
if count < 2 {
|
||||
observer.on(.Error(testError))
|
||||
count++
|
||||
}
|
||||
observer.on(.Next(3))
|
||||
observer.on(.Next(4))
|
||||
observer.on(.Next(5))
|
||||
observer.on(.Completed)
|
||||
|
||||
return NopDisposable.instance
|
||||
}
|
||||
|
||||
_ = sequenceSendingImmediateError
|
||||
.retry()
|
||||
.subscribe { _ in
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct CustomErrorType : ErrorType {
|
||||
|
||||
}
|
||||
|
||||
// retryWhen
|
||||
extension ObservableSingleTest {
|
||||
|
||||
func testRetryWhen_Never() {
|
||||
|
||||
let scheduler = TestScheduler(initialClock: 0)
|
||||
|
|
@ -783,9 +814,9 @@ extension ObservableSingleTest {
|
|||
])
|
||||
|
||||
let res = scheduler.start(300) {
|
||||
xs.retryWhen({ (errors: Observable<NSError>) in
|
||||
return empty.asObservable()
|
||||
})
|
||||
xs.retryWhen { (errors: Observable<NSError>) in
|
||||
return empty
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
|
|
@ -817,9 +848,9 @@ extension ObservableSingleTest {
|
|||
])
|
||||
|
||||
let res = scheduler.start() {
|
||||
xs.retryWhen({ (errors: Observable<NSError>) in
|
||||
return never.asObservable()
|
||||
})
|
||||
xs.retryWhen { (errors: Observable<NSError>) in
|
||||
return never
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
|
|
@ -832,7 +863,7 @@ extension ObservableSingleTest {
|
|||
XCTAssertEqual(res.messages, correct)
|
||||
|
||||
XCTAssertEqual(xs.subscriptions, [
|
||||
Subscription(200, 1000)
|
||||
Subscription(200, 250)
|
||||
])
|
||||
}
|
||||
|
||||
|
|
@ -854,9 +885,9 @@ extension ObservableSingleTest {
|
|||
])
|
||||
|
||||
let res = scheduler.start() {
|
||||
xs.retryWhen({ (errors: Observable<NSError>) in
|
||||
return never.asObservable()
|
||||
})
|
||||
xs.retryWhen { (errors: Observable<NSError>) in
|
||||
return never
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
|
|
@ -891,9 +922,9 @@ extension ObservableSingleTest {
|
|||
])
|
||||
|
||||
let res = scheduler.start() {
|
||||
xs.retryWhen({ (errors: Observable<NSError>) in
|
||||
return empty.asObservable()
|
||||
})
|
||||
xs.retryWhen { (errors: Observable<NSError>) in
|
||||
return empty
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
|
|
@ -923,14 +954,14 @@ extension ObservableSingleTest {
|
|||
])
|
||||
|
||||
let res = scheduler.start(300) {
|
||||
xs.retryWhen({ (errors: Observable<NSError>) in
|
||||
xs.retryWhen { (errors: Observable<NSError>) in
|
||||
return errors.scan(0) { (var a, e) in
|
||||
if ++a == 2 {
|
||||
throw testError
|
||||
throw testError1
|
||||
}
|
||||
return a
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
|
|
@ -938,7 +969,7 @@ extension ObservableSingleTest {
|
|||
next(220, 2),
|
||||
next(240, 1),
|
||||
next(250, 2),
|
||||
error(260, testError)
|
||||
error(260, testError1)
|
||||
]
|
||||
|
||||
XCTAssertEqual(res.messages, correct)
|
||||
|
|
@ -997,13 +1028,13 @@ extension ObservableSingleTest {
|
|||
])
|
||||
|
||||
let res = scheduler.start(300) {
|
||||
xs.retryWhen({ (errors: Observable<NSError>) in
|
||||
xs.retryWhen { (errors: Observable<NSError>) in
|
||||
return errors.scan(0) { (a, e) in
|
||||
return a + 1
|
||||
}.takeWhile { (num: Int) -> Bool in
|
||||
return num < 2
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
|
|
@ -1038,9 +1069,9 @@ extension ObservableSingleTest {
|
|||
])
|
||||
|
||||
let res = scheduler.start() {
|
||||
xs.retryWhen({ (errors: Observable<NSError>) in
|
||||
return never.asObservable()
|
||||
})
|
||||
xs.retryWhen { (errors: Observable<NSError>) in
|
||||
return never
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
|
|
@ -1051,11 +1082,11 @@ extension ObservableSingleTest {
|
|||
XCTAssertEqual(res.messages, correct)
|
||||
|
||||
XCTAssertEqual(xs.subscriptions, [
|
||||
Subscription(200, 1000)
|
||||
Subscription(200, 230)
|
||||
])
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
func testRetryWhen_Incremental_BackOff() {
|
||||
|
||||
let scheduler = TestScheduler(initialClock: 0)
|
||||
|
|
@ -1067,35 +1098,91 @@ extension ObservableSingleTest {
|
|||
])
|
||||
|
||||
let res = scheduler.start(800) {
|
||||
xs.retryWhen({ (errors: Observable<NSError>) in
|
||||
return scheduler.createColdObservable([
|
||||
next(50, 1), // delay 50
|
||||
next(150, 2), // delay 100
|
||||
next(300, 3), // delay 150
|
||||
completed(500) // delay 200
|
||||
])
|
||||
})
|
||||
xs.retryWhen { (errors: Observable<NSError>) in
|
||||
errors.scan((0, nil)) { (a: (Int, NSError!), e) in
|
||||
(a.0 + 1, e)
|
||||
}
|
||||
.flatMap { (a, e) -> Observable<Int64> in
|
||||
if a >= 4 {
|
||||
return failWith(e)
|
||||
}
|
||||
|
||||
return timer(a * 50, scheduler)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
next(205, 1),
|
||||
next(265, 1),
|
||||
next(365, 1),
|
||||
next(515, 1),
|
||||
completed(710)
|
||||
next(375, 1),
|
||||
next(535, 1),
|
||||
error(540, testError)
|
||||
]
|
||||
|
||||
XCTAssertEqual(res.messages, correct)
|
||||
|
||||
XCTAssertEqual(xs.subscriptions, [
|
||||
Subscription(200, 260),
|
||||
Subscription(260, 360),
|
||||
Subscription(360, 510),
|
||||
Subscription(510, 710)
|
||||
Subscription(200, 210),
|
||||
Subscription(260, 270),
|
||||
Subscription(370, 380),
|
||||
Subscription(530, 540)
|
||||
])
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
func testRetryWhen_IgnoresDifferentErrorTypes() {
|
||||
|
||||
let scheduler = TestScheduler(initialClock: 0)
|
||||
|
||||
// just fails
|
||||
let xs = scheduler.createColdObservable([
|
||||
next(5, 1),
|
||||
error(10, testError)
|
||||
])
|
||||
|
||||
let res = scheduler.start(800) {
|
||||
xs.retryWhen { (errors: Observable<CustomErrorType>) in
|
||||
errors
|
||||
}
|
||||
}
|
||||
|
||||
let correct: [Recorded<Int>] = [
|
||||
next(205, 1),
|
||||
error(210, testError)
|
||||
]
|
||||
|
||||
XCTAssertEqual(res.messages, correct)
|
||||
|
||||
XCTAssertEqual(xs.subscriptions, [
|
||||
Subscription(200, 210)
|
||||
])
|
||||
}
|
||||
|
||||
func testRetryWhen_tailRecursiveOptimizationsTest() {
|
||||
var count = 1
|
||||
let sequenceSendingImmediateError: Observable<Int> = create { observer in
|
||||
observer.on(.Next(0))
|
||||
observer.on(.Next(1))
|
||||
observer.on(.Next(2))
|
||||
if count < 2 {
|
||||
observer.on(.Error(testError))
|
||||
count++
|
||||
}
|
||||
observer.on(.Next(3))
|
||||
observer.on(.Next(4))
|
||||
observer.on(.Next(5))
|
||||
observer.on(.Completed)
|
||||
|
||||
return NopDisposable.instance
|
||||
}
|
||||
|
||||
_ = sequenceSendingImmediateError
|
||||
.retryWhen { errors in
|
||||
return errors
|
||||
}
|
||||
.subscribe { _ in
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue