Browse Source

Add optional componentId param to bindComponent (#4299)

Timmy Garrabrant 6 years ago
parent
commit
0a6e34f2dd

+ 77
- 1
lib/src/events/ComponentEventsObserver.test.tsx View File

5
 
5
 
6
 describe('ComponentEventsObserver', () => {
6
 describe('ComponentEventsObserver', () => {
7
   const mockEventsReceiver = new NativeEventsReceiver();
7
   const mockEventsReceiver = new NativeEventsReceiver();
8
-  const uut = new ComponentEventsObserver(mockEventsReceiver);
9
   const didAppearFn = jest.fn();
8
   const didAppearFn = jest.fn();
10
   const didDisappearFn = jest.fn();
9
   const didDisappearFn = jest.fn();
11
   const didMountFn = jest.fn();
10
   const didMountFn = jest.fn();
16
   const previewCompletedFn = jest.fn();
15
   const previewCompletedFn = jest.fn();
17
   const modalDismissedFn = jest.fn();
16
   const modalDismissedFn = jest.fn();
18
   let subscription;
17
   let subscription;
18
+  let uut;
19
 
19
 
20
   class SimpleScreen extends React.Component<any, any> {
20
   class SimpleScreen extends React.Component<any, any> {
21
     render() {
21
     render() {
23
     }
23
     }
24
   }
24
   }
25
 
25
 
26
+  class UnboundScreen extends React.Component<any, any> {
27
+    constructor(props) {
28
+      super(props);
29
+    }
30
+
31
+    componentDidMount() {
32
+      didMountFn();
33
+    }
34
+
35
+    componentWillUnmount() {
36
+      willUnmountFn();
37
+    }
38
+
39
+    componentDidAppear() {
40
+      didAppearFn();
41
+    }
42
+
43
+    componentDidDisappear() {
44
+      didDisappearFn();
45
+    }
46
+
47
+    navigationButtonPressed(event) {
48
+      navigationButtonPressedFn(event);
49
+    }
50
+
51
+    modalDismissed(event) {
52
+      modalDismissedFn(event);
53
+    }
54
+
55
+    searchBarUpdated(event) {
56
+      searchBarUpdatedFn(event);
57
+    }
58
+
59
+    searchBarCancelPressed(event) {
60
+      searchBarCancelPressedFn(event);
61
+    }
62
+
63
+    previewCompleted(event) {
64
+      previewCompletedFn(event);
65
+    }
66
+
67
+    render() {
68
+      return 'Hello';
69
+    }
70
+  }
71
+
26
   class BoundScreen extends React.Component<any, any> {
72
   class BoundScreen extends React.Component<any, any> {
27
     constructor(props) {
73
     constructor(props) {
28
       super(props);
74
       super(props);
70
     }
116
     }
71
   }
117
   }
72
 
118
 
119
+  beforeEach(() => {
120
+    jest.clearAllMocks();
121
+    uut = new ComponentEventsObserver(mockEventsReceiver);
122
+  });
123
+
73
   it(`bindComponent expects a component with componentId`, () => {
124
   it(`bindComponent expects a component with componentId`, () => {
74
     const tree = renderer.create(<SimpleScreen />);
125
     const tree = renderer.create(<SimpleScreen />);
75
     expect(() => uut.bindComponent(tree.getInstance() as any)).toThrow('');
126
     expect(() => uut.bindComponent(tree.getInstance() as any)).toThrow('');
77
     expect(() => uut.bindComponent(tree2.getInstance() as any)).toThrow('');
128
     expect(() => uut.bindComponent(tree2.getInstance() as any)).toThrow('');
78
   });
129
   });
79
 
130
 
131
+  it(`bindComponent accepts an optional componentId`, () => {
132
+    const tree = renderer.create(<UnboundScreen />);
133
+    uut.bindComponent(tree.getInstance() as any, 'myCompId')
134
+
135
+    expect(tree.toJSON()).toBeDefined();
136
+    expect(didAppearFn).not.toHaveBeenCalled();
137
+
138
+    uut.notifyComponentDidAppear({ componentId: 'myCompId', componentName: 'doesnt matter' });
139
+    expect(didAppearFn).toHaveBeenCalledTimes(1);
140
+  });
141
+
142
+  it(`bindComponent should use optional componentId if component has a componentId in props`, () => {
143
+    const tree = renderer.create(<UnboundScreen  componentId={'doNotUseThisId'} />);
144
+    uut.bindComponent(tree.getInstance() as any, 'myCompId')
145
+
146
+    expect(tree.toJSON()).toBeDefined();
147
+    
148
+    uut.notifyComponentDidAppear({ componentId: 'dontUseThisId', componentName: 'doesnt matter' });
149
+    expect(didAppearFn).not.toHaveBeenCalled();
150
+    
151
+
152
+    uut.notifyComponentDidAppear({ componentId: 'myCompId', componentName: 'doesnt matter' });
153
+    expect(didAppearFn).toHaveBeenCalledTimes(1);
154
+  });
155
+
80
   it(`bindComponent notifies listeners by componentId on events`, () => {
156
   it(`bindComponent notifies listeners by componentId on events`, () => {
81
     const tree = renderer.create(<BoundScreen componentId={'myCompId'} />);
157
     const tree = renderer.create(<BoundScreen componentId={'myCompId'} />);
82
     expect(tree.toJSON()).toBeDefined();
158
     expect(tree.toJSON()).toBeDefined();

+ 9
- 8
lib/src/events/ComponentEventsObserver.ts View File

38
     this.nativeEventsReceiver.registerPreviewCompletedListener(this.notifyPreviewCompleted);
38
     this.nativeEventsReceiver.registerPreviewCompletedListener(this.notifyPreviewCompleted);
39
   }
39
   }
40
 
40
 
41
-  public bindComponent(component: React.Component<any>): EventSubscription {
42
-    const componentId = component.props.componentId;
43
-    if (!_.isString(componentId)) {
44
-      throw new Error(`bindComponent expects a component with a componentId in props`);
41
+  public bindComponent(component: React.Component<any>, componentId?: string): EventSubscription {
42
+    const computedComponentId = componentId || component.props.componentId;
43
+
44
+    if (!_.isString(computedComponentId)) {
45
+      throw new Error(`bindComponent expects a component with a componentId in props or a componentId as the second argument`);
45
     }
46
     }
46
-    if (_.isNil(this.listeners[componentId])) {
47
-      this.listeners[componentId] = {};
47
+    if (_.isNil(this.listeners[computedComponentId])) {
48
+      this.listeners[computedComponentId] = {};
48
     }
49
     }
49
     const key = _.uniqueId();
50
     const key = _.uniqueId();
50
-    this.listeners[componentId][key] = component;
51
+    this.listeners[computedComponentId][key] = component;
51
 
52
 
52
-    return { remove: () => _.unset(this.listeners[componentId], key) };
53
+    return { remove: () => _.unset(this.listeners[computedComponentId], key) };
53
   }
54
   }
54
 
55
 
55
   public unmounted(componentId: string) {
56
   public unmounted(componentId: string) {

+ 2
- 2
lib/src/events/EventsRegistry.ts View File

60
     return this.commandsObserver.register(callback);
60
     return this.commandsObserver.register(callback);
61
   }
61
   }
62
 
62
 
63
-  public bindComponent(component: React.Component<any>): EventSubscription {
64
-    return this.componentEventsObserver.bindComponent(component);
63
+  public bindComponent(component: React.Component<any>, componentId?: string): EventSubscription {
64
+    return this.componentEventsObserver.bindComponent(component, componentId);
65
   }
65
   }
66
 }
66
 }