Explorar el Código

[RN] Refactor "Keep track of ongoing network requests" and "Show a progress indicator in the BlankPage"

I'm not saying that the two commits in question were wrong or worse than
what I'm offering. Anyway, I think what I'm offering brings:

* Compliance with expectations i.e. the middleware doesn't compute the
next state from the current state, the reducer does;

* Clarity and/or simplicity i.e. there's no global variable (reqIndex),
there's no need for the term "index" (a.k.a "reqIndex") in the redux
store.

* By renaming net-interceptor to network-activity feels like it's
preparing the feature to implement a NetworkActivityIndicator React
Component which will take on more of the knowledge about the specifics
of what is the network activity redux state exactly, is it maintained by
interception or some other mechanism, and abstracts it in the feature
itself allowing outsiders to merely render a React Component.
j8
Lyubo Marinov hace 7 años
padre
commit
7f8e8177d0

+ 1
- 1
react/features/app/components/App.native.js Ver fichero

@@ -8,7 +8,7 @@ import '../../mobile/audio-mode';
8 8
 import '../../mobile/background';
9 9
 import '../../mobile/external-api';
10 10
 import '../../mobile/full-screen';
11
-import '../../mobile/net-interceptor';
11
+import '../../mobile/network-activity';
12 12
 import '../../mobile/permissions';
13 13
 import '../../mobile/proximity';
14 14
 import '../../mobile/wake-lock';

+ 0
- 11
react/features/mobile/net-interceptor/actionTypes.js Ver fichero

@@ -1,11 +0,0 @@
1
-/**
2
- * The type of redux action to update the pending network requests mapping.
3
- *
4
- * {
5
- *     type: UPDATE_NETWORK_REQUESTS,
6
- *     requests: Object
7
- * }
8
- *
9
- * @protected
10
- */
11
-export const UPDATE_NETWORK_REQUESTS = Symbol('UPDATE_NETWORK_REQUESTS');

+ 0
- 75
react/features/mobile/net-interceptor/functions.js Ver fichero

@@ -1,75 +0,0 @@
1
-import _ from 'lodash';
2
-import XHRInterceptor from 'react-native/Libraries/Network/XHRInterceptor';
3
-
4
-import { UPDATE_NETWORK_REQUESTS } from './actionTypes';
5
-
6
-/**
7
- * Global index for keeping track of XHR requests.
8
- * @type {number}
9
- */
10
-let reqIndex = 0;
11
-
12
-/**
13
- * Starts intercepting network requests. Only XHR requests are supported at the
14
- * moment.
15
- *
16
- * Ongoing request information is kept in redux, and it's removed as soon as a
17
- * given request is complete.
18
- *
19
- * @param {Object} store - The redux store.
20
- * @returns {void}
21
- */
22
-export function startNetInterception({ dispatch, getState }) {
23
-    XHRInterceptor.setOpenCallback((method, url, xhr) => {
24
-        xhr._reqIndex = reqIndex++;
25
-
26
-        const requests = getState()['features/net-interceptor'].requests || {};
27
-        const newRequests = _.cloneDeep(requests);
28
-        const request = {
29
-            method,
30
-            url
31
-        };
32
-
33
-        newRequests[xhr._reqIndex] = request;
34
-
35
-        dispatch({
36
-            type: UPDATE_NETWORK_REQUESTS,
37
-            requests: newRequests
38
-        });
39
-    });
40
-
41
-    XHRInterceptor.setResponseCallback((...args) => {
42
-        const xhr = args.slice(-1)[0];
43
-
44
-        if (typeof xhr._reqIndex === 'undefined') {
45
-            return;
46
-        }
47
-
48
-        const requests = getState()['features/net-interceptor'].requests || {};
49
-        const newRequests = _.cloneDeep(requests);
50
-
51
-        delete newRequests[xhr._reqIndex];
52
-
53
-        dispatch({
54
-            type: UPDATE_NETWORK_REQUESTS,
55
-            requests: newRequests
56
-        });
57
-    });
58
-
59
-    XHRInterceptor.enableInterception();
60
-}
61
-
62
-/**
63
- * Stops intercepting network requests.
64
- *
65
- * @param {Object} store - The redux store.
66
- * @returns {void}
67
- */
68
-export function stopNetInterception({ dispatch }) {
69
-    XHRInterceptor.disableInterception();
70
-
71
-    dispatch({
72
-        type: UPDATE_NETWORK_REQUESTS,
73
-        requests: {}
74
-    });
75
-}

