implement hold discovery dropdown in settings. implement a data privacy export feature

This commit is contained in:
Evan Jarrett
2026-01-07 22:41:14 -06:00
parent d4b88b5105
commit 3409af6c67
39 changed files with 4124 additions and 159 deletions
+53 -1
View File
@@ -7,6 +7,7 @@
package logging
import (
"fmt"
"io"
"log/slog"
"os"
@@ -56,7 +57,16 @@ func InitLogger(level string) {
levelVar.Set(logLevel)
opts := &slog.HandlerOptions{
Level: levelVar,
Level: levelVar,
AddSource: true,
ReplaceAttr: func(groups []string, a slog.Attr) slog.Attr {
if a.Key == slog.SourceKey {
if src, ok := a.Value.Any().(*slog.Source); ok {
a.Value = slog.StringValue(shortenSource(src.File, src.Line))
}
}
return a
},
}
handler := slog.NewTextHandler(os.Stdout, opts)
@@ -127,6 +137,48 @@ func autoRevert() {
"trigger", "auto-revert")
}
// shortenSource shortens file paths for cleaner log output.
// - Our code (atcr.io/): shows pkg/appview/jetstream/processor.go:73
// - Library code (/pkg/mod/): shows indigo/atproto/identity/handle.go:225
// - Other: shows last 3 path components
func shortenSource(file string, line int) string {
// Our code: strip everything up to and including atcr.io/
if idx := strings.Index(file, "atcr.io/"); idx != -1 {
return fmt.Sprintf("%s:%d", file[idx+8:], line) // 8 = len("atcr.io/")
}
// Library code in go mod cache: extract module name + relative path
// Example: /go/pkg/mod/github.com/bluesky-social/indigo@v0.0.0-.../atproto/identity/handle.go
// becomes: indigo/atproto/identity/handle.go:225
if idx := strings.Index(file, "/pkg/mod/"); idx != -1 {
modPath := file[idx+9:] // 9 = len("/pkg/mod/")
if atIdx := strings.Index(modPath, "@"); atIdx != -1 {
// Get module path before @
modFullPath := modPath[:atIdx]
parts := strings.Split(modFullPath, "/")
// Get module name - skip version suffix like "v3" if present
modName := parts[len(parts)-1]
if len(parts) >= 2 && len(modName) >= 2 && modName[0] == 'v' && modName[1] >= '0' && modName[1] <= '9' {
modName = parts[len(parts)-2]
}
// Get path after version
afterAt := modPath[atIdx+1:]
if slashIdx := strings.Index(afterAt, "/"); slashIdx != -1 {
return fmt.Sprintf("%s%s:%d", modName, afterAt[slashIdx:], line)
}
}
}
// Fallback: show last 3 path components
parts := strings.Split(file, "/")
if len(parts) > 3 {
parts = parts[len(parts)-3:]
}
return fmt.Sprintf("%s:%d", strings.Join(parts, "/"), line)
}
func levelToString(l slog.Level) string {
switch l {
case slog.LevelDebug:
+55
View File
@@ -395,3 +395,58 @@ func ExampleSetupTestLogger() {
// cleanup() will restore the original logger when defer runs
}
func TestShortenSource(t *testing.T) {
tests := []struct {
name string
file string
line int
expected string
}{
{
name: "our code",
file: "/app/atcr.io/pkg/appview/jetstream/processor.go",
line: 73,
expected: "pkg/appview/jetstream/processor.go:73",
},
{
name: "indigo library",
file: "/go/pkg/mod/github.com/bluesky-social/indigo@v0.0.0-20251218205144-034a2c019e64/atproto/identity/handle.go",
line: 225,
expected: "indigo/atproto/identity/handle.go:225",
},
{
name: "distribution with v3 suffix",
file: "/go/pkg/mod/github.com/distribution/distribution/v3@v3.0.0-rc.3/registry/storage/driver.go",
line: 123,
expected: "distribution/registry/storage/driver.go:123",
},
{
name: "chi router",
file: "/go/pkg/mod/github.com/go-chi/chi/v5@v5.0.10/mux.go",
line: 42,
expected: "chi/mux.go:42",
},
{
name: "simple module without version suffix",
file: "/go/pkg/mod/github.com/ipfs/go-cid@v0.4.1/cid.go",
line: 99,
expected: "go-cid/cid.go:99",
},
{
name: "fallback - unknown path",
file: "/some/random/path/to/file.go",
line: 10,
expected: "path/to/file.go:10",
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
result := shortenSource(tt.file, tt.line)
if result != tt.expected {
t.Errorf("shortenSource(%q, %d) = %q, want %q", tt.file, tt.line, result, tt.expected)
}
})
}
}