From 8d5702a70bffdfe9cd431c96254a026d9b8c78a4 Mon Sep 17 00:00:00 2001 From: shmck Date: Thu, 2 Apr 2020 19:42:49 -0700 Subject: [PATCH 1/4] setup tutorial file json loader --- .../SelectTutorial/SelectTutorialForm.tsx | 4 +- .../SelectTutorial/forms/TutorialFile.tsx | 40 +++++++++++++++++++ .../SelectTutorial/forms/TutorialUrl.tsx | 2 +- 3 files changed, 44 insertions(+), 2 deletions(-) create mode 100644 web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx diff --git a/web-app/src/containers/SelectTutorial/SelectTutorialForm.tsx b/web-app/src/containers/SelectTutorial/SelectTutorialForm.tsx index 4e4b568e..35eb6bf8 100644 --- a/web-app/src/containers/SelectTutorial/SelectTutorialForm.tsx +++ b/web-app/src/containers/SelectTutorial/SelectTutorialForm.tsx @@ -2,6 +2,7 @@ import * as React from 'react' import { Radio } from '@alifd/next' import TutorialSelect from './forms/TutorialSelect' import TutorialUrl from './forms/TutorialUrl' +import TutorialFile from './forms/TutorialFile' const styles = { formWrapper: { @@ -30,12 +31,13 @@ const SelectTutorialForm = (props: Props) => { > List URL - {/* File */} + File

{props.tab === 'list' && } {props.tab === 'url' && } + {props.tab === 'file' && } ) } diff --git a/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx b/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx new file mode 100644 index 00000000..045cc50d --- /dev/null +++ b/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx @@ -0,0 +1,40 @@ +import * as React from 'react' +import { Form } from '@alifd/next' + +const FormItem = Form.Item + +interface Props { + onTutorialLoad(url: string): void +} + +const TutorialFile = (props: Props) => { + const [json, setJson] = React.useState(null) + + const onChange = (evt: any) => { + const files = evt.target.files + + if (!files.length) { + alert('No file select') + return + } + const uploadedFile = files[0] + const reader = new FileReader() + reader.onload = (e: any) => { + // TODO: handle errors from bad JSON + const fileJson: JSON = JSON.parse(e.target.result) + setJson(fileJson) + } + reader.readAsText(uploadedFile) + } + + return ( +
+ + + +    +
+ ) +} + +export default TutorialFile diff --git a/web-app/src/containers/SelectTutorial/forms/TutorialUrl.tsx b/web-app/src/containers/SelectTutorial/forms/TutorialUrl.tsx index f9727261..9693f3bc 100644 --- a/web-app/src/containers/SelectTutorial/forms/TutorialUrl.tsx +++ b/web-app/src/containers/SelectTutorial/forms/TutorialUrl.tsx @@ -1,5 +1,5 @@ import * as React from 'react' -import { Button, Form, Radio, Input } from '@alifd/next' +import { Button, Form, Input } from '@alifd/next' const FormItem = Form.Item From f85afd1342a0c7d90f3e304a8df14b6ffdf24155 Mon Sep 17 00:00:00 2001 From: shmck Date: Thu, 2 Apr 2020 19:58:41 -0700 Subject: [PATCH 2/4] move load from url into its own function --- .../SelectTutorial/LoadTutorialSummary.tsx | 15 +++-------- .../src/containers/SelectTutorial/index.tsx | 25 +++++++++++++++++-- 2 files changed, 26 insertions(+), 14 deletions(-) diff --git a/web-app/src/containers/SelectTutorial/LoadTutorialSummary.tsx b/web-app/src/containers/SelectTutorial/LoadTutorialSummary.tsx index 898deceb..75a396dc 100644 --- a/web-app/src/containers/SelectTutorial/LoadTutorialSummary.tsx +++ b/web-app/src/containers/SelectTutorial/LoadTutorialSummary.tsx @@ -1,13 +1,11 @@ import * as React from 'react' import useFetch from '../../services/hooks/useFetch' import * as TT from 'typings/tutorial' -import TutorialOverview from '../../components/TutorialOverview' import Loading from '../Loading' interface Props { url: string - send: any - onClear(): void + onSetDataFromUrl(data: TT.Tutorial): void } const LoadTutorialSummary = (props: Props) => { @@ -22,15 +20,8 @@ const LoadTutorialSummary = (props: Props) => { if (!data) { return
No data returned for tutorial
} - const onNext = () => { - props.send({ - type: 'TUTORIAL_START', - payload: { - tutorial: data, - }, - }) - } - return + props.onSetDataFromUrl(data) + return null } export default LoadTutorialSummary diff --git a/web-app/src/containers/SelectTutorial/index.tsx b/web-app/src/containers/SelectTutorial/index.tsx index 34e1155c..f1a56cf8 100644 --- a/web-app/src/containers/SelectTutorial/index.tsx +++ b/web-app/src/containers/SelectTutorial/index.tsx @@ -1,5 +1,7 @@ +import * as TT from 'typings/tutorial' import * as React from 'react' import SelectTutorialForm from './SelectTutorialForm' +import TutorialOverview from '../../components/TutorialOverview' import LoadTutorialSummary from './LoadTutorialSummary' const styles = { @@ -19,17 +21,36 @@ interface Props { } const SelectTutorialPage = (props: Props) => { - const [page, setPage] = React.useState<'form' | 'summary'>('form') + const [data, setData] = React.useState() + const [page, setPage] = React.useState<'form' | 'loading' | 'summary'>('form') const [tab, setTab] = React.useState<'list' | 'url'>('list') const [url, setUrl] = React.useState(null) + + const onNext = () => { + props.send({ + type: 'TUTORIAL_START', + payload: { + tutorial: data, + }, + }) + } const onTutorialLoad = (url: string) => { setUrl(url) + setPage('loading') + } + const onSetDataFromUrl = (d: TT.Tutorial) => { + setData(d) setPage('summary') } + const onClear = () => { + setData(null) + setPage('form') + } return (
{page === 'form' && } - {page === 'summary' && url && setPage('form')} />} + {page === 'loading' && url && } + {page === 'summary' && data && }
) } From b4dff54e0e3f4b02b805cf84434c7def675690c2 Mon Sep 17 00:00:00 2001 From: shmck Date: Thu, 2 Apr 2020 20:04:55 -0700 Subject: [PATCH 3/4] load json file --- .../SelectTutorial/LoadTutorialSummary.tsx | 4 ++-- .../SelectTutorial/SelectTutorialForm.tsx | 10 ++++++---- .../SelectTutorial/forms/TutorialFile.tsx | 13 ++++++------- web-app/src/containers/SelectTutorial/index.tsx | 16 ++++++++++++---- 4 files changed, 26 insertions(+), 17 deletions(-) diff --git a/web-app/src/containers/SelectTutorial/LoadTutorialSummary.tsx b/web-app/src/containers/SelectTutorial/LoadTutorialSummary.tsx index 75a396dc..87cf0118 100644 --- a/web-app/src/containers/SelectTutorial/LoadTutorialSummary.tsx +++ b/web-app/src/containers/SelectTutorial/LoadTutorialSummary.tsx @@ -5,7 +5,7 @@ import Loading from '../Loading' interface Props { url: string - onSetDataFromUrl(data: TT.Tutorial): void + onLoadSummary(data: TT.Tutorial): void } const LoadTutorialSummary = (props: Props) => { @@ -20,7 +20,7 @@ const LoadTutorialSummary = (props: Props) => { if (!data) { return
No data returned for tutorial
} - props.onSetDataFromUrl(data) + props.onLoadSummary(data) return null } diff --git a/web-app/src/containers/SelectTutorial/SelectTutorialForm.tsx b/web-app/src/containers/SelectTutorial/SelectTutorialForm.tsx index 35eb6bf8..b65972f2 100644 --- a/web-app/src/containers/SelectTutorial/SelectTutorialForm.tsx +++ b/web-app/src/containers/SelectTutorial/SelectTutorialForm.tsx @@ -1,3 +1,4 @@ +import * as TT from 'typings/tutorial' import * as React from 'react' import { Radio } from '@alifd/next' import TutorialSelect from './forms/TutorialSelect' @@ -16,7 +17,8 @@ interface Props { tab: string setTab(tab: 'list' | 'url'): void url: string | null - onTutorialLoad(url: string): void + onTutorialLoadFromUrl(url: string): void + onLoadSummary(data: TT.Tutorial | null): void } const SelectTutorialForm = (props: Props) => { @@ -35,9 +37,9 @@ const SelectTutorialForm = (props: Props) => {

- {props.tab === 'list' && } - {props.tab === 'url' && } - {props.tab === 'file' && } + {props.tab === 'list' && } + {props.tab === 'url' && } + {props.tab === 'file' && } ) } diff --git a/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx b/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx index 045cc50d..510e8dda 100644 --- a/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx +++ b/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx @@ -1,15 +1,14 @@ import * as React from 'react' +import * as TT from 'typings/tutorial' import { Form } from '@alifd/next' const FormItem = Form.Item interface Props { - onTutorialLoad(url: string): void + onLoadSummary(data: TT.Tutorial): void } const TutorialFile = (props: Props) => { - const [json, setJson] = React.useState(null) - const onChange = (evt: any) => { const files = evt.target.files @@ -20,9 +19,9 @@ const TutorialFile = (props: Props) => { const uploadedFile = files[0] const reader = new FileReader() reader.onload = (e: any) => { - // TODO: handle errors from bad JSON - const fileJson: JSON = JSON.parse(e.target.result) - setJson(fileJson) + // TODO: handle errors from invalid JSON + const fileJson: TT.Tutorial = JSON.parse(e.target.result) + props.onLoadSummary(fileJson) } reader.readAsText(uploadedFile) } @@ -32,7 +31,7 @@ const TutorialFile = (props: Props) => { -    +
) } diff --git a/web-app/src/containers/SelectTutorial/index.tsx b/web-app/src/containers/SelectTutorial/index.tsx index f1a56cf8..ee4bafae 100644 --- a/web-app/src/containers/SelectTutorial/index.tsx +++ b/web-app/src/containers/SelectTutorial/index.tsx @@ -34,11 +34,11 @@ const SelectTutorialPage = (props: Props) => { }, }) } - const onTutorialLoad = (url: string) => { + const onTutorialLoadFromUrl = (url: string) => { setUrl(url) setPage('loading') } - const onSetDataFromUrl = (d: TT.Tutorial) => { + const onLoadSummary = (d: TT.Tutorial) => { setData(d) setPage('summary') } @@ -48,8 +48,16 @@ const SelectTutorialPage = (props: Props) => { } return (
- {page === 'form' && } - {page === 'loading' && url && } + {page === 'form' && ( + + )} + {page === 'loading' && url && } {page === 'summary' && data && }
) From a1f554b810c657dcce4d481960b38bda872184d4 Mon Sep 17 00:00:00 2001 From: shmck Date: Thu, 2 Apr 2020 20:36:11 -0700 Subject: [PATCH 4/4] fix default chrome bug with upload file --- .../SelectTutorial/forms/TutorialFile.tsx | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) diff --git a/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx b/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx index 510e8dda..da257446 100644 --- a/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx +++ b/web-app/src/containers/SelectTutorial/forms/TutorialFile.tsx @@ -8,8 +8,20 @@ interface Props { onLoadSummary(data: TT.Tutorial): void } +const styles = { + uploadFileButton: { + padding: '0.3rem 0.5rem', + outline: '1px dotted rgb(51, 51, 51)', + borderRadius: '0.2rem', + fontWeight: 400, + fontFamily: + '-apple-system, system-ui, "Segoe UI", Roboto, Oxygen, Ubuntu, Cantarell, "Fira Sans", "Droid Sans", "Helvetica Neue", sans-serif;', + }, +} + const TutorialFile = (props: Props) => { const onChange = (evt: any) => { + evt.preventDefault() const files = evt.target.files if (!files.length) { @@ -29,7 +41,12 @@ const TutorialFile = (props: Props) => { return (
- +
+ +