From cc029cfbc1333eb8bbf3610718c3e8640a201467 Mon Sep 17 00:00:00 2001 From: shmck Date: Sun, 5 Jul 2020 20:25:58 -0700 Subject: [PATCH 1/9] setup reset script Signed-off-by: shmck --- src/channel/index.ts | 3 +++ web-app/src/services/state/actions/editor.ts | 5 +++++ web-app/src/services/state/machine.ts | 3 +++ 3 files changed, 11 insertions(+) diff --git a/src/channel/index.ts b/src/channel/index.ts index 00e9f202..7e46e0e0 100644 --- a/src/channel/index.ts +++ b/src/channel/index.ts @@ -319,6 +319,9 @@ class Channel implements Channel { case 'EDITOR_RUN_TEST': vscode.commands.executeCommand(COMMANDS.RUN_TEST, action?.payload) return + case 'EDITOR_RUN_RESET_SCRIPT': + // if tutorial.config.reset.command, run it + return default: logger(`No match for action type: ${actionType}`) return diff --git a/web-app/src/services/state/actions/editor.ts b/web-app/src/services/state/actions/editor.ts index da0c09e3..befbac26 100644 --- a/web-app/src/services/state/actions/editor.ts +++ b/web-app/src/services/state/actions/editor.ts @@ -117,4 +117,9 @@ export default (editorSend: any) => ({ payload: { position: context.position }, }) }, + runResetScript() { + editorSend({ + type: 'EDITOR_RUN_RESET_SCRIPT', + }) + }, }) diff --git a/web-app/src/services/state/machine.ts b/web-app/src/services/state/machine.ts index d04c7918..453e977a 100644 --- a/web-app/src/services/state/machine.ts +++ b/web-app/src/services/state/machine.ts @@ -168,6 +168,9 @@ export const createMachine = (options: any) => { RUN_TEST: { actions: ['runTest'], }, + RESET_SCRIPT: { + actions: ['runResetScript'], + }, }, }, TestRunning: { From 714879613ff586ea72b3469709f248cdac34d7cb Mon Sep 17 00:00:00 2001 From: shmck Date: Tue, 7 Jul 2020 19:27:30 -0700 Subject: [PATCH 2/9] trigger on reset command Signed-off-by: shmck --- src/channel/index.ts | 11 ++++++++--- typings/tutorial.d.ts | 7 ++++++- 2 files changed, 14 insertions(+), 4 deletions(-) diff --git a/src/channel/index.ts b/src/channel/index.ts index 7e46e0e0..5786bc27 100644 --- a/src/channel/index.ts +++ b/src/channel/index.ts @@ -8,14 +8,15 @@ import saveCommit from '../actions/saveCommit' import { setupActions, solutionActions } from '../actions/setupActions' import tutorialConfig from '../actions/tutorialConfig' import { COMMANDS } from '../editor/commands' -import logger from '../services/logger' import Context from './context' -import { version, compareVersions } from '../services/dependencies' -import { openWorkspace, checkWorkspaceEmpty } from '../services/workspace' import { readFile } from 'fs' import { join } from 'path' import { promisify } from 'util' +import logger from '../services/logger' +import { version, compareVersions } from '../services/dependencies' +import { openWorkspace, checkWorkspaceEmpty } from '../services/workspace' import { showOutput } from '../services/testRunner/output' +import { exec } from '../services/node' import { WORKSPACE_ROOT, TUTORIAL_URL } from '../environment' const readFileAsync = promisify(readFile) @@ -320,7 +321,11 @@ class Channel implements Channel { vscode.commands.executeCommand(COMMANDS.RUN_TEST, action?.payload) return case 'EDITOR_RUN_RESET_SCRIPT': + const tutorial: TT.Tutorial | null = this.context.tutorial.get() // if tutorial.config.reset.command, run it + if (tutorial?.config?.reset?.command) { + await exec({ command: tutorial.config.reset.command }) + } return default: logger(`No match for action type: ${actionType}`) diff --git a/typings/tutorial.d.ts b/typings/tutorial.d.ts index 8dc5d6b3..6dac2b9d 100644 --- a/typings/tutorial.d.ts +++ b/typings/tutorial.d.ts @@ -2,11 +2,16 @@ import { ProgressStatus } from './index' export type Maybe = T | null +export type ConfigReset = { + command?: string +} + export type TutorialConfig = { - appVersions: TutorialAppVersions + appVersions?: TutorialAppVersions testRunner: TestRunnerConfig repo: TutorialRepo dependencies?: TutorialDependency[] + reset?: ConfigReset } /** Logical groupings of tasks */ From 72771c410c5da6a60864731361312c5518a43d9a Mon Sep 17 00:00:00 2001 From: shmck Date: Sat, 11 Jul 2020 09:05:34 -0700 Subject: [PATCH 3/9] setup last pass commit hash Signed-off-by: shmck --- src/channel/index.ts | 4 ++++ src/services/git/lastPass.ts | 12 ++++++++++++ 2 files changed, 16 insertions(+) create mode 100644 src/services/git/lastPass.ts diff --git a/src/channel/index.ts b/src/channel/index.ts index 5786bc27..29649369 100644 --- a/src/channel/index.ts +++ b/src/channel/index.ts @@ -327,6 +327,10 @@ class Channel implements Channel { await exec({ command: tutorial.config.reset.command }) } return + case 'EDITOR_RUN_RESET_TO_LAST_PASS': + return + case 'EDITOR_RUN_RESET_TO_TIMELINE': + return default: logger(`No match for action type: ${actionType}`) return diff --git a/src/services/git/lastPass.ts b/src/services/git/lastPass.ts new file mode 100644 index 00000000..8a2324cf --- /dev/null +++ b/src/services/git/lastPass.ts @@ -0,0 +1,12 @@ +import * as TT from '../../../typings/tutorial' +import * as T from '../../../typings' + +const getLastPassCommitHash = (position: T.Position, levels: TT.Level[]) => { + // get previous position + const { levelId, stepId } = position + + // get solution hash if it exists + // else get setup hash +} + +export default getLastPassCommitHash From fec562f7a21902159c076853890c2fed25dea9c7 Mon Sep 17 00:00:00 2001 From: shmck Date: Sun, 12 Jul 2020 11:10:01 -0700 Subject: [PATCH 4/9] cleanup stories Signed-off-by: shmck --- web-app/stories/Tests.stories.tsx | 2 +- web-app/stories/Tutorial.stories.tsx | 10 ---------- web-app/stories/utils/ApolloDecorator.tsx | 15 --------------- web-app/stories/utils/ProviderDecorator.tsx | 15 +++++++++++++++ web-app/stories/utils/SideBarDecorator.tsx | 7 ++++++- 5 files changed, 22 insertions(+), 27 deletions(-) delete mode 100644 web-app/stories/utils/ApolloDecorator.tsx create mode 100644 web-app/stories/utils/ProviderDecorator.tsx diff --git a/web-app/stories/Tests.stories.tsx b/web-app/stories/Tests.stories.tsx index bdba73d5..220bbb43 100644 --- a/web-app/stories/Tests.stories.tsx +++ b/web-app/stories/Tests.stories.tsx @@ -5,4 +5,4 @@ import SideBarDecorator from './utils/SideBarDecorator' storiesOf('Test Message', module) .addDecorator(SideBarDecorator) - .add('Fail', () => ) + .add('Fail', () => ) diff --git a/web-app/stories/Tutorial.stories.tsx b/web-app/stories/Tutorial.stories.tsx index ff5be851..4854a57e 100644 --- a/web-app/stories/Tutorial.stories.tsx +++ b/web-app/stories/Tutorial.stories.tsx @@ -56,7 +56,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'COMPLETE', hints: ['First Hint', 'Second Hint'], }, { @@ -68,7 +67,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'COMPLETE', }, { id: '1.3', @@ -79,7 +77,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'COMPLETE', }, ], }, @@ -100,7 +97,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'COMPLETE', hints: ['first hint', 'second hint'], }, { @@ -112,7 +108,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'ACTIVE', hints: ['another hint', 'another other hint'], }, { @@ -124,7 +119,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'INCOMPLETE', }, ], }, @@ -134,7 +128,6 @@ const context: Partial = { summary: 'A summary of the 3rd level', content: 'Should support markdown test\n ```js\nvar a = 1\n```\nwhew it works!', setup: null, - status: 'INCOMPLETE', steps: [ { id: '3.1', @@ -145,7 +138,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'INCOMPLETE', }, { id: '3.2', @@ -156,7 +148,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'INCOMPLETE', }, { id: '3.3', @@ -167,7 +158,6 @@ const context: Partial = { solution: { commits: ['hijklmn'], }, - status: 'INCOMPLETE', }, ], }, diff --git a/web-app/stories/utils/ApolloDecorator.tsx b/web-app/stories/utils/ApolloDecorator.tsx deleted file mode 100644 index 90ab62f7..00000000 --- a/web-app/stories/utils/ApolloDecorator.tsx +++ /dev/null @@ -1,15 +0,0 @@ -import { ApolloProvider } from '@apollo/react-hooks' -import React, { Fragment } from 'react' -import client from '../../src/services/apollo' - -function StorybookProvider({ children }) { - return ( - - {children} - - ) -} - -export default (story) => { - return {story()} -} diff --git a/web-app/stories/utils/ProviderDecorator.tsx b/web-app/stories/utils/ProviderDecorator.tsx new file mode 100644 index 00000000..f6a2ca2a --- /dev/null +++ b/web-app/stories/utils/ProviderDecorator.tsx @@ -0,0 +1,15 @@ +import React, { Fragment } from 'react' +import { ConfigProvider } from '@alifd/next' +import enUS from '@alifd/next/lib/locale/en-us' + +export function Provider({ children }) { + return ( + + {children} + + ) +} + +export default (story) => { + return {story()} +} diff --git a/web-app/stories/utils/SideBarDecorator.tsx b/web-app/stories/utils/SideBarDecorator.tsx index 7001797d..318a6494 100644 --- a/web-app/stories/utils/SideBarDecorator.tsx +++ b/web-app/stories/utils/SideBarDecorator.tsx @@ -1,5 +1,6 @@ import * as React from 'react' import { css, jsx } from '@emotion/core' +import { Provider } from './ProviderDecorator' const styles = { container: { @@ -14,6 +15,10 @@ const styles = { }, } -const SideBarDecorator = (storyFn) =>
{storyFn()}
+const SideBarDecorator = (storyFn) => ( + +
{storyFn()}
+
+) export default SideBarDecorator From e4b3ff9393f0dd6ca3393991611175f89ac41aed Mon Sep 17 00:00:00 2001 From: shmck Date: Sun, 12 Jul 2020 11:10:16 -0700 Subject: [PATCH 5/9] add review ui Signed-off-by: shmck --- .../containers/Tutorial/components/Reset.tsx | 53 +++++++++++++++++++ web-app/src/containers/Tutorial/index.tsx | 11 +++- web-app/stories/Review.stories.tsx | 13 +---- 3 files changed, 63 insertions(+), 14 deletions(-) create mode 100644 web-app/src/containers/Tutorial/components/Reset.tsx diff --git a/web-app/src/containers/Tutorial/components/Reset.tsx b/web-app/src/containers/Tutorial/components/Reset.tsx new file mode 100644 index 00000000..249c0cd8 --- /dev/null +++ b/web-app/src/containers/Tutorial/components/Reset.tsx @@ -0,0 +1,53 @@ +import * as React from 'react' +import { Dialog } from '@alifd/next' +import Button from '../../../components/Button' + +interface Props { + onReset(): void +} + +const Reset = (props: Props) => { + const [modalState, setModalState] = React.useState<'none' | 'confirm' | 'progress'>('none') + + const onClose = () => { + setModalState('none') + } + + const onOk = () => { + setModalState('progress') + props.onReset() + return setTimeout(() => { + setModalState('none') + }, 3000) + } + + return ( + <> + + {/* TODO improve reset message */} + + Are you sure? + + + Reverting progress to an earlier commit... + + + ) +} + +export default Reset diff --git a/web-app/src/containers/Tutorial/index.tsx b/web-app/src/containers/Tutorial/index.tsx index baf1bfe7..daaf0f73 100644 --- a/web-app/src/containers/Tutorial/index.tsx +++ b/web-app/src/containers/Tutorial/index.tsx @@ -4,9 +4,10 @@ import * as selectors from '../../services/selectors' import SideMenu from './components/SideMenu' import Level from './components/Level' import Icon from '../../components/Icon' -import SettingsPage from './containers/Settings' +// import SettingsPage from './containers/Settings' import ReviewPage from './containers/Review' import Button from '../../components/Button' +import Reset from './components/Reset' import ProcessMessages from '../../components/ProcessMessages' import TestMessage from '../../components/TestMessage' import { Progress } from '@alifd/next' @@ -100,6 +101,10 @@ const TutorialPage = (props: PageProps) => { props.send({ type: 'RUN_TEST' }) } + const onReset = (): void => { + // TODO + } + const [menuVisible, setMenuVisible] = React.useState(false) const [page, setPage] = React.useState<'level' | 'settings' | 'review'>('level') @@ -149,7 +154,9 @@ const TutorialPage = (props: PageProps) => { )} {/* Center */} -
+
+ +
{/* Right */}
diff --git a/web-app/stories/Review.stories.tsx b/web-app/stories/Review.stories.tsx index b2d77502..51660ec0 100644 --- a/web-app/stories/Review.stories.tsx +++ b/web-app/stories/Review.stories.tsx @@ -142,16 +142,5 @@ storiesOf('Review', module) .addDecorator(SideBarDecorator) .addDecorator(withKnobs) .add('Example', () => { - const progress = { - levels: { - '1': true, - }, - steps: { - '1.1': true, - '1.2': true, - '1.3': true, - '2.1': true, - }, - } - return + return }) From 605bafa0276bf130363c44c2ffb19fb36cf3b014 Mon Sep 17 00:00:00 2001 From: shmck Date: Sun, 12 Jul 2020 11:20:32 -0700 Subject: [PATCH 6/9] update reset message Signed-off-by: shmck --- web-app/src/containers/Tutorial/components/Reset.tsx | 7 +++++-- web-app/src/containers/Tutorial/index.tsx | 2 +- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/web-app/src/containers/Tutorial/components/Reset.tsx b/web-app/src/containers/Tutorial/components/Reset.tsx index 249c0cd8..7c9f9511 100644 --- a/web-app/src/containers/Tutorial/components/Reset.tsx +++ b/web-app/src/containers/Tutorial/components/Reset.tsx @@ -1,6 +1,7 @@ import * as React from 'react' import { Dialog } from '@alifd/next' import Button from '../../../components/Button' +import Markdown from '../../../components/Markdown' interface Props { onReset(): void @@ -26,7 +27,6 @@ const Reset = (props: Props) => { - {/* TODO improve reset message */} { onClose={onClose} footerActions={['ok', 'cancel']} > - Are you sure? + + {`Are you sure you want to reset your progress? +Resetting progress will remove the commits you have made and replace them with the tutorial commit timeline. Your code may look different after resetting.`} + { )} {/* Center */} -
+
From a1a661f9bb82db9852c0a39d35f59b8b3139f3d9 Mon Sep 17 00:00:00 2001 From: shmck Date: Sun, 12 Jul 2020 11:40:05 -0700 Subject: [PATCH 7/9] add footer button styles, temp hide reset Signed-off-by: shmck --- .../containers/Tutorial/components/Reset.tsx | 3 ++- web-app/src/containers/Tutorial/index.tsx | 20 +++++++++---------- 2 files changed, 12 insertions(+), 11 deletions(-) diff --git a/web-app/src/containers/Tutorial/components/Reset.tsx b/web-app/src/containers/Tutorial/components/Reset.tsx index 7c9f9511..33a34207 100644 --- a/web-app/src/containers/Tutorial/components/Reset.tsx +++ b/web-app/src/containers/Tutorial/components/Reset.tsx @@ -4,6 +4,7 @@ import Button from '../../../components/Button' import Markdown from '../../../components/Markdown' interface Props { + disabled: boolean onReset(): void } @@ -24,7 +25,7 @@ const Reset = (props: Props) => { return ( <> - {
)} {/* Left */} - {DISPLAY_RUN_TEST_BUTTON && level.status !== 'COMPLETE' ? ( - - ) : ( -
- )} +
+ {DISPLAY_RUN_TEST_BUTTON && level.status !== 'COMPLETE' ? ( + + ) : null} +
{/* Center */} -
- +
+ {/* 0} /> */}
{/* Right */} -
+
{level.status === 'COMPLETE' || !level.steps.length ? ( ) : ( - { - return ( - - {stepIndex} of {level.steps.length} - - ) - }} - /> + )}
From 98c7c50ee27d9d2b0fc7b19db949788665a8f9a3 Mon Sep 17 00:00:00 2001 From: shmck Date: Sun, 12 Jul 2020 12:06:21 -0700 Subject: [PATCH 9/9] media query on step progress Signed-off-by: shmck --- web-app/package.json | 1 + .../containers/Tutorial/components/Reset.tsx | 2 +- .../Tutorial/components/StepProgress.tsx | 33 +++++++++++-------- web-app/yarn.lock | 5 +++ 4 files changed, 27 insertions(+), 14 deletions(-) diff --git a/web-app/package.json b/web-app/package.json index ee9be258..afb5e63e 100644 --- a/web-app/package.json +++ b/web-app/package.json @@ -39,6 +39,7 @@ "react-addons-css-transition-group": "^15.6.2", "react-dom": "^16.13.1", "reselect": "^4.0.0", + "use-media": "^1.4.0", "xstate": "^4.11.0" }, "devDependencies": { diff --git a/web-app/src/containers/Tutorial/components/Reset.tsx b/web-app/src/containers/Tutorial/components/Reset.tsx index 33a34207..1bf34dfc 100644 --- a/web-app/src/containers/Tutorial/components/Reset.tsx +++ b/web-app/src/containers/Tutorial/components/Reset.tsx @@ -25,7 +25,7 @@ const Reset = (props: Props) => { return ( <> - { {props.current} of {props.max} ) - return ( - { - return Text - }} - /> - ) + + const isWide = useMedia({ minWidth: '340px' }) + + if (isWide) { + return ( + { + return Text + }} + /> + ) + } + return
{Text}
} export default StepProgress diff --git a/web-app/yarn.lock b/web-app/yarn.lock index 10f4dbb1..4578b7e2 100644 --- a/web-app/yarn.lock +++ b/web-app/yarn.lock @@ -13431,6 +13431,11 @@ use-callback-ref@^1.2.1: resolved "https://registry.yarnpkg.com/use-callback-ref/-/use-callback-ref-1.2.3.tgz#9f939dfb5740807bbf9dd79cdd4e99d27e827756" integrity sha512-DPBPh1i2adCZoIArRlTuKRy7yue7QogtEnfv0AKrWsY+GA+4EKe37zhRDouNnyWMoNQFYZZRF+2dLHsWE4YvJA== +use-media@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/use-media/-/use-media-1.4.0.tgz#e777bf1f382a7aacabbd1f9ce3da2b62e58b2a98" + integrity sha512-XsgyUAf3nhzZmEfhc5MqLHwyaPjs78bgytpVJ/xDl0TF4Bptf3vEpBNBBT/EIKOmsOc8UbuECq3mrP3mt1QANA== + use-sidecar@^1.0.1: version "1.0.2" resolved "https://registry.yarnpkg.com/use-sidecar/-/use-sidecar-1.0.2.tgz#e72f582a75842f7de4ef8becd6235a4720ad8af6"