-
Notifications
You must be signed in to change notification settings - Fork 0
/
GitBranchSelectComponent.tsx
118 lines (109 loc) · 3.39 KB
/
GitBranchSelectComponent.tsx
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
import React from 'react'
import * as git from 'isomorphic-git'
import {AuthCallback, GitProgressEvent} from 'isomorphic-git'
import {v4 as uuidv4} from "uuid"
import Select from "./html/Select"
type GitOpts = {
http: git.HttpClient,
url: string,
corsProxy?: string,
author?: { name: string, email: string },
onAuth?: AuthCallback
}
class GitBranchSelectComponent extends React.Component<{
fs: git.PromiseFsClient,
gitOpts: GitOpts,
initialBranch?: string,
onSelect: (branch: string, repoDir: string) => void,
onAuthFailure: (url: string) => void,
onError: (error: Error) => void
}, {
progress: GitProgressEvent,
repoDir: string,
branches: string[],
selected: string
}> {
private cloneRepo() {
const {
fs,
gitOpts: {http, url, corsProxy, onAuth},
initialBranch,
onSelect,
onAuthFailure,
onError
} = this.props
const repoDir = '/' + uuidv4()
this.setState(() => ({}))
git.clone({
fs,
http,
dir: repoDir,
url,
onAuth,
onAuthFailure,
corsProxy,
noCheckout: true,
//singleBranch: true,
depth: 1,
onProgress: progress => {
this.setState(state => ({...state, progress: progress}))
}
}).then(() =>
git.getRemoteInfo({
http,
url,
onAuth,
onAuthFailure,
corsProxy
})
).then(remoteInfo =>
git.listBranches({
fs,
dir: repoDir,
remote: 'origin'
}).then(branches => {
const filteredBranches = branches.filter(e => e !== 'HEAD')
const mainBranch = remoteInfo.HEAD?.replace(/^refs\/heads\//, '')
const selected = initialBranch != null && filteredBranches.includes(initialBranch) ?
initialBranch :
mainBranch != null && filteredBranches.includes(mainBranch) ?
mainBranch :
filteredBranches[0]
this.setState(state => ({
...state,
repoDir: repoDir,
branches: filteredBranches,
selected: selected
}))
onSelect(selected, repoDir)
})
).catch(onError)
}
componentDidMount() {
this.cloneRepo()
}
componentDidUpdate(prevProps: any) {
const {fs, gitOpts} = this.props
if (JSON.stringify([fs, gitOpts]) !== JSON.stringify([prevProps.fs, prevProps.gitOpts])) {
this.cloneRepo()
}
}
componentWillUnmount() {
}
render() {
const {onSelect} = this.props
const {progress, repoDir, branches, selected} = this.state ?? {}
const loading = progress ? progress.phase + '...' : 'Loading...'
return <Select
label="Branch"
items={branches ?? [loading]}
disabled={branches == null}
selected={selected}
onSelect={branch => {
this.setState(state => ({...state, selected: branch}))
onSelect(branch, repoDir)
}}/>
}
}
export default GitBranchSelectComponent
export type {GitOpts}