12
12
#import " DoraemonNetworkInterceptor.h"
13
13
#import " UIViewController+Doraemon.h"
14
14
#import " DoraemonHealthManager.h"
15
+ #import < objc/runtime.h>
15
16
16
- @interface DoraemonNetFlowManager () <DoraemonNetworkInterceptorDelegate, NSStreamDelegate >
17
-
18
- @property (nonatomic , copy ) HttpBodyCallBack bodyCallBack;
19
- @property (nonatomic , strong ) NSMutableData *bodyData;
17
+ @interface NSInputStream (DoraemonHttpBodyCallBack)
20
18
19
+ @property (nonatomic , strong ) id <NSStreamDelegate > dkStrongDelegate;
21
20
@end
22
21
23
- @implementation DoraemonNetFlowManager
22
+ @implementation NSInputStream (DoraemonHttpBodyCallBack)
24
23
25
- + (DoraemonNetFlowManager *)shareInstance {
26
- static dispatch_once_t once;
27
- static DoraemonNetFlowManager *instance;
28
- dispatch_once (&once, ^{
29
- instance = [[DoraemonNetFlowManager alloc ] init ];
30
- });
31
- return instance;
24
+ - (void )setDkStrongDelegate : (id <NSStreamDelegate >)dkStrongDelegate {
25
+ objc_setAssociatedObject (self, @selector (dkStrongDelegate ), dkStrongDelegate, OBJC_ASSOCIATION_RETAIN_NONATOMIC );
32
26
}
33
27
34
- - (void )canInterceptNetFlow : (BOOL )enable {
35
- _canIntercept = enable;
36
- if (enable) {
37
- [[DoraemonNetworkInterceptor shareInstance ] addDelegate: self ];
38
- _startInterceptDate = [NSDate date ];
39
- }else {
40
- [DoraemonNetworkInterceptor.shareInstance removeDelegate: self ];
41
- _startInterceptDate = nil ;
42
- [[DoraemonNetFlowDataSource shareInstance ] clear ];
43
- }
28
+ - (id <NSStreamDelegate >)dkStrongDelegate {
29
+ return objc_getAssociatedObject (self, _cmd);
44
30
}
31
+ @end
45
32
46
- - (void )httpBodyFromRequest : (NSURLRequest *)request bodyCallBack : (HttpBodyCallBack)complete {
47
- NSData *httpBody = nil ;
48
- if (request.HTTPBody ) {
49
- httpBody = request.HTTPBody ;
50
- complete (httpBody);
51
- return ;
52
- }
53
- if ([request.HTTPMethod isEqualToString: @" POST" ]) {
54
- NSInputStream *stream = request.HTTPBodyStream ;
55
- [stream setDelegate: self ];
56
- self.bodyCallBack = complete;
57
- [stream scheduleInRunLoop: [NSRunLoop currentRunLoop ] forMode: NSDefaultRunLoopMode ];
58
- [stream open ];
59
- } else {
60
- complete (httpBody);
33
+ @interface DoraemonInputStreamDelegate : NSObject <NSStreamDelegate >
34
+
35
+ @property (nonatomic , strong ) NSMutableData *bodyData;
36
+ @property (nonatomic , copy ) HttpBodyCallBack bodyCallBack;
37
+ @end
38
+
39
+ @implementation DoraemonInputStreamDelegate
40
+ - (instancetype )initWithCallback : (HttpBodyCallBack)callback inputStream : (NSInputStream *)inputStream {
41
+ self = [super init ];
42
+ if (self){
43
+ _bodyCallBack = callback;
44
+ inputStream.dkStrongDelegate = self;// keep alive
45
+ inputStream.delegate = self;
61
46
}
47
+ return self;
62
48
}
63
49
64
50
#pragma mark -- NSStreamDelegate
@@ -89,7 +75,6 @@ - (void)stream:(NSStream *)aStream handleEvent:(NSStreamEvent)eventCode {
89
75
{
90
76
[aStream close ];
91
77
[aStream removeFromRunLoop: [NSRunLoop currentRunLoop ] forMode: NSDefaultRunLoopMode ];
92
- aStream = nil ;
93
78
if (self.bodyCallBack ) {
94
79
self.bodyCallBack ([self .bodyData copy ]);
95
80
}
@@ -101,6 +86,60 @@ - (void)stream:(NSStream *)aStream handleEvent:(NSStreamEvent)eventCode {
101
86
}
102
87
}
103
88
89
+
90
+ @end
91
+
92
+
93
+
94
+
95
+ @interface DoraemonNetFlowManager () <DoraemonNetworkInterceptorDelegate>
96
+
97
+
98
+ @property (nonatomic , strong ) NSMapTable *bodyCallBackMap;
99
+
100
+ @end
101
+
102
+ @implementation DoraemonNetFlowManager
103
+
104
+ + (DoraemonNetFlowManager *)shareInstance {
105
+ static dispatch_once_t once;
106
+ static DoraemonNetFlowManager *instance;
107
+ dispatch_once (&once, ^{
108
+ instance = [[DoraemonNetFlowManager alloc ] init ];
109
+ instance.bodyCallBackMap = [NSMapTable mapTableWithKeyOptions: NSPointerFunctionsWeakMemory valueOptions: NSPointerFunctionsStrongMemory];
110
+ });
111
+ return instance;
112
+ }
113
+
114
+ - (void )canInterceptNetFlow : (BOOL )enable {
115
+ _canIntercept = enable;
116
+ if (enable) {
117
+ [[DoraemonNetworkInterceptor shareInstance ] addDelegate: self ];
118
+ _startInterceptDate = [NSDate date ];
119
+ }else {
120
+ [DoraemonNetworkInterceptor.shareInstance removeDelegate: self ];
121
+ _startInterceptDate = nil ;
122
+ [[DoraemonNetFlowDataSource shareInstance ] clear ];
123
+ }
124
+ }
125
+
126
+ - (void )httpBodyFromRequest : (NSURLRequest *)request bodyCallBack : (HttpBodyCallBack)complete {
127
+ NSData *httpBody = nil ;
128
+ if (request.HTTPBody ) {
129
+ httpBody = request.HTTPBody ;
130
+ complete (httpBody);
131
+ return ;
132
+ }
133
+ if ([request.HTTPMethod isEqualToString: @" POST" ]) {
134
+ NSInputStream *stream = request.HTTPBodyStream ;
135
+ DoraemonInputStreamDelegate *delegate = [[DoraemonInputStreamDelegate alloc ] initWithCallback: complete inputStream: stream];
136
+ [stream scheduleInRunLoop: [NSRunLoop currentRunLoop ] forMode: NSDefaultRunLoopMode ];
137
+ [stream open ];
138
+ } else {
139
+ complete (httpBody);
140
+ }
141
+ }
142
+
104
143
#pragma mark -- DoraemonNetworkInterceptorDelegate
105
144
- (void )doraemonNetworkInterceptorDidReceiveData : (NSData *)data response : (NSURLResponse *)response request : (NSURLRequest *)request error : (NSError *)error startTime : (NSTimeInterval )startTime {
106
145
[DoraemonNetFlowHttpModel dealWithResponseData: data response: response request: request complete: ^(DoraemonNetFlowHttpModel *httpModel) {
0 commit comments