@coorpacademy/app-review 0.0.21-alpha.4 → 0.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/es/actions/courses.d.ts +2 -3
- package/es/actions/data/is-fetching.d.ts +5 -0
- package/es/actions/data/is-fetching.js +4 -0
- package/es/actions/data/validate-slide.d.ts +5 -0
- package/es/actions/data/validate-slide.js +6 -0
- package/es/actions/finished-slides.d.ts +7 -0
- package/es/actions/finished-slides.js +7 -0
- package/es/actions/index.d.ts +2 -5
- package/es/actions/index.js +1 -3
- package/es/actions/navigation.d.ts +5 -6
- package/es/actions/review-status.d.ts +7 -0
- package/es/actions/review-status.js +7 -0
- package/es/actions/slides.d.ts +20 -0
- package/es/actions/slides.js +17 -0
- package/es/actions/step-items.d.ts +14 -0
- package/es/actions/step-items.js +12 -0
- package/es/actions/token.d.ts +0 -1
- package/es/common/index.d.ts +8 -0
- package/es/common/index.js +8 -0
- package/es/configure-store.d.ts +3 -12
- package/es/configure-store.js +5 -7
- package/es/fixtures/qcm-slide.d.ts +2 -0
- package/es/fixtures/qcm-slide.js +29 -0
- package/es/fixtures/temp-fixture.d.ts +3 -0
- package/es/fixtures/temp-fixture.js +84 -0
- package/es/helpers/css-register.d.ts +1 -0
- package/es/helpers/css-register.js +2 -0
- package/es/index.d.ts +5 -12
- package/es/index.js +62 -14
- package/es/index.test.d.ts +1 -0
- package/es/index.test.js +52 -0
- package/es/middlewares/on-start-app.d.ts +1 -2
- package/es/middlewares/on-start-app.js +20 -9
- package/es/reducers/courses.d.ts +2 -3
- package/es/reducers/courses.js +2 -1
- package/es/reducers/data.d.ts +7 -0
- package/es/reducers/data.js +76 -0
- package/es/reducers/finished-slides.d.ts +6 -0
- package/es/reducers/finished-slides.js +32 -0
- package/es/reducers/index.d.ts +11 -6
- package/es/reducers/index.js +14 -4
- package/es/reducers/navigation.d.ts +4 -3
- package/es/reducers/navigation.js +4 -1
- package/es/reducers/review-status.d.ts +5 -0
- package/es/reducers/review-status.js +15 -0
- package/es/reducers/slides.d.ts +6 -0
- package/es/reducers/slides.js +112 -0
- package/es/reducers/step-items.d.ts +6 -0
- package/es/reducers/step-items.js +75 -0
- package/es/reducers/token.d.ts +5 -7
- package/es/reducers/token.js +4 -12
- package/es/services/fetch-demo.d.ts +0 -1
- package/es/services/fetch-demo.test.d.ts +0 -1
- package/es/services/fetch-responses.d.ts +6 -7
- package/es/services/fetch-responses.js +2 -2
- package/es/services/fetch.mocks.d.ts +3 -4
- package/es/services/fetch.mocks.js +3 -3
- package/es/types/common.d.ts +7 -0
- package/es/types/common.js +1 -0
- package/es/types/data/index.d.ts +14 -0
- package/es/types/data/index.js +1 -0
- package/es/types/dispatchers.d.ts +17 -0
- package/es/types/dispatchers.js +1 -0
- package/es/types/finished-slides.d.ts +9 -0
- package/es/types/finished-slides.js +1 -0
- package/es/types/review-status.d.ts +1 -0
- package/es/types/review-status.js +1 -0
- package/es/types/slides.d.ts +87 -0
- package/es/types/slides.js +1 -0
- package/es/types/states.d.ts +6 -0
- package/es/types/states.js +1 -0
- package/es/types/step-items.d.ts +26 -0
- package/es/types/step-items.js +5 -0
- package/es/types/store-state.d.ts +12 -0
- package/es/types/store-state.js +1 -0
- package/es/types/utils.d.ts +3 -0
- package/es/types/utils.js +1 -0
- package/es/types/views.d.ts +64 -0
- package/es/types/views.js +1 -0
- package/lib/actions/courses.d.ts +2 -3
- package/lib/actions/data/is-fetching.d.ts +5 -0
- package/lib/actions/data/is-fetching.js +4 -0
- package/lib/actions/data/validate-slide.d.ts +5 -0
- package/lib/actions/data/validate-slide.js +6 -0
- package/lib/actions/finished-slides.d.ts +7 -0
- package/lib/actions/finished-slides.js +7 -0
- package/lib/actions/index.d.ts +2 -5
- package/lib/actions/index.js +1 -3
- package/lib/actions/navigation.d.ts +5 -6
- package/lib/actions/review-status.d.ts +7 -0
- package/lib/actions/review-status.js +7 -0
- package/lib/actions/slides.d.ts +20 -0
- package/lib/actions/slides.js +17 -0
- package/lib/actions/step-items.d.ts +14 -0
- package/lib/actions/step-items.js +12 -0
- package/lib/actions/token.d.ts +0 -1
- package/lib/common/index.d.ts +8 -0
- package/lib/common/index.js +8 -0
- package/lib/configure-store.d.ts +3 -12
- package/lib/configure-store.js +10 -59
- package/lib/fixtures/qcm-slide.d.ts +2 -0
- package/lib/fixtures/qcm-slide.js +29 -0
- package/lib/fixtures/temp-fixture.d.ts +3 -0
- package/lib/fixtures/temp-fixture.js +84 -0
- package/lib/helpers/css-register.d.ts +1 -0
- package/lib/helpers/css-register.js +2 -0
- package/lib/index.d.ts +5 -12
- package/lib/index.js +71 -34
- package/lib/index.test.d.ts +1 -0
- package/lib/index.test.js +160 -0
- package/lib/middlewares/on-start-app.d.ts +1 -2
- package/lib/middlewares/on-start-app.js +29 -16
- package/lib/reducers/courses.d.ts +2 -3
- package/lib/reducers/courses.js +2 -1
- package/lib/reducers/data.d.ts +7 -0
- package/lib/reducers/data.js +77 -0
- package/lib/reducers/finished-slides.d.ts +6 -0
- package/lib/reducers/finished-slides.js +44 -0
- package/lib/reducers/index.d.ts +11 -6
- package/lib/reducers/index.js +14 -4
- package/lib/reducers/navigation.d.ts +4 -3
- package/lib/reducers/navigation.js +6 -1
- package/lib/reducers/review-status.d.ts +5 -0
- package/lib/reducers/review-status.js +16 -0
- package/lib/reducers/slides.d.ts +6 -0
- package/lib/reducers/slides.js +119 -0
- package/lib/reducers/step-items.d.ts +6 -0
- package/lib/reducers/step-items.js +87 -0
- package/lib/reducers/token.d.ts +5 -7
- package/lib/reducers/token.js +4 -13
- package/lib/services/fetch-demo.d.ts +0 -1
- package/lib/services/fetch-demo.js +25 -23
- package/lib/services/fetch-demo.test.d.ts +0 -1
- package/lib/services/fetch-responses.d.ts +6 -7
- package/lib/services/fetch-responses.js +2 -2
- package/lib/services/fetch.mocks.d.ts +3 -4
- package/lib/services/fetch.mocks.js +28 -16
- package/lib/types/common.d.ts +7 -0
- package/lib/types/common.js +1 -0
- package/lib/types/data/index.d.ts +14 -0
- package/lib/types/data/index.js +1 -0
- package/lib/types/dispatchers.d.ts +17 -0
- package/lib/types/dispatchers.js +1 -0
- package/lib/types/finished-slides.d.ts +9 -0
- package/lib/types/finished-slides.js +1 -0
- package/lib/types/review-status.d.ts +1 -0
- package/lib/types/review-status.js +1 -0
- package/lib/types/slides.d.ts +87 -0
- package/lib/types/slides.js +1 -0
- package/lib/types/states.d.ts +6 -0
- package/lib/types/states.js +1 -0
- package/lib/types/step-items.d.ts +26 -0
- package/lib/types/step-items.js +5 -0
- package/lib/types/store-state.d.ts +12 -0
- package/lib/types/store-state.js +1 -0
- package/lib/types/utils.d.ts +3 -0
- package/lib/types/utils.js +1 -0
- package/lib/types/views.d.ts +64 -0
- package/lib/types/views.js +1 -0
- package/package.json +21 -7
- package/src/actions/courses.ts +2 -2
- package/src/actions/data/is-fetching.ts +12 -0
- package/src/actions/data/validate-slide.ts +15 -0
- package/src/actions/finished-slides.ts +21 -0
- package/src/actions/index.ts +8 -5
- package/src/actions/navigation.ts +6 -5
- package/src/actions/review-status.ts +19 -0
- package/src/actions/slides.ts +45 -0
- package/src/actions/step-items.ts +39 -0
- package/src/common/index.ts +14 -0
- package/src/configure-store.ts +14 -22
- package/src/fixtures/qcm-slide.ts +31 -0
- package/src/fixtures/temp-fixture.ts +94 -0
- package/src/helpers/css-modules-require-hook.d.ts +4 -0
- package/src/helpers/css-register.ts +3 -0
- package/src/index.test.tsx +82 -0
- package/src/index.tsx +75 -22
- package/src/middlewares/on-start-app.ts +35 -20
- package/src/reducers/courses.ts +3 -2
- package/src/reducers/data.ts +88 -0
- package/src/reducers/finished-slides.ts +48 -0
- package/src/reducers/index.ts +14 -4
- package/src/reducers/navigation.ts +7 -3
- package/src/reducers/review-status.ts +23 -0
- package/src/reducers/slides.ts +136 -0
- package/src/reducers/step-items.ts +112 -0
- package/src/reducers/token.ts +6 -15
- package/src/services/fetch-demo.ts +17 -15
- package/src/services/fetch-responses.ts +7 -7
- package/src/services/fetch.mocks.ts +29 -14
- package/src/types/common.ts +8 -0
- package/src/types/data/index.ts +16 -0
- package/src/types/dispatchers.ts +18 -0
- package/src/types/finished-slides.ts +9 -0
- package/src/types/globals.d.ts +6 -0
- package/src/types/review-status.ts +1 -0
- package/src/types/slides.ts +107 -0
- package/src/types/states.ts +6 -0
- package/src/types/step-items.ts +31 -0
- package/src/types/store-state.ts +20 -0
- package/src/types/utils.ts +4 -0
- package/src/types/views.tsx +69 -0
- package/es/actions/courses.d.ts.map +0 -1
- package/es/actions/index.d.ts.map +0 -1
- package/es/actions/navigation.d.ts.map +0 -1
- package/es/actions/token.d.ts.map +0 -1
- package/es/components/__tmp-backup-vues-mobile/revision-home.d.ts +0 -10
- package/es/components/__tmp-backup-vues-mobile/revision-home.d.ts.map +0 -1
- package/es/components/__tmp-backup-vues-mobile/revision-home.js +0 -83
- package/es/components/__tmp-backup-vues-mobile/revision-home.stories.d.ts +0 -1
- package/es/components/__tmp-backup-vues-mobile/revision-home.stories.d.ts.map +0 -1
- package/es/components/__tmp-backup-vues-mobile/revision-home.stories.js +0 -14
- package/es/components/__tmp-backup-vues-mobile/revision-onboarding.d.ts +0 -4
- package/es/components/__tmp-backup-vues-mobile/revision-onboarding.d.ts.map +0 -1
- package/es/components/__tmp-backup-vues-mobile/revision-onboarding.js +0 -57
- package/es/components/__tmp-backup-vues-mobile/revision-quizzer.d.ts +0 -19
- package/es/components/__tmp-backup-vues-mobile/revision-quizzer.d.ts.map +0 -1
- package/es/components/__tmp-backup-vues-mobile/revision-quizzer.js +0 -120
- package/es/configure-store.d.ts.map +0 -1
- package/es/index.d.ts.map +0 -1
- package/es/middlewares/on-start-app.d.ts.map +0 -1
- package/es/reducers/courses.d.ts.map +0 -1
- package/es/reducers/index.d.ts.map +0 -1
- package/es/reducers/navigation.d.ts.map +0 -1
- package/es/reducers/token.d.ts.map +0 -1
- package/es/services/fetch-demo.d.ts.map +0 -1
- package/es/services/fetch-demo.test.d.ts.map +0 -1
- package/es/services/fetch-responses.d.ts.map +0 -1
- package/es/services/fetch.mocks.d.ts.map +0 -1
- package/lib/actions/courses.d.ts.map +0 -1
- package/lib/actions/index.d.ts.map +0 -1
- package/lib/actions/navigation.d.ts.map +0 -1
- package/lib/actions/token.d.ts.map +0 -1
- package/lib/components/__tmp-backup-vues-mobile/revision-home.d.ts +0 -10
- package/lib/components/__tmp-backup-vues-mobile/revision-home.d.ts.map +0 -1
- package/lib/components/__tmp-backup-vues-mobile/revision-home.js +0 -98
- package/lib/components/__tmp-backup-vues-mobile/revision-home.stories.d.ts +0 -1
- package/lib/components/__tmp-backup-vues-mobile/revision-home.stories.d.ts.map +0 -1
- package/lib/components/__tmp-backup-vues-mobile/revision-home.stories.js +0 -14
- package/lib/components/__tmp-backup-vues-mobile/revision-onboarding.d.ts +0 -4
- package/lib/components/__tmp-backup-vues-mobile/revision-onboarding.d.ts.map +0 -1
- package/lib/components/__tmp-backup-vues-mobile/revision-onboarding.js +0 -60
- package/lib/components/__tmp-backup-vues-mobile/revision-quizzer.d.ts +0 -19
- package/lib/components/__tmp-backup-vues-mobile/revision-quizzer.d.ts.map +0 -1
- package/lib/components/__tmp-backup-vues-mobile/revision-quizzer.js +0 -128
- package/lib/configure-store.d.ts.map +0 -1
- package/lib/index.d.ts.map +0 -1
- package/lib/middlewares/on-start-app.d.ts.map +0 -1
- package/lib/reducers/courses.d.ts.map +0 -1
- package/lib/reducers/index.d.ts.map +0 -1
- package/lib/reducers/navigation.d.ts.map +0 -1
- package/lib/reducers/token.d.ts.map +0 -1
- package/lib/services/fetch-demo.d.ts.map +0 -1
- package/lib/services/fetch-demo.test.d.ts.map +0 -1
- package/lib/services/fetch-responses.d.ts.map +0 -1
- package/lib/services/fetch.mocks.d.ts.map +0 -1
- package/src/components/__tmp-backup-vues-mobile/revision-home.stories.tsx +0 -16
- package/src/components/__tmp-backup-vues-mobile/revision-home.tsx +0 -125
- package/src/components/__tmp-backup-vues-mobile/revision-onboarding.tsx +0 -84
- package/src/components/__tmp-backup-vues-mobile/revision-quizzer.tsx +0 -176
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
/* eslint-disable no-console */
|
|
2
|
+
import {SlidesViewProps} from '../types/views';
|
|
3
|
+
|
|
4
|
+
export const correctionPopinProps: SlidesViewProps['correctionPopinProps'] = {
|
|
5
|
+
klf: {
|
|
6
|
+
label: 'Key learning factor',
|
|
7
|
+
tooltip: 'Some tooltip info.',
|
|
8
|
+
onClick: () => {
|
|
9
|
+
console.log('klf onClick');
|
|
10
|
+
}
|
|
11
|
+
},
|
|
12
|
+
information: {
|
|
13
|
+
label: 'Key learning factor',
|
|
14
|
+
message: 'info msg'
|
|
15
|
+
},
|
|
16
|
+
next: {
|
|
17
|
+
label: 'Next',
|
|
18
|
+
ariaLabel: 'Next'
|
|
19
|
+
},
|
|
20
|
+
successLabel: 'CORRECT ANSWER',
|
|
21
|
+
failureLabel: 'WRONG ANSWER'
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
const confettiAnimationProps = {
|
|
25
|
+
'aria-label': 'aria lottie',
|
|
26
|
+
'data-name': 'default-lottie',
|
|
27
|
+
className: undefined,
|
|
28
|
+
animationSrc: 'https://static-staging.coorpacademy.com/animations/review/confetti.json',
|
|
29
|
+
loop: undefined,
|
|
30
|
+
autoplay: true,
|
|
31
|
+
rendererSettings: {
|
|
32
|
+
hideOnTransparent: false,
|
|
33
|
+
animationClassName: ''
|
|
34
|
+
},
|
|
35
|
+
ie11ImageBackup:
|
|
36
|
+
'https://static-staging.coorpacademy.com/animations/review/conffeti_congrats.svg',
|
|
37
|
+
animationControl: undefined
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
const starAnimationProps = {
|
|
41
|
+
'aria-label': 'Review Card Congrats Container',
|
|
42
|
+
'data-name': 'card-star',
|
|
43
|
+
animationLottie: {
|
|
44
|
+
'aria-label': 'aria lottie',
|
|
45
|
+
'data-name': 'default-lottie',
|
|
46
|
+
animationSrc: 'https://static-staging.coorpacademy.com/animations/review/star.json',
|
|
47
|
+
ie11ImageBackup:
|
|
48
|
+
'https://static-staging.coorpacademy.com/animations/review/stars_icon_congrats.svg'
|
|
49
|
+
},
|
|
50
|
+
iconAriaLabel: 'Image without information',
|
|
51
|
+
cardType: 'card-star',
|
|
52
|
+
reviewCardTitle: 'You have won',
|
|
53
|
+
reviewCardValue: '100',
|
|
54
|
+
timerAnimation: 200
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
const rankAnimationProps = {
|
|
58
|
+
'aria-label': 'Review Card Congrats Container',
|
|
59
|
+
'data-name': 'card-rank',
|
|
60
|
+
animationLottie: {
|
|
61
|
+
'aria-label': 'aria lottie',
|
|
62
|
+
'data-name': 'default-lottie',
|
|
63
|
+
animationSrc: 'https://static-staging.coorpacademy.com/animations/review/rank.json',
|
|
64
|
+
ie11ImageBackup:
|
|
65
|
+
'https://static-staging.coorpacademy.com/animations/review/rank_icon_congrats.svg'
|
|
66
|
+
},
|
|
67
|
+
cardType: 'card-rank',
|
|
68
|
+
iconAriaLabel: 'Image without information',
|
|
69
|
+
reviewCardTitle: 'You are now',
|
|
70
|
+
reviewCardValue: '14',
|
|
71
|
+
rankSuffix: 'th',
|
|
72
|
+
timerAnimation: 200
|
|
73
|
+
};
|
|
74
|
+
|
|
75
|
+
export const congratsProps: SlidesViewProps['congratsProps'] = {
|
|
76
|
+
'aria-label': 'Review Congratulations',
|
|
77
|
+
'data-name': 'review-congrats',
|
|
78
|
+
animationLottie: confettiAnimationProps,
|
|
79
|
+
title: 'Congratulations!',
|
|
80
|
+
cardCongratsStar: starAnimationProps,
|
|
81
|
+
cardCongratsRank: rankAnimationProps,
|
|
82
|
+
buttonRevising: {
|
|
83
|
+
'aria-label': 'Continue revising button',
|
|
84
|
+
label: 'Continue revising',
|
|
85
|
+
onClick: () => console.log('Continue revising'),
|
|
86
|
+
type: 'tertiary'
|
|
87
|
+
},
|
|
88
|
+
buttonRevisingSkill: {
|
|
89
|
+
label: 'Revise another skill',
|
|
90
|
+
'aria-label': 'Revise another skill button',
|
|
91
|
+
onClick: () => console.log('Revise another skill'),
|
|
92
|
+
type: 'primary'
|
|
93
|
+
}
|
|
94
|
+
};
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
import browserEnv from 'browser-env';
|
|
2
|
+
import test from 'ava';
|
|
3
|
+
import type {ExecutionContext} from 'ava';
|
|
4
|
+
import React from 'react';
|
|
5
|
+
import {render, fireEvent, act} from '@testing-library/react';
|
|
6
|
+
import {slide} from './fixtures/qcm-slide';
|
|
7
|
+
import type {AppOptions} from './types/common';
|
|
8
|
+
import AppReview from '.';
|
|
9
|
+
|
|
10
|
+
browserEnv({pretendToBeVisual: true});
|
|
11
|
+
|
|
12
|
+
const elementExists = (foundElements: NodeListOf<Element>): Element =>
|
|
13
|
+
foundElements && foundElements[0];
|
|
14
|
+
|
|
15
|
+
const sleep = (msToSleep: number): Promise<void> =>
|
|
16
|
+
new Promise(resolve => {
|
|
17
|
+
setTimeout(resolve, msToSleep);
|
|
18
|
+
});
|
|
19
|
+
|
|
20
|
+
const waitForChanges = async (msToWait = 3000): Promise<void> => {
|
|
21
|
+
await act(async () => {
|
|
22
|
+
await sleep(msToWait); // wait *just* a little longer than the timeout in the component
|
|
23
|
+
});
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
const LIMIT = 5;
|
|
27
|
+
|
|
28
|
+
const clickAllSlides = async (
|
|
29
|
+
t: ExecutionContext<unknown>,
|
|
30
|
+
container: HTMLElement,
|
|
31
|
+
accumulator = 0
|
|
32
|
+
): Promise<void> => {
|
|
33
|
+
if (accumulator === LIMIT) return;
|
|
34
|
+
|
|
35
|
+
// last one needs to wait for more calculations && components updates
|
|
36
|
+
if (accumulator === 4)
|
|
37
|
+
await act(async () => {
|
|
38
|
+
await sleep(1000);
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
const validateButton = container.querySelectorAll(
|
|
42
|
+
`[data-name="slide-validate-button-${accumulator}"]`
|
|
43
|
+
);
|
|
44
|
+
t.truthy(elementExists(validateButton));
|
|
45
|
+
|
|
46
|
+
await act(async () => {
|
|
47
|
+
await fireEvent.click(validateButton[0]);
|
|
48
|
+
});
|
|
49
|
+
|
|
50
|
+
const nextButton = container.querySelectorAll(
|
|
51
|
+
`[data-name="next-question-button-${accumulator}"]`
|
|
52
|
+
);
|
|
53
|
+
t.truthy(elementExists(nextButton));
|
|
54
|
+
|
|
55
|
+
await act(async () => {
|
|
56
|
+
await fireEvent.click(nextButton[0]);
|
|
57
|
+
});
|
|
58
|
+
|
|
59
|
+
await clickAllSlides(t, container, accumulator + 1);
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
const appOptions: AppOptions = {
|
|
63
|
+
token: process.env.API_TEST_TOKEN || '',
|
|
64
|
+
slide
|
|
65
|
+
};
|
|
66
|
+
|
|
67
|
+
test('should validate all the slides (all correct scenario)', async t => {
|
|
68
|
+
t.plan(13);
|
|
69
|
+
const {container} = render(<AppReview options={appOptions} key={0} />);
|
|
70
|
+
await waitForChanges(1000);
|
|
71
|
+
|
|
72
|
+
const wrapper = container.querySelector('[data-name="slides-revision-container"]');
|
|
73
|
+
t.truthy(wrapper);
|
|
74
|
+
|
|
75
|
+
const stackedSlidesContainer = wrapper.querySelector('[data-name="stacked-slides-container"]');
|
|
76
|
+
|
|
77
|
+
t.truthy(stackedSlidesContainer);
|
|
78
|
+
|
|
79
|
+
await clickAllSlides(t, container);
|
|
80
|
+
|
|
81
|
+
t.pass();
|
|
82
|
+
});
|
package/src/index.tsx
CHANGED
|
@@ -1,36 +1,94 @@
|
|
|
1
1
|
import React, {useEffect, useState} from 'react';
|
|
2
2
|
import {connect, Provider} from 'react-redux';
|
|
3
|
-
import
|
|
3
|
+
import AppReviewTemplate from '@coorpacademy/components/es/template/app-review';
|
|
4
4
|
|
|
5
5
|
import configureStore from './configure-store';
|
|
6
6
|
import {navigateTo, navigateBack, startApp} from './actions/navigation';
|
|
7
|
+
import {updateSlidesOnNext, updateSlidesOnValidation} from './actions/slides';
|
|
7
8
|
import {getCurrentViewName} from './reducers/navigation';
|
|
9
|
+
import type {SlidesViewStaticProps} from './types/views';
|
|
10
|
+
import type {AppOptions} from './types/common';
|
|
11
|
+
import type {StoreState} from './types/store-state';
|
|
12
|
+
import {congratsProps, correctionPopinProps} from './fixtures/temp-fixture';
|
|
13
|
+
import {updateFinishedSlides} from './actions/finished-slides';
|
|
14
|
+
import {updateReviewStatus} from './actions/review-status';
|
|
15
|
+
import {updateStepItemsOnValidation, updateStepItemsOnNext} from './actions/step-items';
|
|
16
|
+
import type {Dispatchers} from './types/dispatchers';
|
|
17
|
+
import {validateSlide} from './actions/data/validate-slide';
|
|
8
18
|
|
|
9
19
|
// -----------------------------------------------------------------------------
|
|
10
20
|
|
|
11
|
-
|
|
12
|
-
|
|
21
|
+
type StaticProps = {
|
|
22
|
+
viewName: 'home' | 'onboarding' | 'slides';
|
|
23
|
+
slides: SlidesViewStaticProps;
|
|
13
24
|
};
|
|
14
25
|
|
|
15
|
-
|
|
16
|
-
|
|
26
|
+
// -----------------------------------------------------------------------------
|
|
27
|
+
|
|
28
|
+
const mapDispatchToProps: Dispatchers = {
|
|
29
|
+
navigateTo,
|
|
30
|
+
navigateBack,
|
|
31
|
+
validateSlide,
|
|
32
|
+
updateSlidesOnValidation,
|
|
33
|
+
updateSlidesOnNext,
|
|
34
|
+
updateReviewStatus,
|
|
35
|
+
updateStepItemsOnValidation,
|
|
36
|
+
updateStepItemsOnNext,
|
|
37
|
+
updateFinishedSlides
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
const mapStateToProps = (state: StoreState): StaticProps => {
|
|
41
|
+
return {
|
|
42
|
+
viewName: getCurrentViewName(state),
|
|
43
|
+
slides: {
|
|
44
|
+
headerProps: {
|
|
45
|
+
mode: '__revision_mode',
|
|
46
|
+
skillName: '__agility',
|
|
47
|
+
onQuitClick: (): void => {
|
|
48
|
+
// eslint-disable-next-line no-console
|
|
49
|
+
console.log('onQuitClick');
|
|
50
|
+
},
|
|
51
|
+
'aria-label': 'aria-header-wrapper',
|
|
52
|
+
closeButtonAriaLabel: 'aria-close-button'
|
|
53
|
+
},
|
|
54
|
+
slides: state.ui.slides,
|
|
55
|
+
validate: {
|
|
56
|
+
label: '__validate'
|
|
57
|
+
},
|
|
58
|
+
finishedSlides: state.ui.finishedSlides,
|
|
59
|
+
stepItems: state.ui.stepItems,
|
|
60
|
+
reviewStatus: state.ui.reviewStatus,
|
|
61
|
+
correctionPopinProps,
|
|
62
|
+
congratsProps,
|
|
63
|
+
slideValidationResult: state.data.slideValidationResult
|
|
64
|
+
}
|
|
65
|
+
};
|
|
66
|
+
};
|
|
67
|
+
|
|
68
|
+
// Props = StaticProps && Dispatchers
|
|
69
|
+
|
|
70
|
+
const App = connect(mapStateToProps, mapDispatchToProps)(AppReviewTemplate);
|
|
17
71
|
|
|
18
72
|
// -----------------------------------------------------------------------------
|
|
19
73
|
|
|
20
|
-
const
|
|
74
|
+
const AppReview = ({options}: {options: AppOptions}): JSX.Element => {
|
|
21
75
|
const [store, setStore] = useState(null);
|
|
76
|
+
const [appStarted, setAppStarted] = useState(false);
|
|
22
77
|
|
|
23
78
|
useEffect(() => {
|
|
24
|
-
|
|
25
|
-
const store = await configureStore();
|
|
79
|
+
if (store) {
|
|
26
80
|
store.dispatch(startApp(options));
|
|
27
|
-
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
81
|
+
setAppStarted(true);
|
|
82
|
+
} else {
|
|
83
|
+
const _configure = async (): Promise<void> => {
|
|
84
|
+
const _store = await configureStore();
|
|
85
|
+
setStore(_store);
|
|
86
|
+
};
|
|
87
|
+
_configure();
|
|
88
|
+
}
|
|
89
|
+
}, [options, store]);
|
|
32
90
|
|
|
33
|
-
if (!store) return null;
|
|
91
|
+
if (!store || !appStarted) return null;
|
|
34
92
|
|
|
35
93
|
return (
|
|
36
94
|
<Provider store={store}>
|
|
@@ -42,17 +100,12 @@ const AppRevision = ({options}: Props) => {
|
|
|
42
100
|
// -----------------------------------------------------------------------------
|
|
43
101
|
|
|
44
102
|
declare global {
|
|
103
|
+
// eslint-disable-next-line no-shadow
|
|
45
104
|
interface Window {
|
|
46
105
|
__REDUX_DEVTOOLS_EXTENSION__?: boolean;
|
|
47
106
|
}
|
|
48
107
|
}
|
|
49
108
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
export type AppOptions = {
|
|
53
|
-
token: string;
|
|
54
|
-
theme?: any;
|
|
55
|
-
translations?: any;
|
|
56
|
-
};
|
|
109
|
+
// -----------------------------------------------------------------------------
|
|
57
110
|
|
|
58
|
-
export default
|
|
111
|
+
export default AppReview;
|
|
@@ -1,30 +1,45 @@
|
|
|
1
|
-
import fetch from 'cross-fetch';
|
|
2
1
|
import type {Middleware} from 'redux';
|
|
3
2
|
import {Dispatch} from 'redux';
|
|
4
3
|
|
|
5
|
-
import {Action
|
|
6
|
-
import
|
|
7
|
-
import
|
|
4
|
+
import {Action} from '../actions';
|
|
5
|
+
// import fetchCourse from '../services/fetch-demo';
|
|
6
|
+
import {VIEWS} from '../common';
|
|
7
|
+
import {navigateTo, START_APP, ViewPath} from '../actions/navigation';
|
|
8
|
+
import {storeToken} from '../actions/token';
|
|
9
|
+
import {storeFirstSlide} from '../actions/slides';
|
|
10
|
+
// import {receivedCourse} from '../actions/courses';
|
|
11
|
+
import {StoreState} from '../types/store-state';
|
|
8
12
|
|
|
9
|
-
const onStartApp: Middleware<{}, StoreState, Dispatch<Action>> =
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
13
|
+
const onStartApp: Middleware<{}, StoreState, Dispatch<Action>> =
|
|
14
|
+
({dispatch}) =>
|
|
15
|
+
next =>
|
|
16
|
+
(action: Action) => {
|
|
17
|
+
if (action.type === START_APP) {
|
|
18
|
+
// eslint-disable-next-line no-warning-comments
|
|
19
|
+
// TODO: fetchProgression + fetchSlide à partir de la progression passée dans les options de l'app
|
|
20
|
+
const {slide} = action.payload;
|
|
21
|
+
if (slide) {
|
|
22
|
+
const {token} = action.payload;
|
|
23
|
+
dispatch(storeToken(token));
|
|
24
|
+
dispatch(storeFirstSlide(slide));
|
|
25
|
+
}
|
|
15
26
|
|
|
16
|
-
|
|
17
|
-
// demo service
|
|
27
|
+
const initialView: ViewPath = slide ? VIEWS.slides : VIEWS.onboarding;
|
|
18
28
|
|
|
19
|
-
|
|
20
|
-
const universalRef = 'dis_xxx15';
|
|
29
|
+
dispatch(navigateTo(initialView));
|
|
21
30
|
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
});
|
|
25
|
-
}
|
|
31
|
+
// --------------
|
|
32
|
+
// demo service
|
|
26
33
|
|
|
27
|
-
|
|
28
|
-
|
|
34
|
+
// const language = 'fr';
|
|
35
|
+
// const universalRef = 'dis_xxx15';
|
|
36
|
+
|
|
37
|
+
// fetchCourse(token, language, universalRef).then(course => {
|
|
38
|
+
// dispatch(receivedCourse(course));
|
|
39
|
+
// });
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
return next(action);
|
|
43
|
+
};
|
|
29
44
|
|
|
30
45
|
export default onStartApp;
|
package/src/reducers/courses.ts
CHANGED
|
@@ -1,12 +1,13 @@
|
|
|
1
|
-
import {ReceivedCourse, RECEIVED_COURSE} from '../actions';
|
|
1
|
+
import {ReceivedCourse, RECEIVED_COURSE} from '../actions/courses';
|
|
2
2
|
|
|
3
3
|
// -----------------------------------------------------------------------------
|
|
4
4
|
|
|
5
|
-
export type State = Array<
|
|
5
|
+
export type State = Array<unknown>;
|
|
6
6
|
export const initialState: State = [];
|
|
7
7
|
|
|
8
8
|
// -----------------------------------------------------------------------------
|
|
9
9
|
|
|
10
|
+
// eslint-disable-next-line default-param-last
|
|
10
11
|
const reducer = (state: State = initialState, action: ReceivedCourse): State => {
|
|
11
12
|
switch (action.type) {
|
|
12
13
|
case RECEIVED_COURSE: {
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
import getOr from 'lodash/fp/getOr';
|
|
2
|
+
import noop from 'lodash/fp/noop';
|
|
3
|
+
import set from 'lodash/fp/set';
|
|
4
|
+
import {StoreToken, STORE_TOKEN} from '../actions/token';
|
|
5
|
+
import {IsFetching, IS_FETCHING_TRUE} from '../actions/data/is-fetching';
|
|
6
|
+
import {ValidateSlide, VALIDATE_SLIDE} from '../actions/data/validate-slide';
|
|
7
|
+
import {DataState} from '../types/data';
|
|
8
|
+
import {setToken} from './token';
|
|
9
|
+
|
|
10
|
+
const defaultState = {
|
|
11
|
+
isFetching: true,
|
|
12
|
+
slideValidationResult: null,
|
|
13
|
+
token: null
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
type ApiActions = IsFetching | ValidateSlide | StoreToken;
|
|
17
|
+
|
|
18
|
+
// eslint-disable-next-line default-param-last
|
|
19
|
+
const data = (state: DataState = defaultState, action: ApiActions): DataState => {
|
|
20
|
+
switch (action.type) {
|
|
21
|
+
case STORE_TOKEN: {
|
|
22
|
+
return setToken(action.payload, state);
|
|
23
|
+
}
|
|
24
|
+
case VALIDATE_SLIDE: {
|
|
25
|
+
const previousSlideNumber: number = getOr(-1, 'slideValidationResult.slideNumber', state);
|
|
26
|
+
// hard coded for now
|
|
27
|
+
return set(
|
|
28
|
+
'slideValidationResult',
|
|
29
|
+
{
|
|
30
|
+
slideNumber: previousSlideNumber + 1,
|
|
31
|
+
result: 'success',
|
|
32
|
+
// exitNode
|
|
33
|
+
nextSlide: {
|
|
34
|
+
questionText: 'Test',
|
|
35
|
+
answerUI: {
|
|
36
|
+
model: {
|
|
37
|
+
answers: [
|
|
38
|
+
{
|
|
39
|
+
title: 'There is no need for a password',
|
|
40
|
+
onClick: noop,
|
|
41
|
+
selected: false
|
|
42
|
+
},
|
|
43
|
+
{
|
|
44
|
+
title: 'Lorem ipsum',
|
|
45
|
+
onClick: noop,
|
|
46
|
+
selected: false
|
|
47
|
+
},
|
|
48
|
+
{
|
|
49
|
+
title: 'Lorem',
|
|
50
|
+
onClick: noop,
|
|
51
|
+
selected: true,
|
|
52
|
+
order: 1
|
|
53
|
+
},
|
|
54
|
+
{
|
|
55
|
+
title: 'You need to have a password',
|
|
56
|
+
onClick: noop,
|
|
57
|
+
selected: false
|
|
58
|
+
},
|
|
59
|
+
{
|
|
60
|
+
title: 'Pouet',
|
|
61
|
+
onClick: noop,
|
|
62
|
+
selected: true,
|
|
63
|
+
order: 0
|
|
64
|
+
}
|
|
65
|
+
],
|
|
66
|
+
type: 'qcmDrag'
|
|
67
|
+
},
|
|
68
|
+
help: 'Help text will appear here'
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
},
|
|
72
|
+
state
|
|
73
|
+
);
|
|
74
|
+
}
|
|
75
|
+
case IS_FETCHING_TRUE: {
|
|
76
|
+
return set('isFetching', true, state);
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
// case VALIDATE_SLIDE_FAILURE: {
|
|
80
|
+
// return set('entities.isFetching', false, state);
|
|
81
|
+
// }
|
|
82
|
+
|
|
83
|
+
default:
|
|
84
|
+
return state;
|
|
85
|
+
}
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
export default data;
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import forEach from 'lodash/fp/forEach';
|
|
2
|
+
import {UpdateFinishedSlides, UPDATE_FINISHED_SLIDES} from '../actions/finished-slides';
|
|
3
|
+
import {slideNumbers} from '../common';
|
|
4
|
+
import {FinishedSlides} from '../types/finished-slides';
|
|
5
|
+
|
|
6
|
+
const _forEach: <T>(
|
|
7
|
+
iteratee: (value: T[keyof T], index: number) => void,
|
|
8
|
+
collection: T
|
|
9
|
+
// @ts-expect-error to remove lodash's forEach iteratee args number cap
|
|
10
|
+
) => void = forEach.convert({
|
|
11
|
+
cap: false
|
|
12
|
+
});
|
|
13
|
+
|
|
14
|
+
// -----------------------------------------------------------------------------
|
|
15
|
+
|
|
16
|
+
export type State = FinishedSlides;
|
|
17
|
+
export const initialState: State = {
|
|
18
|
+
slideNumbers
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
// -----------------------------------------------------------------------------
|
|
22
|
+
|
|
23
|
+
// eslint-disable-next-line default-param-last
|
|
24
|
+
const reducer = (state: State = initialState, action: UpdateFinishedSlides): State => {
|
|
25
|
+
switch (action.type) {
|
|
26
|
+
case UPDATE_FINISHED_SLIDES: {
|
|
27
|
+
const {slideNumbers: _slideNumbers, ...rest} = state;
|
|
28
|
+
const {slideNumber, value} = action.payload;
|
|
29
|
+
const _state: State = {
|
|
30
|
+
slideNumbers: _slideNumbers
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
_forEach<Omit<State, 'slideNumbers'>>((finishedSlide, index) => {
|
|
34
|
+
const previousValue = finishedSlide;
|
|
35
|
+
_state[index] = previousValue;
|
|
36
|
+
}, rest);
|
|
37
|
+
|
|
38
|
+
_state[slideNumber] = value;
|
|
39
|
+
return _state;
|
|
40
|
+
}
|
|
41
|
+
default:
|
|
42
|
+
return state;
|
|
43
|
+
}
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
// -----------------------------------------------------------------------------
|
|
47
|
+
|
|
48
|
+
export default reducer;
|
package/src/reducers/index.ts
CHANGED
|
@@ -1,13 +1,23 @@
|
|
|
1
1
|
import {combineReducers} from 'redux';
|
|
2
2
|
|
|
3
|
+
import data from './data';
|
|
3
4
|
import courses from './courses';
|
|
5
|
+
import finishedSlides from './finished-slides';
|
|
4
6
|
import navigation from './navigation';
|
|
5
|
-
import
|
|
7
|
+
import reviewStatus from './review-status';
|
|
8
|
+
import slides from './slides';
|
|
9
|
+
import stepItems from './step-items';
|
|
6
10
|
|
|
7
|
-
const
|
|
11
|
+
const ui = combineReducers({
|
|
8
12
|
courses,
|
|
13
|
+
finishedSlides,
|
|
9
14
|
navigation,
|
|
10
|
-
|
|
15
|
+
reviewStatus,
|
|
16
|
+
slides,
|
|
17
|
+
stepItems
|
|
11
18
|
});
|
|
12
19
|
|
|
13
|
-
export default
|
|
20
|
+
export default combineReducers({
|
|
21
|
+
ui,
|
|
22
|
+
data
|
|
23
|
+
});
|
|
@@ -1,13 +1,16 @@
|
|
|
1
|
-
import {NAVIGATE_BACK, NAVIGATE_TO} from '../actions/navigation';
|
|
1
|
+
import {NAVIGATE_BACK, NAVIGATE_TO, ViewPath} from '../actions/navigation';
|
|
2
2
|
import type {NavigateTo, NavigateBack} from '../actions/navigation';
|
|
3
|
+
import {StoreState} from '../types/store-state';
|
|
4
|
+
import {NavigationState as State} from '../types/states';
|
|
3
5
|
|
|
4
6
|
// -----------------------------------------------------------------------------
|
|
5
7
|
|
|
6
|
-
export type State = Array<string>;
|
|
8
|
+
// export type State = Array<string>;
|
|
7
9
|
export const initialState: State = ['home'];
|
|
8
10
|
|
|
9
11
|
// -----------------------------------------------------------------------------
|
|
10
12
|
|
|
13
|
+
// eslint-disable-next-line default-param-last
|
|
11
14
|
const reducer = (state: State = initialState, action: NavigateTo | NavigateBack): State => {
|
|
12
15
|
switch (action.type) {
|
|
13
16
|
case NAVIGATE_TO: {
|
|
@@ -25,7 +28,8 @@ const reducer = (state: State = initialState, action: NavigateTo | NavigateBack)
|
|
|
25
28
|
|
|
26
29
|
// -----------------------------------------------------------------------------
|
|
27
30
|
|
|
28
|
-
export const getCurrentViewName = appState
|
|
31
|
+
export const getCurrentViewName = (appState: StoreState): ViewPath =>
|
|
32
|
+
appState.ui.navigation[appState.ui.navigation.length - 1];
|
|
29
33
|
|
|
30
34
|
// -----------------------------------------------------------------------------
|
|
31
35
|
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import {UpdateReviewStatus, UPDATE_REVIEW_STATUS} from '../actions/review-status';
|
|
2
|
+
|
|
3
|
+
// -----------------------------------------------------------------------------
|
|
4
|
+
|
|
5
|
+
export type State = 'finished' | 'ongoing';
|
|
6
|
+
export const initialState: State = 'ongoing';
|
|
7
|
+
|
|
8
|
+
// -----------------------------------------------------------------------------
|
|
9
|
+
|
|
10
|
+
// eslint-disable-next-line default-param-last
|
|
11
|
+
const reducer = (state: State = initialState, action: UpdateReviewStatus): State => {
|
|
12
|
+
switch (action.type) {
|
|
13
|
+
case UPDATE_REVIEW_STATUS: {
|
|
14
|
+
return action.payload;
|
|
15
|
+
}
|
|
16
|
+
default:
|
|
17
|
+
return state;
|
|
18
|
+
}
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
// -----------------------------------------------------------------------------
|
|
22
|
+
|
|
23
|
+
export default reducer;
|