+ 0
- 25
react/features/mobile/net-interceptor/middleware.js Ver fichero

@@ -1,25 +0,0 @@
1
-import { APP_WILL_MOUNT, APP_WILL_UNMOUNT } from '../../app';
2
-import { MiddlewareRegistry } from '../../base/redux';
3
-
4
-import { startNetInterception, stopNetInterception } from './functions';
5
-
6
-/**
7
- * Middleware which captures app startup and conference actions in order to
8
- * clear the image cache.
9
- *
10
- * @returns {Function}
11
- */
12
-MiddlewareRegistry.register(store => next => action => {
13
-    const result = next(action);
14
-
15
-    switch (action.type) {
16
-    case APP_WILL_MOUNT:
17
-        startNetInterception(store);
18
-        break;
19
-    case APP_WILL_UNMOUNT:
20
-        stopNetInterception(store);
21
-        break;
22
-    }
23
-
24
-    return result;
25
-});

+ 0
- 15
react/features/mobile/net-interceptor/reducer.js Ver fichero

@@ -1,15 +0,0 @@
1
-import { ReducerRegistry } from '../../base/redux';
2
-
3
-import { UPDATE_NETWORK_REQUESTS } from './actionTypes';
4
-
5
-ReducerRegistry.register('features/net-interceptor', (state = {}, action) => {
6
-    switch (action.type) {
7
-    case UPDATE_NETWORK_REQUESTS:
8
-        return {
9
-            ...state,
10
-            requests: action.requests
11
-        };
12
-    }
13
-
14
-    return state;
15
-});

+ 37
- 0
react/features/mobile/network-activity/actionTypes.js Ver fichero

@@ -0,0 +1,37 @@
1
+/**
2
+ * The type of redux action to add a network request to the redux store/state.
3
+ *
4
+ * {
5
+ *     type: _ADD_NETWORK_REQUEST,
6
+ *     request: Object
7
+ * }
8
+ *
9
+ * @protected
10
+ */
11
+export const _ADD_NETWORK_REQUEST = Symbol('_ADD_NETWORK_REQUEST');
12
+
13
+/**
14
+ * The type of redux action to remove all network requests from the redux
15
+ * store/state.
16
+ *
17
+ * {
18
+ *     type: _REMOVE_ALL_NETWORK_REQUESTS,
19
+ * }
20
+ *
21
+ * @protected
22
+ */
23
+export const _REMOVE_ALL_NETWORK_REQUESTS
24
+    = Symbol('_REMOVE_ALL_NETWORK_REQUESTS');
25
+
26
+/**
27
+ * The type of redux action to remove a network request from the redux
28
+ * store/state.
29
+ *
30
+ * {
31
+ *     type: _REMOVE_NETWORK_REQUEST,
32
+ *     request: Object
33
+ * }
34
+ *
35
+ * @protected
36
+ */
37
+export const _REMOVE_NETWORK_REQUEST = Symbol('_REMOVE_NETWORK_REQUEST');

react/features/mobile/net-interceptor/index.js → react/features/mobile/network-activity/index.js Ver fichero


+ 81
- 0
react/features/mobile/network-activity/middleware.js Ver fichero

