home to your local SPACEGIRL 馃挮
arimelody.space
1package admin
2
3import (
4 "fmt"
5 "net/http"
6 "os"
7 "strings"
8
9 "arimelody-web/admin/templates"
10 "arimelody-web/controller"
11 "arimelody-web/model"
12)
13
14func serveReleases(app *model.AppState) http.Handler {
15 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
16 session := r.Context().Value("session").(*model.Session)
17
18 slices := strings.Split(strings.TrimPrefix(r.URL.Path, "/releases")[1:], "/")
19 releaseID := slices[0]
20
21 var action string = ""
22 if len(slices) > 1 {
23 action = slices[1]
24 }
25
26 if len(releaseID) > 0 {
27 serveRelease(app, releaseID, action).ServeHTTP(w, r)
28 return
29 }
30
31 type ReleasesData struct {
32 adminPageData
33 Releases []*model.Release
34 }
35
36 releases, err := controller.GetAllReleases(app.DB, false, 0, true)
37 if err != nil {
38 fmt.Fprintf(os.Stderr, "WARN: Failed to fetch releases: %s\n", err)
39 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
40 return
41 }
42
43 err = templates.ReleasesTemplate.Execute(w, ReleasesData{
44 adminPageData: adminPageData{
45 Path: r.URL.Path,
46 Session: session,
47 },
48 Releases: releases,
49 })
50 if err != nil {
51 fmt.Fprintf(os.Stderr, "WARN: Failed to serve releases page: %s\n", err)
52 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
53 return
54 }
55 })
56}
57
58func serveRelease(app *model.AppState, releaseID string, action string) http.Handler {
59 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
60 session := r.Context().Value("session").(*model.Session)
61
62 release, err := controller.GetRelease(app.DB, releaseID, true)
63 if err != nil {
64 if strings.Contains(err.Error(), "no rows") {
65 http.NotFound(w, r)
66 return
67 }
68 fmt.Printf("WARN: Failed to fetch full release data for %s: %s\n", releaseID, err)
69 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
70 return
71 }
72
73 if len(action) > 0 {
74 switch action {
75 case "editcredits":
76 serveEditCredits(release).ServeHTTP(w, r)
77 return
78 case "addcredit":
79 serveAddCredit(app, release).ServeHTTP(w, r)
80 return
81 case "newcredit":
82 serveNewCredit(app).ServeHTTP(w, r)
83 return
84 case "editlinks":
85 serveEditLinks(release).ServeHTTP(w, r)
86 return
87 case "edittracks":
88 serveEditTracks(release).ServeHTTP(w, r)
89 return
90 case "addtrack":
91 serveAddTrack(app, release).ServeHTTP(w, r)
92 return
93 case "newtrack":
94 serveNewTrack(app).ServeHTTP(w, r)
95 return
96 }
97 http.NotFound(w, r)
98 return
99 }
100
101 type ReleaseResponse struct {
102 adminPageData
103 Release *model.Release
104 }
105
106 for i, track := range release.Tracks {
107 track.Number = i + 1
108 }
109
110 err = templates.EditReleaseTemplate.Execute(w, ReleaseResponse{
111 adminPageData: adminPageData{ Path: r.URL.Path, Session: session },
112 Release: release,
113 })
114 if err != nil {
115 fmt.Printf("WARN: Failed to serve admin release page for %s: %s\n", release.ID, err)
116 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
117 }
118 })
119}
120
121func serveEditCredits(release *model.Release) http.Handler {
122 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
123 w.Header().Set("Content-Type", "text/html")
124 err := templates.EditCreditsTemplate.Execute(w, release)
125 if err != nil {
126 fmt.Printf("WARN: Failed to serve edit credits component for %s: %s\n", release.ID, err)
127 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
128 }
129 })
130}
131
132func serveAddCredit(app *model.AppState, release *model.Release) http.Handler {
133 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
134 artists, err := controller.GetArtistsNotOnRelease(app.DB, release.ID)
135 if err != nil {
136 fmt.Printf("WARN: Failed to fetch artists not on %s: %s\n", release.ID, err)
137 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
138 return
139 }
140
141 type response struct {
142 ReleaseID string;
143 Artists []*model.Artist
144 }
145
146 w.Header().Set("Content-Type", "text/html")
147 err = templates.AddCreditTemplate.Execute(w, response{
148 ReleaseID: release.ID,
149 Artists: artists,
150 })
151 if err != nil {
152 fmt.Printf("WARN: Failed to serve add credits component for %s: %s\n", release.ID, err)
153 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
154 }
155 })
156}
157
158func serveNewCredit(app *model.AppState) http.Handler {
159 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
160 artistID := strings.Split(r.URL.Path, "/")[3]
161 artist, err := controller.GetArtist(app.DB, artistID)
162 if err != nil {
163 fmt.Printf("WARN: Failed to fetch artist %s: %s\n", artistID, err)
164 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
165 return
166 }
167 if artist == nil {
168 http.NotFound(w, r)
169 return
170 }
171
172 w.Header().Set("Content-Type", "text/html")
173 err = templates.NewCreditTemplate.Execute(w, artist)
174 if err != nil {
175 fmt.Printf("WARN: Failed to serve new credit component for %s: %s\n", artist.ID, err)
176 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
177 }
178 })
179}
180
181func serveEditLinks(release *model.Release) http.Handler {
182 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
183 w.Header().Set("Content-Type", "text/html")
184 err := templates.EditLinksTemplate.Execute(w, release)
185 if err != nil {
186 fmt.Printf("WARN: Failed to serve edit links component for %s: %s\n", release.ID, err)
187 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
188 }
189 })
190}
191
192func serveEditTracks(release *model.Release) http.Handler {
193 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
194 w.Header().Set("Content-Type", "text/html")
195
196 type editTracksData struct { Release *model.Release }
197
198 err := templates.EditTracksTemplate.Execute(w, editTracksData{ Release: release })
199 if err != nil {
200 fmt.Printf("WARN: Failed to serve edit tracks component for %s: %s\n", release.ID, err)
201 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
202 }
203 })
204}
205
206func serveAddTrack(app *model.AppState, release *model.Release) http.Handler {
207 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
208 tracks, err := controller.GetTracksNotOnRelease(app.DB, release.ID)
209 if err != nil {
210 fmt.Printf("WARN: Failed to fetch tracks not on %s: %s\n", release.ID, err)
211 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
212 return
213 }
214
215 type response struct {
216 ReleaseID string;
217 Tracks []*model.Track
218 }
219
220 w.Header().Set("Content-Type", "text/html")
221 err = templates.AddTrackTemplate.Execute(w, response{
222 ReleaseID: release.ID,
223 Tracks: tracks,
224 })
225 if err != nil {
226 fmt.Printf("WARN: Failed to add tracks component for %s: %s\n", release.ID, err)
227 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
228 }
229 })
230}
231
232func serveNewTrack(app *model.AppState) http.Handler {
233 return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
234 trackID := strings.Split(r.URL.Path, "/")[3]
235 track, err := controller.GetTrack(app.DB, trackID)
236 if err != nil {
237 fmt.Printf("WARN: Failed to fetch track %s: %s\n", trackID, err)
238 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
239 return
240 }
241 if track == nil {
242 http.NotFound(w, r)
243 return
244 }
245
246 w.Header().Set("Content-Type", "text/html")
247 err = templates.NewTrackTemplate.Execute(w, track)
248 if err != nil {
249 fmt.Printf("WARN: Failed to serve new track component for %s: %s\n", track.ID, err)
250 http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
251 }
252 })
253}