blob: 251a37934e60c4eeac05933be5d746fc0c588aa4 [file] [log] [blame]
gio0eaf2712024-04-14 13:08:46 +04001package welcome
2
3import (
4 "encoding/json"
5 "fmt"
6 "io"
7 "net/http"
8 "strings"
9 "time"
10
11 "github.com/giolekva/pcloud/core/installer"
12 "github.com/giolekva/pcloud/core/installer/soft"
13)
14
15type DodoAppServer struct {
16 port int
17 sshKey string
18 client soft.Client
19 namespace string
20 env installer.EnvConfig
giof8843412024-05-22 16:38:05 +040021 jc installer.JobCreator
gio0eaf2712024-04-14 13:08:46 +040022 workers map[string]struct{}
23}
24
25func NewDodoAppServer(
26 port int,
27 sshKey string,
28 client soft.Client,
29 namespace string,
giof8843412024-05-22 16:38:05 +040030 jc installer.JobCreator,
gio0eaf2712024-04-14 13:08:46 +040031 env installer.EnvConfig,
32) *DodoAppServer {
33 return &DodoAppServer{
34 port,
35 sshKey,
36 client,
37 namespace,
38 env,
giof8843412024-05-22 16:38:05 +040039 jc,
gio0eaf2712024-04-14 13:08:46 +040040 map[string]struct{}{},
41 }
42}
43
44func (s *DodoAppServer) Start() error {
45 http.HandleFunc("/update", s.handleUpdate)
46 http.HandleFunc("/register-worker", s.handleRegisterWorker)
47 return http.ListenAndServe(fmt.Sprintf(":%d", s.port), nil)
48}
49
50type updateReq struct {
51 Ref string `json:"ref"`
52}
53
54func (s *DodoAppServer) handleUpdate(w http.ResponseWriter, r *http.Request) {
55 fmt.Println("update")
56 var req updateReq
57 var contents strings.Builder
58 io.Copy(&contents, r.Body)
59 c := contents.String()
60 fmt.Println(c)
61 if err := json.NewDecoder(strings.NewReader(c)).Decode(&req); err != nil {
62 fmt.Println(err)
63 return
64 }
65 if req.Ref != "refs/heads/master" {
66 return
67 }
68 go func() {
69 time.Sleep(20 * time.Second)
giof8843412024-05-22 16:38:05 +040070 if err := UpdateDodoApp(s.client, s.namespace, s.sshKey, s.jc, &s.env); err != nil {
gio0eaf2712024-04-14 13:08:46 +040071 fmt.Println(err)
72 }
73 }()
74 for addr, _ := range s.workers {
75 go func() {
76 // TODO(gio): make port configurable
77 http.Get(fmt.Sprintf("http://%s:3000/update", addr))
78 }()
79 }
80}
81
82type registerWorkerReq struct {
83 Address string `json:"address"`
84}
85
86func (s *DodoAppServer) handleRegisterWorker(w http.ResponseWriter, r *http.Request) {
87 var req registerWorkerReq
88 if err := json.NewDecoder(r.Body).Decode(&req); err != nil {
89 http.Error(w, err.Error(), http.StatusInternalServerError)
90 return
91 }
92 s.workers[req.Address] = struct{}{}
93 fmt.Printf("registered worker: %s\n", req.Address)
94}
95
giof8843412024-05-22 16:38:05 +040096func UpdateDodoApp(client soft.Client, namespace string, sshKey string, jc installer.JobCreator, env *installer.EnvConfig) error {
gio0eaf2712024-04-14 13:08:46 +040097 repo, err := client.GetRepo("app")
98 if err != nil {
99 return err
100 }
giof8843412024-05-22 16:38:05 +0400101 nsc := installer.NewNoOpNamespaceCreator()
gio0eaf2712024-04-14 13:08:46 +0400102 if err != nil {
103 return err
104 }
giof8843412024-05-22 16:38:05 +0400105 hf := installer.NewGitHelmFetcher()
106 m, err := installer.NewAppManager(repo, nsc, jc, hf, "/.dodo")
gio0eaf2712024-04-14 13:08:46 +0400107 if err != nil {
108 return err
109 }
110 appCfg, err := soft.ReadFile(repo, "app.cue")
111 fmt.Println(string(appCfg))
112 if err != nil {
113 return err
114 }
115 app, err := installer.NewDodoApp(appCfg)
116 if err != nil {
117 return err
118 }
giof8843412024-05-22 16:38:05 +0400119 lg := installer.GitRepositoryLocalChartGenerator{"app", namespace}
gio0eaf2712024-04-14 13:08:46 +0400120 if _, err := m.Install(app, "app", "/.dodo/app", namespace, map[string]any{
121 "repoAddr": repo.FullAddress(),
122 "sshPrivateKey": sshKey,
giof8843412024-05-22 16:38:05 +0400123 }, installer.WithConfig(env), installer.WithBranch("dodo"), installer.WithLocalChartGenerator(lg)); err != nil {
gio0eaf2712024-04-14 13:08:46 +0400124 return err
125 }
126 return nil
127}