Skip to content

Commit 02c4db3

Browse files
refactor: move steps into separate files
1 parent 24a8c97 commit 02c4db3

5 files changed

Lines changed: 106 additions & 83 deletions

File tree

source/app.tsx

Lines changed: 22 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1,48 +1,38 @@
1-
import React, { useEffect, useState, useMemo } from 'react'
2-
import CloneRepo from './import/CloneRepo.js'
3-
import ProjectName from './import/ProjectName.js'
4-
import Step1 from './import/Step1.js'
51
import { Box } from 'ink'
6-
import { validateName, isAnswerConfirmed } from './import/utils.js'
72
import Divider from 'ink-divider'
3+
import React, { useState } from 'react'
4+
import Step1 from './import/Step1.js'
5+
import Step2 from './import/Step2.js'
6+
import { canShowStep } from './import/utils.js'
87

98
const App = () => {
109
const [projectName, setProjectName] = useState<string>('')
11-
const [errorMessage, setErrormessage] = useState<string | undefined>()
1210
const [step, setStep] = useState(1)
13-
const isProjectNameSet = useMemo(
14-
() => isAnswerConfirmed(projectName, errorMessage),
15-
[projectName, errorMessage],
16-
)
17-
18-
useEffect(() => {
19-
setErrormessage(validateName(projectName))
20-
}, [projectName])
2111

2212
const finishStep = () => setStep(step + 1)
2313

24-
const canShowStep = (currentStep: number) => {
25-
return step > currentStep - 1
26-
}
27-
2814
return (
29-
<Box flexDirection={'column'} rowGap={1}>
30-
<ProjectName
31-
errorMessage={errorMessage}
15+
<Box
16+
flexDirection={'column'}
17+
rowGap={1}
18+
>
19+
<Step1
3220
onSubmit={setProjectName}
21+
onCompletion={finishStep}
3322
projectName={projectName}
3423
/>
35-
{isProjectNameSet && (
36-
<>
37-
{/* Step 1 */}
38-
{canShowStep(1) && <Step1 projectName={projectName} onCompletion={finishStep} />}
39-
{/* Step 2 */}
40-
{canShowStep(2) && (
41-
<>
42-
<Divider titlePadding={2} titleColor={'whiteBright'} title={'Installation setup'} />
43-
</>
44-
)}
45-
</>
24+
{canShowStep(step, 2) && (
25+
<Step2
26+
projectName={projectName}
27+
onCompletion={finishStep}
28+
/>
29+
)}
30+
{canShowStep(step, 3) && (
31+
<Divider
32+
titlePadding={2}
33+
titleColor={'whiteBright'}
34+
title={'Installation setup'}
35+
/>
4636
)}
4737
</Box>
4838
)

source/import/CloneRepo.tsx

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
import { join } from 'node:path'
2-
import { repoUrl } from './config.js'
3-
import React, { useState, type FC } from 'react'
4-
import { Text, Box } from 'ink'
5-
import { Script, Spawn } from 'ink-spawn'
62
import * as process from 'node:process'
3+
import { Box, Text } from 'ink'
4+
import { Script, Spawn } from 'ink-spawn'
5+
import React, { useState, type FC } from 'react'
6+
import { repoUrl } from './config.js'
7+
import { canShowStep } from './utils.js'
78

89
interface Props {
910
projectName: string
@@ -19,14 +20,13 @@ const CloneRepo: FC<Props> = ({ projectName, onCompletion }) => {
1920

2021
const finishStep = () => setStep(step + 1)
2122

22-
const canShowStep = (currentStep: number) => {
23-
return step > currentStep - 1
24-
}
25-
2623
return (
27-
<Box flexDirection={'column'} gap={0}>
24+
<Box
25+
flexDirection={'column'}
26+
gap={0}
27+
>
2828
<Script>
29-
{canShowStep(1) && (
29+
{canShowStep(step, 1) && (
3030
<>
3131
<Text color={'whiteBright'}>Cloning dAppBooster in </Text>
3232
<Text italic>{projectName}</Text>
@@ -44,7 +44,7 @@ const CloneRepo: FC<Props> = ({ projectName, onCompletion }) => {
4444
command="git"
4545
args={['clone', '--depth', '1', '--no-checkout', repoUrl, projectName]}
4646
/>
47-
{canShowStep(2) && <Text color={'whiteBright'}>Fetching tags</Text>}
47+
{canShowStep(step, 2) && <Text color={'whiteBright'}>Fetching tags</Text>}
4848
<Spawn
4949
shell
5050
cwd={projectDir}
@@ -58,7 +58,7 @@ const CloneRepo: FC<Props> = ({ projectName, onCompletion }) => {
5858
finishStep()
5959
}}
6060
/>
61-
{canShowStep(3) && <Text color={'whiteBright'}>Checking out latest tag</Text>}
61+
{canShowStep(step, 3) && <Text color={'whiteBright'}>Checking out latest tag</Text>}
6262
<Spawn
6363
shell
6464
cwd={projectDir}
@@ -70,7 +70,7 @@ const CloneRepo: FC<Props> = ({ projectName, onCompletion }) => {
7070
finishStep()
7171
}}
7272
/>
73-
{canShowStep(4) && <Text color={'whiteBright'}>Removing .git folder</Text>}
73+
{canShowStep(step, 4) && <Text color={'whiteBright'}>Removing .git folder</Text>}
7474
<Spawn
7575
shell
7676
cwd={projectDir}
@@ -82,7 +82,7 @@ const CloneRepo: FC<Props> = ({ projectName, onCompletion }) => {
8282
finishStep()
8383
}}
8484
/>
85-
{canShowStep(5) && <Text color={'whiteBright'}>Initializing Git repository</Text>}
85+
{canShowStep(step, 5) && <Text color={'whiteBright'}>Initializing Git repository</Text>}
8686
<Spawn
8787
shell
8888
cwd={projectDir}

source/import/ProjectName.tsx

Lines changed: 0 additions & 27 deletions
This file was deleted.

source/import/Step1.tsx

Lines changed: 46 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,53 @@
1-
import Divider from 'ink-divider'
2-
import CloneRepo from './CloneRepo.js'
3-
import React, { type FC } from 'react'
1+
import BigText from 'ink-big-text'
2+
import Gradient from 'ink-gradient'
3+
import React, { type FC, useMemo, useCallback } from 'react'
4+
import Ask from './Ask.js'
5+
import { isValidName } from './utils.js'
46

57
interface Props {
6-
projectName: string
78
onCompletion: () => void
9+
onSubmit: (value: string) => void
10+
projectName: string
811
}
912

10-
const Step1: FC<Props> = ({ projectName, onCompletion }) => (
11-
<>
12-
<Divider titlePadding={2} titleColor={'whiteBright'} title={`Cloning "${projectName}"`} />
13-
<CloneRepo projectName={projectName} onCompletion={onCompletion} />
14-
</>
15-
)
13+
const Step1: FC<Props> = ({ projectName, onSubmit, onCompletion }) => {
14+
const validateName = useCallback((name: string): string => {
15+
if (name.length > 0 && !isValidName(name)) return 'Not a valid name!'
16+
17+
return ''
18+
}, [])
19+
20+
const errorMessage = useMemo(() => validateName(projectName), [projectName, validateName])
21+
22+
const handleSubmit = useCallback(
23+
(name: string) => {
24+
onSubmit(name)
25+
26+
if (validateName(name) === '') {
27+
onCompletion()
28+
}
29+
},
30+
[onSubmit, onCompletion, validateName],
31+
)
32+
33+
return (
34+
<>
35+
<Gradient colors={['#ff438c', '#bb1d79', '#8b46a4', '#6a2581']}>
36+
<BigText
37+
lineHeight={1}
38+
font={'chrome'}
39+
text="dAppBooster"
40+
/>
41+
</Gradient>
42+
<Ask
43+
answer={projectName}
44+
errorMessage={errorMessage}
45+
onSubmit={handleSubmit}
46+
question={'Project name?'}
47+
tip={'Letters (a–z, A–Z), numbers (0–9), hyphens (-), and underscores (_) are allowed.'}
48+
/>
49+
</>
50+
)
51+
}
1652

1753
export default Step1

source/import/Step2.tsx

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import Divider from 'ink-divider'
2+
import React, {type FC} from 'react'
3+
import CloneRepo from './CloneRepo.js'
4+
5+
interface Props {
6+
projectName: string
7+
onCompletion: () => void
8+
}
9+
10+
const Step2: FC<Props> = ({projectName, onCompletion}) => (
11+
<>
12+
<Divider
13+
titlePadding={2}
14+
titleColor={'whiteBright'}
15+
title={`Cloning "${projectName}"`}
16+
/>
17+
<CloneRepo
18+
projectName={projectName}
19+
onCompletion={onCompletion}
20+
/>
21+
</>
22+
)
23+
24+
export default Step2

0 commit comments

Comments
 (0)