-
Notifications
You must be signed in to change notification settings - Fork 361
/
create.go
164 lines (132 loc) · 4.2 KB
/
create.go
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
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
package samples
import (
"context"
"fmt"
"os"
"os/signal"
log "github.com/sirupsen/logrus"
"github.com/spf13/afero"
"gopkg.in/src-d/go-git.v4"
)
// CreationStatus is the current step in the sample creation routine
type CreationStatus int
const (
// WillInitialize means this sample will be initialized
WillInitialize CreationStatus = iota
// DidInitialize means this sample has finished initializing
DidInitialize
// WillCopy means the downloaded sample will be copied to the target path
WillCopy
// DidCopy means the downloaded sample has finished being copied to the target path
DidCopy
// WillConfigure means the .env of the sample will be configured with the user's Stripe account details
WillConfigure
// DidConfigure means the .env of the sample has finished being configured with the user's Stripe account details
DidConfigure
// Done means sample creation is complete
Done
)
// CreationResult is the return value sent over a channel
type CreationResult struct {
State CreationStatus
Path string
PostInstall string
Err error
}
// Create creates a sample at a destination with the selected integration, client language, and server language
func (sampleManager *SampleManager) Create(
ctx context.Context,
sampleName string,
selectedConfig *SelectedConfig,
destination string,
forceRefresh bool,
resultChan chan<- CreationResult,
) {
defer close(resultChan)
cacheFolder, err := sampleManager.appCacheFolder("samples-list")
if err != nil {
logger := log.Logger{
Out: os.Stdout,
}
logger.WithFields(log.Fields{
"prefix": "samples.create.cacheFolder",
"error": err,
}).Debug("Could not create cacheFolder for samples")
}
sampleManager.SampleLister = newCachedGithubSampleLister(sampleManager, sampleListGithubURL, cacheFolder)
exists, _ := afero.DirExists(sampleManager.Fs, destination)
if exists {
resultChan <- CreationResult{Err: fmt.Errorf("Path already exists for: %s", destination)}
return
}
if forceRefresh {
err := sampleManager.DeleteCache(sampleName)
if err != nil {
logger := log.Logger{
Out: os.Stdout,
}
logger.WithFields(log.Fields{
"prefix": "samples.create.forceRefresh",
"error": err,
}).Debug("Could not clear cache")
}
}
resultChan <- CreationResult{State: WillInitialize}
// Initialize the selected sample in the local cache directory.
// This will either clone or update the specified sample,
// depending on whether or not it's. Additionally, this
// identifies if the sample has multiple integrations and what
// languages it supports.
err = sampleManager.Initialize(sampleName)
if err != nil {
switch e := err.Error(); e {
case git.NoErrAlreadyUpToDate.Error():
// Repo is already up to date. This isn't a program
// error to continue as normal
break
case git.ErrRepositoryAlreadyExists.Error():
// If the repository already exists and we don't pull
// for some reason, that's fine as we can use the existing
// repository
break
default:
resultChan <- CreationResult{Err: err}
return
}
}
resultChan <- CreationResult{State: DidInitialize}
sampleManager.SelectedConfig = *selectedConfig
// Setup to intercept ctrl+c
c := make(chan os.Signal, 1)
signal.Notify(c, os.Interrupt)
go func() {
<-c
sampleManager.Cleanup(sampleName)
os.Exit(1)
}()
resultChan <- CreationResult{State: WillCopy}
// Create the target folder to copy the sample in to. We do
// this here in case any of the steps above fail, minimizing
// the change that we create a dangling empty folder
targetPath, err := sampleManager.MakeFolder(destination)
if err != nil {
resultChan <- CreationResult{Err: err}
return
}
// Perform the copy of the sample given the selected options
// from the selections above
err = sampleManager.Copy(targetPath)
if err != nil {
resultChan <- CreationResult{Err: err}
return
}
resultChan <- CreationResult{State: DidCopy}
resultChan <- CreationResult{State: WillConfigure}
err = sampleManager.WriteDotEnv(ctx, targetPath)
if err != nil {
resultChan <- CreationResult{Err: err}
return
}
resultChan <- CreationResult{State: DidConfigure}
resultChan <- CreationResult{State: Done, Path: targetPath, PostInstall: sampleManager.PostInstall()}
}