repos / pico

pico services mono repo
git clone https://github.com/picosh/pico.git

commit
0e5bfd8
parent
338dd1d
author
Eric Bower
date
2025-05-24 21:20:50 -0400 EDT
fix: lint suggestions
18 files changed,  +158, -151
M pkg/apps/pico/cli.go
+4, -3
 1@@ -187,16 +187,17 @@ func Middleware(handler *CliHandler) pssh.SSHServerMiddleware {
 2 
 3 			cmd := strings.TrimSpace(args[0])
 4 			if len(args) == 1 {
 5-				if cmd == "help" {
 6+				switch cmd {
 7+				case "help":
 8 					opts.help()
 9 					return nil
10-				} else if cmd == "logs" {
11+				case "logs":
12 					err = opts.logs(sesh.Context())
13 					if err != nil {
14 						sesh.Fatal(err)
15 					}
16 					return nil
17-				} else {
18+				default:
19 					return next(sesh)
20 				}
21 			}
M pkg/apps/pipe/api.go
+1, -1
1@@ -443,7 +443,7 @@ func StartApiServer() {
2 
3 	go func() {
4 		for {
5-			_, err := pingSession.Write([]byte(fmt.Sprintf("%s: pipe-web ping\n", time.Now().UTC().Format(time.RFC3339))))
6+			_, err := fmt.Fprintf(pingSession, fmt.Sprintf("%s: pipe-web ping\n", time.Now().UTC().Format(time.RFC3339)))
7 			if err != nil {
8 				logger.Error("pipe ping error", "err", err.Error())
9 			}
M pkg/apps/pipe/cli.go
+4, -3
 1@@ -254,11 +254,12 @@ func Middleware(handler *CliHandler) pssh.SSHServerMiddleware {
 2 							var pipes []*psub.Client
 3 
 4 							for _, client := range channel.GetClients() {
 5-								if client.Direction == psub.ChannelDirectionInput {
 6+								switch client.Direction {
 7+								case psub.ChannelDirectionInput:
 8 									pubs = append(pubs, client)
 9-								} else if client.Direction == psub.ChannelDirectionOutput {
10+								case psub.ChannelDirectionOutput:
11 									subs = append(subs, client)
12-								} else if client.Direction == psub.ChannelDirectionInputOutput {
13+								case psub.ChannelDirectionInputOutput:
14 									pipes = append(pipes, client)
15 								}
16 							}
M pkg/apps/prose/api.go
+6, -6
 1@@ -387,8 +387,8 @@ func postHandler(w http.ResponseWriter, r *http.Request) {
 2 		if err != nil {
 3 			logger.Error("readme", "err", err.Error())
 4 		}
 5-		if readmeParsed.MetaData.Title != "" {
 6-			blogName = readmeParsed.MetaData.Title
 7+		if readmeParsed.Title != "" {
 8+			blogName = readmeParsed.Title
 9 		}
10 		withStyles = readmeParsed.WithStyles
11 		ogImage = readmeParsed.Image
12@@ -455,11 +455,11 @@ func postHandler(w http.ResponseWriter, r *http.Request) {
13 			if err != nil {
14 				logger.Error("parse not found file", "err", err.Error())
15 			}
16-			if notFoundParsed.MetaData.Title != "" {
17-				title = notFoundParsed.MetaData.Title
18+			if notFoundParsed.Title != "" {
19+				title = notFoundParsed.Title
20 			}
21-			if notFoundParsed.MetaData.Description != "" {
22-				desc = notFoundParsed.MetaData.Description
23+			if notFoundParsed.Description != "" {
24+				desc = notFoundParsed.Description
25 			}
26 			ogImage = notFoundParsed.Image
27 			ogImageCard = notFoundParsed.ImageCard
M pkg/apps/prose/scp_hooks.go
+2, -2
 1@@ -74,11 +74,11 @@ func (p *MarkdownHooks) FileMeta(s *pssh.SSHServerConnSession, data *filehandler
 2 	data.Description = parsedText.Description
 3 
 4 	if parsedText.PublishAt != nil && !parsedText.PublishAt.IsZero() {
 5-		data.PublishAt = parsedText.MetaData.PublishAt
 6+		data.PublishAt = parsedText.PublishAt
 7 	}
 8 
 9 	isHiddenFilename := slices.Contains(p.Cfg.HiddenPosts, data.Filename)
10-	data.Hidden = parsedText.MetaData.Hidden || isHiddenFilename
11+	data.Hidden = parsedText.Hidden || isHiddenFilename
12 
13 	return nil
14 }
M pkg/db/stub/stub.go
+64, -64
  1@@ -23,178 +23,178 @@ func NewStubDB(logger *slog.Logger) *StubDB {
  2 	return d
  3 }
  4 
  5-var notImpl = fmt.Errorf("not implemented")
  6+var errNotImpl = fmt.Errorf("not implemented")
  7 
  8 func (me *StubDB) RegisterUser(username, pubkey, comment string) (*db.User, error) {
  9-	return nil, notImpl
 10+	return nil, errNotImpl
 11 }
 12 
 13 func (me *StubDB) RemoveUsers(userIDs []string) error {
 14-	return notImpl
 15+	return errNotImpl
 16 }
 17 
 18 func (me *StubDB) InsertPublicKey(userID, key, name string, tx *sql.Tx) error {
 19-	return notImpl
 20+	return errNotImpl
 21 }
 22 
 23 func (me *StubDB) UpdatePublicKey(pubkeyID, name string) (*db.PublicKey, error) {
 24-	return nil, notImpl
 25+	return nil, errNotImpl
 26 }
 27 
 28 func (me *StubDB) FindPublicKeyForKey(key string) (*db.PublicKey, error) {
 29-	return nil, notImpl
 30+	return nil, errNotImpl
 31 }
 32 
 33 func (me *StubDB) FindPublicKey(pubkeyID string) (*db.PublicKey, error) {
 34-	return nil, notImpl
 35+	return nil, errNotImpl
 36 }
 37 
 38 func (me *StubDB) FindKeysForUser(user *db.User) ([]*db.PublicKey, error) {
 39-	return []*db.PublicKey{}, notImpl
 40+	return []*db.PublicKey{}, errNotImpl
 41 }
 42 
 43 func (me *StubDB) RemoveKeys(keyIDs []string) error {
 44-	return notImpl
 45+	return errNotImpl
 46 }
 47 
 48 func (me *StubDB) FindPostsBeforeDate(date *time.Time, space string) ([]*db.Post, error) {
 49-	return []*db.Post{}, notImpl
 50+	return []*db.Post{}, errNotImpl
 51 }
 52 
 53 func (me *StubDB) FindUserForKey(username string, key string) (*db.User, error) {
 54-	return nil, notImpl
 55+	return nil, errNotImpl
 56 }
 57 
 58 func (me *StubDB) FindUserByPubkey(key string) (*db.User, error) {
 59-	return nil, notImpl
 60+	return nil, errNotImpl
 61 }
 62 
 63 func (me *StubDB) FindUser(userID string) (*db.User, error) {
 64-	return nil, notImpl
 65+	return nil, errNotImpl
 66 }
 67 
 68 func (me *StubDB) ValidateName(name string) (bool, error) {
 69-	return false, notImpl
 70+	return false, errNotImpl
 71 }
 72 
 73 func (me *StubDB) FindUserByName(name string) (*db.User, error) {
 74-	return nil, notImpl
 75+	return nil, errNotImpl
 76 }
 77 
 78 func (me *StubDB) FindUserForNameAndKey(name string, key string) (*db.User, error) {
 79-	return nil, notImpl
 80+	return nil, errNotImpl
 81 }
 82 
 83 func (me *StubDB) FindUserForToken(token string) (*db.User, error) {
 84-	return nil, notImpl
 85+	return nil, errNotImpl
 86 }
 87 
 88 func (me *StubDB) SetUserName(userID string, name string) error {
 89-	return notImpl
 90+	return errNotImpl
 91 }
 92 
 93 func (me *StubDB) FindPostWithFilename(filename string, persona_id string, space string) (*db.Post, error) {
 94-	return nil, notImpl
 95+	return nil, errNotImpl
 96 }
 97 
 98 func (me *StubDB) FindPostWithSlug(slug string, user_id string, space string) (*db.Post, error) {
 99-	return nil, notImpl
100+	return nil, errNotImpl
101 }
102 
103 func (me *StubDB) FindPost(postID string) (*db.Post, error) {
104-	return nil, notImpl
105+	return nil, errNotImpl
106 }
107 
108 func (me *StubDB) FindAllPosts(page *db.Pager, space string) (*db.Paginate[*db.Post], error) {
109-	return &db.Paginate[*db.Post]{}, notImpl
110+	return &db.Paginate[*db.Post]{}, errNotImpl
111 }
112 
113 func (me *StubDB) FindAllUpdatedPosts(page *db.Pager, space string) (*db.Paginate[*db.Post], error) {
114-	return &db.Paginate[*db.Post]{}, notImpl
115+	return &db.Paginate[*db.Post]{}, errNotImpl
116 }
117 
118 func (me *StubDB) InsertPost(post *db.Post) (*db.Post, error) {
119-	return nil, notImpl
120+	return nil, errNotImpl
121 }
122 
123 func (me *StubDB) UpdatePost(post *db.Post) (*db.Post, error) {
124-	return nil, notImpl
125+	return nil, errNotImpl
126 }
127 
128 func (me *StubDB) RemovePosts(postIDs []string) error {
129-	return notImpl
130+	return errNotImpl
131 }
132 
133 func (me *StubDB) FindPostsForUser(page *db.Pager, userID string, space string) (*db.Paginate[*db.Post], error) {
134-	return &db.Paginate[*db.Post]{}, notImpl
135+	return &db.Paginate[*db.Post]{}, errNotImpl
136 }
137 
138 func (me *StubDB) FindAllPostsForUser(userID string, space string) ([]*db.Post, error) {
139-	return []*db.Post{}, notImpl
140+	return []*db.Post{}, errNotImpl
141 }
142 
143 func (me *StubDB) FindPosts() ([]*db.Post, error) {
144-	return []*db.Post{}, notImpl
145+	return []*db.Post{}, errNotImpl
146 }
147 
148 func (me *StubDB) FindExpiredPosts(space string) ([]*db.Post, error) {
149-	return []*db.Post{}, notImpl
150+	return []*db.Post{}, errNotImpl
151 }
152 
153 func (me *StubDB) FindUpdatedPostsForUser(userID string, space string) ([]*db.Post, error) {
154-	return []*db.Post{}, notImpl
155+	return []*db.Post{}, errNotImpl
156 }
157 
158 func (me *StubDB) Close() error {
159-	return notImpl
160+	return errNotImpl
161 }
162 
163 func (me *StubDB) InsertVisit(view *db.AnalyticsVisits) error {
164-	return notImpl
165+	return errNotImpl
166 }
167 
168 func (me *StubDB) VisitSummary(opts *db.SummaryOpts) (*db.SummaryVisits, error) {
169-	return &db.SummaryVisits{}, notImpl
170+	return &db.SummaryVisits{}, errNotImpl
171 }
172 
173 func (me *StubDB) FindVisitSiteList(opts *db.SummaryOpts) ([]*db.VisitUrl, error) {
174-	return []*db.VisitUrl{}, notImpl
175+	return []*db.VisitUrl{}, errNotImpl
176 }
177 
178 func (me *StubDB) FindUsers() ([]*db.User, error) {
179-	return []*db.User{}, notImpl
180+	return []*db.User{}, errNotImpl
181 }
182 
183 func (me *StubDB) ReplaceTagsForPost(tags []string, postID string) error {
184-	return notImpl
185+	return errNotImpl
186 }
187 
188 func (me *StubDB) ReplaceAliasesForPost(aliases []string, postID string) error {
189-	return notImpl
190+	return errNotImpl
191 }
192 
193 func (me *StubDB) FindUserPostsByTag(page *db.Pager, tag, userID, space string) (*db.Paginate[*db.Post], error) {
194-	return &db.Paginate[*db.Post]{}, notImpl
195+	return &db.Paginate[*db.Post]{}, errNotImpl
196 }
197 
198 func (me *StubDB) FindPostsByTag(pager *db.Pager, tag, space string) (*db.Paginate[*db.Post], error) {
199-	return &db.Paginate[*db.Post]{}, notImpl
200+	return &db.Paginate[*db.Post]{}, errNotImpl
201 }
202 
203 func (me *StubDB) FindPopularTags(space string) ([]string, error) {
204-	return []string{}, notImpl
205+	return []string{}, errNotImpl
206 }
207 
208 func (me *StubDB) FindTagsForPost(postID string) ([]string, error) {
209-	return []string{}, notImpl
210+	return []string{}, errNotImpl
211 }
212 
213 func (me *StubDB) FindFeature(userID string, feature string) (*db.FeatureFlag, error) {
214-	return nil, notImpl
215+	return nil, errNotImpl
216 }
217 
218 func (me *StubDB) FindFeaturesForUser(userID string) ([]*db.FeatureFlag, error) {
219-	return []*db.FeatureFlag{}, notImpl
220+	return []*db.FeatureFlag{}, errNotImpl
221 }
222 
223 func (me *StubDB) HasFeatureForUser(userID string, feature string) bool {
224@@ -202,81 +202,81 @@ func (me *StubDB) HasFeatureForUser(userID string, feature string) bool {
225 }
226 
227 func (me *StubDB) FindTotalSizeForUser(userID string) (int, error) {
228-	return 0, notImpl
229+	return 0, errNotImpl
230 }
231 
232 func (me *StubDB) InsertFeedItems(postID string, items []*db.FeedItem) error {
233-	return notImpl
234+	return errNotImpl
235 }
236 
237 func (me *StubDB) FindFeedItemsByPostID(postID string) ([]*db.FeedItem, error) {
238-	return []*db.FeedItem{}, notImpl
239+	return []*db.FeedItem{}, errNotImpl
240 }
241 
242 func (me *StubDB) UpsertProject(userID, name, projectDir string) (*db.Project, error) {
243-	return nil, notImpl
244+	return nil, errNotImpl
245 }
246 
247 func (me *StubDB) InsertProject(userID, name, projectDir string) (string, error) {
248-	return "", notImpl
249+	return "", errNotImpl
250 }
251 
252 func (me *StubDB) UpdateProject(userID, name string) error {
253-	return notImpl
254+	return errNotImpl
255 }
256 
257 func (me *StubDB) FindProjectByName(userID, name string) (*db.Project, error) {
258-	return &db.Project{}, notImpl
259+	return &db.Project{}, errNotImpl
260 }
261 
262 func (me *StubDB) InsertToken(userID, name string) (string, error) {
263-	return "", notImpl
264+	return "", errNotImpl
265 }
266 
267 func (me *StubDB) UpsertToken(userID, name string) (string, error) {
268-	return "", notImpl
269+	return "", errNotImpl
270 }
271 
272 func (me *StubDB) FindTokenByName(userID, name string) (string, error) {
273-	return "", notImpl
274+	return "", errNotImpl
275 }
276 
277 func (me *StubDB) RemoveToken(tokenID string) error {
278-	return notImpl
279+	return errNotImpl
280 }
281 
282 func (me *StubDB) FindTokensForUser(userID string) ([]*db.Token, error) {
283-	return []*db.Token{}, notImpl
284+	return []*db.Token{}, errNotImpl
285 }
286 
287 func (me *StubDB) InsertFeature(userID, name string, expiresAt time.Time) (*db.FeatureFlag, error) {
288-	return nil, notImpl
289+	return nil, errNotImpl
290 }
291 
292 func (me *StubDB) RemoveFeature(userID string, name string) error {
293-	return notImpl
294+	return errNotImpl
295 }
296 
297 func (me *StubDB) AddPicoPlusUser(username, email, paymentType, txId string) error {
298-	return notImpl
299+	return errNotImpl
300 }
301 
302 func (me *StubDB) FindTagsForUser(userID string, tag string) ([]string, error) {
303-	return []string{}, notImpl
304+	return []string{}, errNotImpl
305 }
306 
307 func (me *StubDB) FindUserStats(userID string) (*db.UserStats, error) {
308-	return nil, notImpl
309+	return nil, errNotImpl
310 }
311 
312 func (me *StubDB) InsertTunsEventLog(log *db.TunsEventLog) error {
313-	return notImpl
314+	return errNotImpl
315 }
316 
317 func (me *StubDB) FindTunsEventLogsByAddr(userID, addr string) ([]*db.TunsEventLog, error) {
318-	return nil, notImpl
319+	return nil, errNotImpl
320 }
321 
322 func (me *StubDB) FindTunsEventLogs(userID string) ([]*db.TunsEventLog, error) {
323-	return nil, notImpl
324+	return nil, errNotImpl
325 }
M pkg/filehandlers/post_handler.go
+1, -1
1@@ -150,7 +150,7 @@ func (h *ScpUploadHandler) Write(s *pssh.SSHServerConnSession, entry *sendutils.
2 	if post != nil {
3 		metadata.Cur = post
4 		metadata.Data = post.Data
5-		metadata.Post.PublishAt = post.PublishAt
6+		metadata.PublishAt = post.PublishAt
7 	}
8 
9 	err = h.Hooks.FileMeta(s, &metadata)
M pkg/pobj/util.go
+3, -2
 1@@ -18,9 +18,10 @@ func EnvDriverDetector(logger *slog.Logger) (storage.ObjectStorage, error) {
 2 	driver := GetEnv("OBJECT_DRIVER", "fs")
 3 	logger.Info("driver detected", "driver", driver)
 4 
 5-	if driver == "memory" {
 6+	switch driver {
 7+	case "memory":
 8 		return storage.NewStorageMemory(map[string]map[string]string{})
 9-	} else if driver == "minio" {
10+	case "minio":
11 		url := GetEnv("MINIO_URL", "")
12 		user := GetEnv("MINIO_ROOT_USER", "")
13 		pass := GetEnv("MINIO_ROOT_PASSWORD", "")
M pkg/pssh/pty.go
+1, -5
 1@@ -30,11 +30,7 @@ func PtyMdw(mdw SSHServerMiddleware, waitTimeout time.Duration) SSHServerMiddlew
 2 			if waitTimeout > 0 {
 3 				afterTime := time.Now().Add(waitTimeout)
 4 
 5-				for {
 6-					if time.Now().After(afterTime) {
 7-						break
 8-					}
 9-
10+				for time.Now().After(afterTime) {
11 					_, _, ok := sesh.Pty()
12 					if ok {
13 						break
M pkg/pssh/server.go
+1, -1
1@@ -147,7 +147,7 @@ func (s *SSHServerConnSession) Close() error {
2 
3 func (s *SSHServerConnSession) Exit(code int) error {
4 	status := struct{ Status uint32 }{uint32(code)}
5-	_, err := s.Channel.SendRequest("exit-status", false, ssh.Marshal(&status))
6+	_, err := s.SendRequest("exit-status", false, ssh.Marshal(&status))
7 	return err
8 }
9 
M pkg/send/list/list.go
+1, -0
1@@ -12,6 +12,7 @@ func Middleware(writeHandler utils.CopyFromClientHandler) pssh.SSHServerMiddlewa
2 	return func(sshHandler pssh.SSHServerHandler) pssh.SSHServerHandler {
3 		return func(session *pssh.SSHServerConnSession) error {
4 			cmd := session.Command()
5+			//nolint
6 			if !(len(cmd) > 1 && cmd[0] == "command" && cmd[1] == "ls") {
7 				return sshHandler(session)
8 			}
M pkg/send/pipe/pipe.go
+1, -1
1@@ -51,7 +51,7 @@ func Middleware(writeHandler utils.CopyFromClientHandler, ext string) pssh.SSHSe
2 			}
3 
4 			if result != "" {
5-				_, err = session.Write([]byte(fmt.Sprintf("%s\r\n", result)))
6+				_, err := fmt.Fprintf(session, fmt.Sprintf("%s\r\n", result))
7 				if err != nil {
8 					utils.ErrorHandler(session, err)
9 				}
M pkg/send/protocols/rsync/rsync.go
+1, -1
1@@ -157,7 +157,7 @@ func (h *handler) Remove(willReceive []*rsyncutils.ReceiverFile) error {
2 
3 	for _, file := range toDelete {
4 		errs = append(errs, h.writeHandler.Delete(h.session, &utils.FileEntry{Filepath: path.Join("/", h.root, file)}))
5-		_, err = h.session.Stderr().Write([]byte(fmt.Sprintf("deleting %s\r\n", file)))
6+		_, err = fmt.Fprintf(h.session.Stderr(), fmt.Sprintf("deleting %s\r\n", file))
7 		errs = append(errs, err)
8 	}
9 
M pkg/send/protocols/sftp/handler.go
+1, -1
1@@ -73,7 +73,7 @@ func (f *handler) Filelist(r *sftp.Request) (sftp.ListerAt, error) {
2 
3 		if !list {
4 			listData = slices.DeleteFunc(listData, func(f os.FileInfo) bool {
5-				return !(f.Name() == "" || f.Name() == filepath.Base(r.Filepath))
6+				return f.Name() != "" && f.Name() != filepath.Base(r.Filepath)
7 			})
8 		}
9 
M pkg/shared/listparser.go
+10, -9
 1@@ -101,26 +101,27 @@ func PublishAtDate(date string) (*time.Time, error) {
 2 }
 3 
 4 func TokenToMetaField(meta *ListMetaData, token *SplitToken) error {
 5-	if token.Key == "publish_at" {
 6+	switch token.Key {
 7+	case "publish_at":
 8 		publishAt, err := PublishAtDate(token.Value)
 9 		if err == nil {
10 			meta.PublishAt = publishAt
11 		}
12-	} else if token.Key == "title" {
13+	case "title":
14 		meta.Title = token.Value
15-	} else if token.Key == "description" {
16+	case "description":
17 		meta.Description = token.Value
18-	} else if token.Key == "list_type" {
19+	case "list_type":
20 		meta.ListType = token.Value
21-	} else if token.Key == "tags" {
22+	case "tags":
23 		tags := strings.Split(token.Value, ",")
24 		meta.Tags = make([]string, 0)
25 		for _, tag := range tags {
26 			meta.Tags = append(meta.Tags, strings.TrimSpace(tag))
27 		}
28-	} else if token.Key == "layout" {
29+	case "layout":
30 		meta.Layout = token.Value
31-	} else if token.Key == "digest_interval" {
32+	case "digest_interval":
33 		if !slices.Contains(DigestIntervalOpts, token.Value) {
34 			return fmt.Errorf(
35 				"(%s) is not a valid option, choose from [%s]",
36@@ -129,9 +130,9 @@ func TokenToMetaField(meta *ListMetaData, token *SplitToken) error {
37 			)
38 		}
39 		meta.DigestInterval = token.Value
40-	} else if token.Key == "email" {
41+	case "email":
42 		meta.Email = token.Value
43-	} else if token.Key == "inline_content" {
44+	case "inline_content":
45 		v, err := strconv.ParseBool(token.Value)
46 		if err != nil {
47 			// its empty or its improperly configured, just send the content
M pkg/shared/mdparser.go
+13, -13
  1@@ -257,7 +257,7 @@ func ParseText(text string) (*ParsedText, error) {
  2 	}
  3 	// 3. else, set it to nothing (slug should get used later down the line)
  4 	// this is implicit since it's already ""
  5-	parsed.MetaData.Title = title
  6+	parsed.Title = title
  7 
  8 	// only handle toc after the title is extracted (if it's getting extracted)
  9 	mtoc, err := toToc(metaData["toc"])
 10@@ -275,49 +275,49 @@ func ParseText(text string) (*ParsedText, error) {
 11 	if err != nil {
 12 		return &parsed, fmt.Errorf("front-matter field (%s): %w", "description", err)
 13 	}
 14-	parsed.MetaData.Description = description
 15+	parsed.Description = description
 16 
 17 	domain, err := toString(metaData["domain"])
 18 	if err != nil {
 19 		return &parsed, fmt.Errorf("front-matter field (%s): %w", "domain", err)
 20 	}
 21-	parsed.MetaData.Domain = domain
 22+	parsed.Domain = domain
 23 
 24 	layout, err := toString(metaData["layout"])
 25 	if err != nil {
 26 		return &parsed, fmt.Errorf("front-matter field (%s): %w", "layout", err)
 27 	}
 28-	parsed.MetaData.Layout = layout
 29+	parsed.Layout = layout
 30 
 31 	image, err := toString(metaData["image"])
 32 	if err != nil {
 33 		return &parsed, fmt.Errorf("front-matter field (%s): %w", "image", err)
 34 	}
 35-	parsed.MetaData.Image = image
 36+	parsed.Image = image
 37 
 38 	card, err := toString(metaData["card"])
 39 	if err != nil {
 40 		return &parsed, fmt.Errorf("front-matter field (%s): %w", "card", err)
 41 	}
 42-	parsed.MetaData.ImageCard = card
 43+	parsed.ImageCard = card
 44 
 45 	hidden, err := toBool(metaData["draft"], false)
 46 	if err != nil {
 47 		return &parsed, fmt.Errorf("front-matter field (%s): %w", "draft", err)
 48 	}
 49-	parsed.MetaData.Hidden = hidden
 50+	parsed.Hidden = hidden
 51 
 52 	withStyles, err := toBool(metaData["with_styles"], true)
 53 	if err != nil {
 54 		return &parsed, fmt.Errorf("front-matter field (%s): %w", "with_style", err)
 55 	}
 56-	parsed.MetaData.WithStyles = withStyles
 57+	parsed.WithStyles = withStyles
 58 
 59 	favicon, err := toString(metaData["favicon"])
 60 	if err != nil {
 61 		return &parsed, fmt.Errorf("front-matter field (%s): %w", "favicon", err)
 62 	}
 63-	parsed.MetaData.Favicon = favicon
 64+	parsed.Favicon = favicon
 65 
 66 	publishAt := &time.Time{}
 67 	date, err := toString(metaData["date"])
 68@@ -332,7 +332,7 @@ func ParseText(text string) (*ParsedText, error) {
 69 		}
 70 		publishAt = &nextDate
 71 	}
 72-	parsed.MetaData.PublishAt = publishAt
 73+	parsed.PublishAt = publishAt
 74 
 75 	orderedMetaData := meta.GetItems(context)
 76 
 77@@ -340,13 +340,13 @@ func ParseText(text string) (*ParsedText, error) {
 78 	if err != nil {
 79 		return &parsed, err
 80 	}
 81-	parsed.MetaData.Nav = nav
 82+	parsed.Nav = nav
 83 
 84 	aliases, err := toAliases(metaData["aliases"])
 85 	if err != nil {
 86 		return &parsed, err
 87 	}
 88-	parsed.MetaData.Aliases = aliases
 89+	parsed.Aliases = aliases
 90 
 91 	rtags := metaData["tags"]
 92 	tags, err := toTags(rtags)
 93@@ -357,7 +357,7 @@ func ParseText(text string) (*ParsedText, error) {
 94 	if rtags == nil {
 95 		tags = AstTags(doc)
 96 	}
 97-	parsed.MetaData.Tags = tags
 98+	parsed.Tags = tags
 99 
100 	// Rendering happens last to allow any of the previous steps to manipulate
101 	// the AST.
M pkg/shared/mime/mime.go
+41, -36
  1@@ -4,77 +4,82 @@ import "path/filepath"
  2 
  3 func GetMimeType(fpath string) string {
  4 	ext := filepath.Ext(fpath)
  5-	if ext == ".svg" {
  6+	switch ext {
  7+	case ".svg":
  8 		return "image/svg+xml"
  9-	} else if ext == ".css" {
 10+	case ".css":
 11 		return "text/css"
 12-	} else if ext == ".js" {
 13+	case ".js":
 14 		return "text/javascript"
 15-	} else if ext == ".ico" {
 16+	case ".ico":
 17 		return "image/x-icon"
 18-	} else if ext == ".pdf" {
 19+	case ".pdf":
 20 		return "application/pdf"
 21-	} else if ext == ".html" || ext == ".htm" {
 22+	case ".htm":
 23+	case ".html":
 24 		return "text/html"
 25-	} else if ext == ".jpg" || ext == ".jpeg" {
 26+	case ".jpeg":
 27+	case ".jpg":
 28 		return "image/jpeg"
 29-	} else if ext == ".png" {
 30+	case ".png":
 31 		return "image/png"
 32-	} else if ext == ".gif" {
 33+	case ".gif":
 34 		return "image/gif"
 35-	} else if ext == ".webp" {
 36+	case ".webp":
 37 		return "image/webp"
 38-	} else if ext == ".otf" {
 39+	case ".otf":
 40 		return "font/otf"
 41-	} else if ext == ".woff" {
 42+	case ".woff":
 43 		return "font/woff"
 44-	} else if ext == ".woff2" {
 45+	case ".woff2":
 46 		return "font/woff2"
 47-	} else if ext == ".ttf" {
 48+	case ".ttf":
 49 		return "font/ttf"
 50-	} else if ext == ".md" {
 51+	case ".md":
 52 		return "text/markdown; charset=UTF-8"
 53-	} else if ext == ".json" || ext == ".map" {
 54+	case ".map":
 55+	case ".json":
 56 		return "application/json"
 57-	} else if ext == ".rss" {
 58+	case ".rss":
 59 		return "application/rss+xml"
 60-	} else if ext == ".atom" {
 61+	case ".atom":
 62 		return "application/atom+xml"
 63-	} else if ext == ".webmanifest" {
 64+	case ".webmanifest":
 65 		return "application/manifest+json"
 66-	} else if ext == ".xml" {
 67+	case ".xml":
 68 		return "application/xml"
 69-	} else if ext == ".xsl" {
 70+	case ".xsl":
 71 		return "application/xml"
 72-	} else if ext == ".avif" {
 73+	case ".avif":
 74 		return "image/avif"
 75-	} else if ext == ".heif" {
 76+	case ".heif":
 77 		return "image/heif"
 78-	} else if ext == ".heic" {
 79+	case ".heic":
 80 		return "image/heif"
 81-	} else if ext == ".opus" {
 82+	case ".opus":
 83 		return "audio/opus"
 84-	} else if ext == ".wav" {
 85+	case ".wav":
 86 		return "audio/wav"
 87-	} else if ext == ".mp3" {
 88+	case ".mp3":
 89 		return "audio/mpeg"
 90-	} else if ext == ".mp4" {
 91+	case ".mp4":
 92 		return "video/mp4"
 93-	} else if ext == ".mpeg" {
 94+	case ".mpeg":
 95 		return "video/mpeg"
 96-	} else if ext == ".wasm" {
 97+	case ".wasm":
 98 		return "application/wasm"
 99-	} else if ext == ".opml" {
100+	case ".opml":
101 		return "text/x-opml"
102-	} else if ext == ".eot" {
103+	case ".eot":
104 		return "application/vnd.ms-fontobject"
105-	} else if ext == ".yml" || ext == ".yaml" {
106+	case ".yaml":
107+	case ".yml":
108 		return "text/x-yaml"
109-	} else if ext == ".zip" {
110+	case ".zip":
111 		return "application/zip"
112-	} else if ext == ".rar" {
113+	case ".rar":
114 		return "application/vnd.rar"
115-	} else if ext == ".txt" {
116+	case ".txt":
117 		return "text/plain"
118 	}
119 
M pkg/shared/storage/proxy.go
+3, -2
 1@@ -38,12 +38,13 @@ func UriToImgProcessOpts(uri string) (*ImgProcessOpts, error) {
 2 				if sg == "" {
 3 					continue
 4 				}
 5-				if idx == 1 {
 6+				switch idx {
 7+				case 1:
 8 					r.Width, err = strconv.Atoi(sg)
 9 					if err != nil {
10 						return opts, err
11 					}
12-				} else if idx == 2 {
13+				case 2:
14 					r.Height, err = strconv.Atoi(sg)
15 					if err != nil {
16 						return opts, err