@financial-times/n-myft-ui 30.4.3 → 30.4.5

Sign up to get free protection for your applications and to get access to all the features.
@@ -40,7 +40,6 @@ const instantAlertsIconUpdate = ({ event, followPlusInstantAlerts }) => {
40
40
  return;
41
41
  }
42
42
 
43
-
44
43
  const instantAlertsOn = Boolean(currentConcept && currentConcept.rel && currentConcept.rel.properties && currentConcept.rel.properties.instant);
45
44
  toggleInstantAlertsClass({instantAlertsOn, followPlusInstantAlerts });
46
45
  };
@@ -72,5 +71,6 @@ export default () => {
72
71
  followPlusInstantAlerts.addEventListener('click', () => sendModalToggleEvent({followPlusInstantAlerts}));
73
72
 
74
73
  document.body.addEventListener('myft.user.followed.concept.load', (event) => instantAlertsIconLoad({event, followPlusInstantAlerts}));
74
+
75
75
  document.body.addEventListener('myft.user.followed.concept.update', (event) => instantAlertsIconUpdate({event, followPlusInstantAlerts}));
76
76
  };
@@ -45,11 +45,34 @@ const positionModal = ({ event, preferencesModal } = {}) => {
45
45
  }
46
46
  };
47
47
 
48
- const preferenceModalShowAndHide = ({ event, preferencesModal }) => {
48
+ const tracking = (conceptId) => {
49
+ const trackingData = {
50
+ category: 'component',
51
+ action: 'view',
52
+ concept_id: conceptId,
53
+ component: {
54
+ type: 'component',
55
+ name: 'pop-up-box',
56
+ id: '72de123e-5082-11ee-be56-0242ac120002',
57
+ }
58
+ }
59
+
60
+ const trackingEvent = new CustomEvent('oTracking.event', {
61
+ detail: trackingData,
62
+ bubbles: true
63
+ });
64
+
65
+ document.body.dispatchEvent(trackingEvent);
66
+ };
67
+
68
+ const preferenceModalShowAndHide = ({ event, preferencesModal, conceptId }) => {
49
69
  preferencesModal.classList.toggle('n-myft-ui__preferences-modal--show');
50
70
 
51
71
  if (preferencesModal.classList.contains('n-myft-ui__preferences-modal--show')) {
52
72
  positionModal({ event, preferencesModal });
73
+
74
+ tracking(conceptId);
75
+
53
76
  } else {
54
77
  // Remove existing errors when hiding the modal
55
78
  renderError({
@@ -64,7 +87,6 @@ const removeTopic = async ({ event, conceptId, preferencesModal }) => {
64
87
 
65
88
  try {
66
89
  await myFtClient.remove('user', null, 'followed', 'concept', conceptId, { token: csrfToken });
67
-
68
90
  preferenceModalShowAndHide({ preferencesModal });
69
91
 
70
92
  } catch (error) {
@@ -74,6 +96,11 @@ const removeTopic = async ({ event, conceptId, preferencesModal }) => {
74
96
  event.target.removeAttribute('disabled');
75
97
  };
76
98
 
99
+ const getAlertsPreferenceText = (addedTextBuffer) => {
100
+ const alertsEnabledText = `Your delivery channels: ${addedTextBuffer.join(', ')}.`;
101
+ return Array.isArray(addedTextBuffer) && addedTextBuffer.length > 0 ? alertsEnabledText : '';
102
+ };
103
+
77
104
  const getAlertsPreferences = async ({ event, preferencesModal }) => {
78
105
  const preferencesList = preferencesModal.querySelector('[data-component-id="myft-preferences-modal-list"]');
79
106
 
@@ -91,6 +118,8 @@ const getAlertsPreferences = async ({ event, preferencesModal }) => {
91
118
  }
92
119
  });
93
120
 
121
+ preferencesList.innerHTML = getAlertsPreferenceText(addedTextBuffer);
122
+
94
123
  try {
95
124
  // We need the service worker registration to check for a subscription
96
125
  const serviceWorkerRegistration = await navigator.serviceWorker.ready;
@@ -98,43 +127,50 @@ const getAlertsPreferences = async ({ event, preferencesModal }) => {
98
127
  if (subscription) {
99
128
  addedTextBuffer.push('browser');
100
129
  }
101
-
102
130
  } catch (error) {
103
131
  // eslint-disable-next-line no-console
104
132
  console.warn('There was an error fetching the browser notification preferences', error);
105
133
  }
106
- const alertsEnabledText = `Your delivery channels: ${addedTextBuffer.join(', ')}.`;
107
- const alertsDisabledText = 'You have previously disabled all delivery channels';
108
- preferencesList.innerHTML = addedTextBuffer.length > 0 ? alertsEnabledText : alertsDisabledText;
134
+
135
+ preferencesList.innerHTML = getAlertsPreferenceText(addedTextBuffer);
109
136
  };
110
137
 
111
138
  const setCheckboxForAlertConcept = ({ event, preferencesModal }) => {
112
139
  const conceptId = preferencesModal.dataset.conceptId;
113
140
  const instantAlertsCheckbox = preferencesModal.querySelector('[data-component-id="myft-preferences-modal-checkbox"]');
141
+
114
142
  // search through all the concepts that the user has followed and check whether
115
143
  // 1. the concept which this instant alert modal controls is within them, AND;
116
144
  // 2. the said concept has instant alert enabled
117
145
  // if so, check the checkbox within the modal
118
146
  const currentConcept = event.detail.items.find(item => item && item.uuid === conceptId);
119
147
  if (currentConcept && currentConcept._rel && currentConcept._rel.instant) {
148
+ instantAlertsCheckbox.dataset.trackable = 'pop-up-box|set-instant-alert-off';
120
149
  instantAlertsCheckbox.checked = true;
121
150
  } else {
151
+ instantAlertsCheckbox.dataset.trackable = 'pop-up-box|set-instant-alert-on';
122
152
  instantAlertsCheckbox.checked = false;
123
153
  }
124
154
  };
125
155
 
126
156
  const toggleInstantAlertsPreference = async ({ event, conceptId, preferencesModal }) => {
127
- const instantAlertsToggle = event.target;
157
+ const instantAlertsCheckbox = event.target;
158
+
159
+ if (!instantAlertsCheckbox) {
160
+ return;
161
+ }
128
162
 
129
- instantAlertsToggle.setAttribute('disabled', true);
163
+ instantAlertsCheckbox.setAttribute('disabled', true);
130
164
 
131
165
  const data = {
132
166
  token: csrfToken
133
167
  };
134
168
 
135
- if (instantAlertsToggle.checked) {
169
+ if (instantAlertsCheckbox.checked) {
170
+ instantAlertsCheckbox.dataset.trackable = 'pop-up-box|set-instant-alert-off';
136
171
  data._rel = {instant: 'true'};
137
172
  } else {
173
+ instantAlertsCheckbox.dataset.trackable = 'pop-up-box|set-instant-alert-on';
138
174
  data._rel = {instant: 'false'};
139
175
  }
140
176
 
@@ -146,12 +182,12 @@ const toggleInstantAlertsPreference = async ({ event, conceptId, preferencesModa
146
182
  preferencesModal
147
183
  });
148
184
 
149
- instantAlertsToggle.checked = instantAlertsToggle.checked
185
+ instantAlertsCheckbox.checked = instantAlertsCheckbox.checked
150
186
  ? false
151
187
  : true;
152
188
  }
153
189
 
154
- instantAlertsToggle.removeAttribute('disabled');
190
+ instantAlertsCheckbox.removeAttribute('disabled');
155
191
  };
156
192
 
157
193
  export default () => {
@@ -162,19 +198,28 @@ export default () => {
162
198
  * If this was to be used in other locations it would need some additional work to avoid being singleton
163
199
  */
164
200
  const preferencesModal = document.querySelector('[data-component-id="myft-preferences-modal"]');
201
+
202
+ if (!preferencesModal) {
203
+ return;
204
+ }
165
205
  const conceptId = preferencesModal.dataset.conceptId;
166
206
 
167
- if (!preferencesModal || !conceptId) {
207
+ if (!conceptId) {
168
208
  return;
169
209
  }
170
210
 
171
211
  const removeTopicButton = preferencesModal.querySelector('[data-component-id="myft-preference-modal-remove"]');
172
212
  const instantAlertsCheckbox = preferencesModal.querySelector('[data-component-id="myft-preferences-modal-checkbox"]');
173
213
 
214
+ if (!removeTopicButton || !instantAlertsCheckbox) {
215
+ return;
216
+ }
217
+
174
218
  removeTopicButton.addEventListener('click', event => removeTopic({ event, conceptId, preferencesModal }));
219
+
175
220
  instantAlertsCheckbox.addEventListener('change', event => toggleInstantAlertsPreference({ event, conceptId, preferencesModal }));
176
221
 
177
- document.addEventListener('myft.preference-modal.show-hide.toggle', event => preferenceModalShowAndHide({ event, preferencesModal }));
222
+ document.addEventListener('myft.preference-modal.show-hide.toggle', event => preferenceModalShowAndHide({ event, preferencesModal, conceptId }));
178
223
 
179
224
  document.addEventListener('myft.user.preferred.preference.load', (event) => getAlertsPreferences({ event, preferencesModal }));
180
225
 
@@ -36,6 +36,7 @@ export default function InstantAlertsPreferencesModal({ flags, conceptId, visibl
36
36
  name="receive-instant-alerts"
37
37
  value="receive-instant-alerts"
38
38
  data-component-id="myft-preferences-modal-checkbox"
39
+ data-trackable-context-concept_id={conceptId}
39
40
  />
40
41
  <span className="o-forms-input__label n-myft-ui__preferences-modal__checkbox__message">
41
42
  Get instant alerts for this topic
@@ -44,9 +45,9 @@ export default function InstantAlertsPreferencesModal({ flags, conceptId, visibl
44
45
  </span>
45
46
 
46
47
  <p data-component-id="myft-preferences-modal-list" className="n-myft-ui__preferences-modal__text"></p>
47
- <a className="n-myft-ui__preferences-modal__text" href="/myft/alerts">Manage your preferences here</a>
48
+ <a className="n-myft-ui__preferences-modal__text" href="/myft/alerts" data-trackable="pop-up-box|contact-preference" data-trackable-context-concept_id={conceptId}>Manage your delivery channels here</a>
48
49
  <span className="n-myft-ui__preferences-modal-error" data-component-id="myft-preference-modal-error"></span>
49
- <button className="n-myft-ui__preferences-modal__remove-button" data-component-id="myft-preference-modal-remove">Remove from myFT</button>
50
+ <button className="n-myft-ui__preferences-modal__remove-button" data-component-id="myft-preference-modal-remove" data-trackable="pop-up-box|remove-from-myFT" data-trackable-context-concept_id={conceptId}>Remove from myFT</button>
50
51
  </div>
51
52
  </div>
52
53
  );
@@ -57,7 +57,8 @@ function InstantAlertsPreferencesModal(_ref) {
57
57
  type: 'checkbox',
58
58
  name: 'receive-instant-alerts',
59
59
  value: 'receive-instant-alerts',
60
- 'data-component-id': 'myft-preferences-modal-checkbox'
60
+ 'data-component-id': 'myft-preferences-modal-checkbox',
61
+ 'data-trackable-context-concept_id': conceptId
61
62
  }),
62
63
  _react2.default.createElement(
63
64
  'span',
@@ -69,13 +70,13 @@ function InstantAlertsPreferencesModal(_ref) {
69
70
  _react2.default.createElement('p', { 'data-component-id': 'myft-preferences-modal-list', className: 'n-myft-ui__preferences-modal__text' }),
70
71
  _react2.default.createElement(
71
72
  'a',
72
- { className: 'n-myft-ui__preferences-modal__text', href: '/myft/alerts' },
73
- 'Manage your preferences here'
73
+ { className: 'n-myft-ui__preferences-modal__text', href: '/myft/alerts', 'data-trackable': 'pop-up-box|contact-preference', 'data-trackable-context-concept_id': conceptId },
74
+ 'Manage your delivery channels here'
74
75
  ),
75
76
  _react2.default.createElement('span', { className: 'n-myft-ui__preferences-modal-error', 'data-component-id': 'myft-preference-modal-error' }),
76
77
  _react2.default.createElement(
77
78
  'button',
78
- { className: 'n-myft-ui__preferences-modal__remove-button', 'data-component-id': 'myft-preference-modal-remove' },
79
+ { className: 'n-myft-ui__preferences-modal__remove-button', 'data-component-id': 'myft-preference-modal-remove', 'data-trackable': 'pop-up-box|remove-from-myFT', 'data-trackable-context-concept_id': conceptId },
79
80
  'Remove from myFT'
80
81
  )
81
82
  )
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@financial-times/n-myft-ui",
3
- "version": "30.4.3",
3
+ "version": "30.4.5",
4
4
  "description": "Client side component for interaction with myft",
5
5
  "main": "server.js",
6
6
  "scripts": {
package/secrets.js CHANGED
@@ -6,6 +6,7 @@ module.exports = {
6
6
  '190b4443-dc03-bd53-e79b-b4b6fbd04e64', // segment ID for subscribe URL
7
7
  'ce23dd51-4421-32fc-23df-30099f38f1a4', // segment ID for USG test https://financialtimes.atlassian.net/browse/UG-1191
8
8
  'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx', // regex for uuid generator
9
- 'a5676e20-5c92-47f3-a76c-11f9761121f5' // test/navigationAlphaTest.spec.js
9
+ 'a5676e20-5c92-47f3-a76c-11f9761121f5', // test/navigationAlphaTest.spec.js
10
+ '72de123e-5082-11ee-be56-0242ac120002' // components/jsx/preferences-modal/index.js
10
11
  ]
11
12
  };