@@ -0,0 +1,81 @@
1
+/* @flow */
2
+
3
+import XHRInterceptor from 'react-native/Libraries/Network/XHRInterceptor';
4
+
5
+import { APP_WILL_MOUNT, APP_WILL_UNMOUNT } from '../../app';
6
+import { MiddlewareRegistry } from '../../base/redux';
7
+
8
+import {
9
+    _ADD_NETWORK_REQUEST,
10
+    _REMOVE_ALL_NETWORK_REQUESTS,
11
+    _REMOVE_NETWORK_REQUEST
12
+} from './actionTypes';
13
+
14
+/**
15
+ * Middleware which captures app startup and conference actions in order to
16
+ * clear the image cache.
17
+ *
18
+ * @returns {Function}
19
+ */
20
+MiddlewareRegistry.register(store => next => action => {
21
+    const result = next(action);
22
+
23
+    switch (action.type) {
24
+    case APP_WILL_MOUNT:
25
+        _startNetInterception(store);
26
+        break;
27
+
28
+    case APP_WILL_UNMOUNT:
29
+        _stopNetInterception(store);
30
+        break;
31
+    }
32
+
33
+    return result;
34
+});
35
+
36
+/**
37
+ * Starts intercepting network requests. Only XHR requests are supported at the
38
+ * moment.
39
+ *
40
+ * Ongoing request information is kept in redux, and it's removed as soon as a
41
+ * given request is complete.
42
+ *
43
+ * @param {Object} store - The redux store.
44
+ * @private
45
+ * @returns {void}
46
+ */
47
+function _startNetInterception({ dispatch }) {
48
+    XHRInterceptor.setOpenCallback((method, url, xhr) => dispatch({
49
+        type: _ADD_NETWORK_REQUEST,
50
+        request: xhr,
51
+
52
+        // The following are not really necessary read anywhere at the time of
53
+        // this writing but are provided anyway if the reducer chooses to
54
+        // remember them:
55
+        method,
56
+        url
57
+    }));
58
+    XHRInterceptor.setResponseCallback((...args) => dispatch({
59
+        type: _REMOVE_NETWORK_REQUEST,
60
+
61
+        // XXX The XHR is the last argument of the responseCallback.
62
+        request: args[args.length - 1]
63
+    }));
64
+
65
+    XHRInterceptor.enableInterception();
66
+}
67
+
68
+/**
69
+ * Stops intercepting network requests.
70
+ *
71
+ * @param {Object} store - The redux store.
72
+ * @private
73
+ * @returns {void}
74
+ */
75
+function _stopNetInterception({ dispatch }) {
76
+    XHRInterceptor.disableInterception();
77
+
78
+    dispatch({
79
+        type: _REMOVE_ALL_NETWORK_REQUESTS
80
+    });
81
+}

+ 60
- 0
react/features/mobile/network-activity/reducer.js Ver fichero

@@ -0,0 +1,60 @@
1
+/* @flow */
2
+
3
+import { ReducerRegistry, set } from '../../base/redux';
4
+
5
+import {
6
+    _ADD_NETWORK_REQUEST,
7
+    _REMOVE_ALL_NETWORK_REQUESTS,
8
+    _REMOVE_NETWORK_REQUEST
9
+} from './actionTypes';
10
+
11
+/**
12
+ * The initial redux state of the feature network-activity.
13
+ *
14
+ * @type {{
15
+ *     requests: Map
16
+ * }}
17
+ */
18
+const _INITIAL_STATE = {
19
+    /**
20
+     * The ongoing network requests i.e. the network request which have been
21
+     * added to the redux store/state and have not been removed.
22
+     *
23
+     * @type {Map}
24
+     */
25
+    requests: new Map()
26
+};
27
+
28
+ReducerRegistry.register(
29
+    'features/network-activity',
30
+    (state = _INITIAL_STATE, action) => {
31
+        switch (action.type) {
32
+        case _ADD_NETWORK_REQUEST: {
33
+            const {
34
+                type, // eslint-disable-line no-unused-vars
35
+
36
+                request: key,
37
+                ...value
38
+            } = action;
39
+            const requests = new Map(state.requests);
40
+
41
+            requests.set(key, value);
42
+
43
+            return set(state, 'requests', requests);
44
+        }
45
+
46
+        case _REMOVE_ALL_NETWORK_REQUESTS:
47
+            return set(state, 'requests', _INITIAL_STATE.requests);
48
+
49
+        case _REMOVE_NETWORK_REQUEST: {
50
+            const { request: key } = action;
51
+            const requests = new Map(state.requests);
52
+
53
+            requests.delete(key);
54
+
55
+            return set(state, 'requests', requests);
56
+        }
57
+        }
58
+
59
+        return state;
60
+    });

+ 5
- 2
react/features/welcome/components/BlankPage.native.js Ver fichero

@@ -1,3 +1,5 @@
1
+/* @flow */
2
+
1 3
 import PropTypes from 'prop-types';
2 4
 import React from 'react';
3 5
 import { ActivityIndicator, View } from 'react-native';
@@ -61,10 +63,11 @@ class BlankPage extends AbstractBlankPage {
61 63
  * }}
62 64
  */
63 65
 function _mapStateToProps(state) {
64
-    const { requests } = state['features/net-interceptor'];
66
+    const { requests } = state['features/network-activity'];
65 67
 
66 68
     return {
67
-        _networkActivity: Boolean(requests && Object.keys(requests).length)
69
+        _networkActivity:
70
+            Boolean(requests && (requests.length || requests.size))
68 71
     };
69 72
 }
70 73
 

Loading…
Cancelar
Guardar