Mirror of @tangled.org/core. Running on a Raspberry Pi Zero 2 (Please be gentle).

appview: use less `OwnerSlashRepo()` in handlers

Signed-off-by: Seongmin Lee <git@boltless.me>

authored by boltless.me and committed by

Tangled 7b60cbfc 4143799e

+112 -92
+9 -4
appview/issues/issues.go
··· 312 312 // notify about the issue closure 313 313 rp.notifier.NewIssueState(r.Context(), syntax.DID(user.Did), issue) 314 314 315 - rp.pages.HxLocation(w, fmt.Sprintf("/%s/issues/%d", f.OwnerSlashRepo(), issue.IssueId)) 315 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 316 + rp.pages.HxLocation(w, fmt.Sprintf("/%s/issues/%d", ownerSlashRepo, issue.IssueId)) 316 317 return 317 318 } else { 318 319 l.Error("user is not permitted to close issue") ··· 363 362 // notify about the issue reopen 364 363 rp.notifier.NewIssueState(r.Context(), syntax.DID(user.Did), issue) 365 364 366 - rp.pages.HxLocation(w, fmt.Sprintf("/%s/issues/%d", f.OwnerSlashRepo(), issue.IssueId)) 365 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 366 + rp.pages.HxLocation(w, fmt.Sprintf("/%s/issues/%d", ownerSlashRepo, issue.IssueId)) 367 367 return 368 368 } else { 369 369 l.Error("user is not the owner of the repo") ··· 468 466 } 469 467 rp.notifier.NewIssueComment(r.Context(), &comment, mentions) 470 468 471 - rp.pages.HxLocation(w, fmt.Sprintf("/%s/issues/%d#comment-%d", f.OwnerSlashRepo(), issue.IssueId, commentId)) 469 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 470 + rp.pages.HxLocation(w, fmt.Sprintf("/%s/issues/%d#comment-%d", ownerSlashRepo, issue.IssueId, commentId)) 472 471 } 473 472 474 473 func (rp *Issues) IssueComment(w http.ResponseWriter, r *http.Request) { ··· 991 988 } 992 989 } 993 990 rp.notifier.NewIssue(r.Context(), issue, mentions) 994 - rp.pages.HxLocation(w, fmt.Sprintf("/%s/issues/%d", f.OwnerSlashRepo(), issue.IssueId)) 991 + 992 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 993 + rp.pages.HxLocation(w, fmt.Sprintf("/%s/issues/%d", ownerSlashRepo, issue.IssueId)) 995 994 return 996 995 } 997 996 }
+2 -2
appview/middleware/middleware.go
··· 164 164 ok, err := mw.enforcer.E.Enforce(actor.Did, f.Knot, f.DidSlashRepo(), requiredPerm) 165 165 if err != nil || !ok { 166 166 // we need a logged in user 167 - log.Printf("%s does not have perms of a %s in repo %s", actor.Did, requiredPerm, f.OwnerSlashRepo()) 167 + log.Printf("%s does not have perms of a %s in repo %s", actor.Did, requiredPerm, f.DidSlashRepo()) 168 168 http.Error(w, "Forbiden", http.StatusUnauthorized) 169 169 return 170 170 } ··· 327 327 return 328 328 } 329 329 330 - fullName := f.OwnerHandle() + "/" + f.Name 330 + fullName := reporesolver.GetBaseRepoPath(r, &f.Repo) 331 331 332 332 if r.Header.Get("User-Agent") == "Go-http-client/1.1" { 333 333 if r.URL.Query().Get("go-get") == "1" {
+2 -2
appview/pages/repoinfo/repoinfo.go
··· 21 21 return path.Join(r.owner(), r.Name) 22 22 } 23 23 24 - func (r RepoInfo) OwnerWithoutAt() string { 24 + func (r RepoInfo) ownerWithoutAt() string { 25 25 if r.OwnerHandle != "" { 26 26 return r.OwnerHandle 27 27 } else { ··· 30 30 } 31 31 32 32 func (r RepoInfo) FullNameWithoutAt() string { 33 - return path.Join(r.OwnerWithoutAt(), r.Name) 33 + return path.Join(r.ownerWithoutAt(), r.Name) 34 34 } 35 35 36 36 func (r RepoInfo) GetTabs() [][]string {
+24 -16
appview/pulls/pulls.go
··· 268 268 r.Context(), 269 269 &xrpcc, 270 270 &tangled.RepoMergeCheck_Input{ 271 - Did: f.OwnerDid(), 271 + Did: f.Did, 272 272 Name: f.Name, 273 273 Branch: pull.TargetBranch, 274 274 Patch: patch, ··· 382 382 } else { 383 383 // pulls within the same repo 384 384 knot = f.Knot 385 - ownerDid = f.OwnerDid() 385 + ownerDid = f.Did 386 386 repoName = f.Name 387 387 } 388 388 ··· 802 802 } 803 803 s.notifier.NewPullComment(r.Context(), comment, mentions) 804 804 805 - s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d#comment-%d", f.OwnerSlashRepo(), pull.PullId, commentId)) 805 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 806 + s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d#comment-%d", ownerSlashRepo, pull.PullId, commentId)) 806 807 return 807 808 } 808 809 } ··· 827 826 Host: host, 828 827 } 829 828 830 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 829 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 831 830 xrpcBytes, err := tangled.RepoBranches(r.Context(), xrpcc, "", 0, repo) 832 831 if err != nil { 833 832 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { ··· 992 991 Host: host, 993 992 } 994 993 995 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 994 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 996 995 xrpcBytes, err := tangled.RepoCompare(r.Context(), xrpcc, repo, targetBranch, sourceBranch) 997 996 if err != nil { 998 997 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { ··· 1274 1273 1275 1274 s.notifier.NewPull(r.Context(), pull) 1276 1275 1277 - s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", f.OwnerSlashRepo(), pullId)) 1276 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 1277 + s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", ownerSlashRepo, pullId)) 1278 1278 } 1279 1279 1280 1280 func (s *Pulls) createStackedPullRequest( ··· 1376 1374 return 1377 1375 } 1378 1376 1379 - s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls", f.OwnerSlashRepo())) 1377 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 1378 + s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls", ownerSlashRepo)) 1380 1379 } 1381 1380 1382 1381 func (s *Pulls) ValidatePatch(w http.ResponseWriter, r *http.Request) { ··· 1436 1433 Host: host, 1437 1434 } 1438 1435 1439 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 1436 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 1440 1437 xrpcBytes, err := tangled.RepoBranches(r.Context(), xrpcc, "", 0, repo) 1441 1438 if err != nil { 1442 1439 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { ··· 1557 1554 Host: targetHost, 1558 1555 } 1559 1556 1560 - targetRepo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 1557 + targetRepo := fmt.Sprintf("%s/%s", f.Did, f.Name) 1561 1558 targetXrpcBytes, err := tangled.RepoBranches(r.Context(), targetXrpcc, "", 0, targetRepo) 1562 1559 if err != nil { 1563 1560 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { ··· 1688 1685 Host: host, 1689 1686 } 1690 1687 1691 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 1688 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 1692 1689 xrpcBytes, err := tangled.RepoCompare(r.Context(), xrpcc, repo, pull.TargetBranch, pull.PullSource.Branch) 1693 1690 if err != nil { 1694 1691 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { ··· 1925 1922 return 1926 1923 } 1927 1924 1928 - s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", f.OwnerSlashRepo(), pull.PullId)) 1925 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 1926 + s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", ownerSlashRepo, pull.PullId)) 1929 1927 } 1930 1928 1931 1929 func (s *Pulls) resubmitStackedPullHelper( ··· 2119 2115 return 2120 2116 } 2121 2117 2122 - s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", f.OwnerSlashRepo(), pull.PullId)) 2118 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 2119 + s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", ownerSlashRepo, pull.PullId)) 2123 2120 } 2124 2121 2125 2122 func (s *Pulls) MergePull(w http.ResponseWriter, r *http.Request) { ··· 2173 2168 2174 2169 authorName := ident.Handle.String() 2175 2170 mergeInput := &tangled.RepoMerge_Input{ 2176 - Did: f.OwnerDid(), 2171 + Did: f.Did, 2177 2172 Name: f.Name, 2178 2173 Branch: pull.TargetBranch, 2179 2174 Patch: patch, ··· 2238 2233 s.notifier.NewPullState(r.Context(), syntax.DID(user.Did), p) 2239 2234 } 2240 2235 2241 - s.pages.HxLocation(w, fmt.Sprintf("/@%s/%s/pulls/%d", f.OwnerHandle(), f.Name, pull.PullId)) 2236 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 2237 + s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", ownerSlashRepo, pull.PullId)) 2242 2238 } 2243 2239 2244 2240 func (s *Pulls) ClosePull(w http.ResponseWriter, r *http.Request) { ··· 2311 2305 s.notifier.NewPullState(r.Context(), syntax.DID(user.Did), p) 2312 2306 } 2313 2307 2314 - s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", f.OwnerSlashRepo(), pull.PullId)) 2308 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 2309 + s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", ownerSlashRepo, pull.PullId)) 2315 2310 } 2316 2311 2317 2312 func (s *Pulls) ReopenPull(w http.ResponseWriter, r *http.Request) { ··· 2385 2378 s.notifier.NewPullState(r.Context(), syntax.DID(user.Did), p) 2386 2379 } 2387 2380 2388 - s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", f.OwnerSlashRepo(), pull.PullId)) 2381 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 2382 + s.pages.HxLocation(w, fmt.Sprintf("/%s/pulls/%d", ownerSlashRepo, pull.PullId)) 2389 2383 } 2390 2384 2391 2385 func newStack(f *reporesolver.ResolvedRepo, user *oauth.User, targetBranch, patch string, pullSource *models.PullSource, stackId string) (models.Stack, error) {
+2 -2
appview/repo/archive.go
··· 31 31 xrpcc := &indigoxrpc.Client{ 32 32 Host: host, 33 33 } 34 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 35 - archiveBytes, err := tangled.RepoArchive(r.Context(), xrpcc, "tar.gz", "", ref, repo) 34 + didSlashRepo := f.DidSlashRepo() 35 + archiveBytes, err := tangled.RepoArchive(r.Context(), xrpcc, "tar.gz", "", ref, didSlashRepo) 36 36 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 37 37 l.Error("failed to call XRPC repo.archive", "err", xrpcerr) 38 38 rp.pages.Error503(w)
+9 -2
appview/repo/artifact.go
··· 174 174 175 175 artifact := artifacts[0] 176 176 177 - ownerPds := f.OwnerId.PDSEndpoint() 177 + ownerId, err := rp.idResolver.ResolveIdent(r.Context(), f.Did) 178 + if err != nil { 179 + log.Println("failed to resolve repo owner did", f.Did, err) 180 + http.Error(w, "repository owner not found", http.StatusNotFound) 181 + return 182 + } 183 + 184 + ownerPds := ownerId.PDSEndpoint() 178 185 url, _ := url.Parse(fmt.Sprintf("%s/xrpc/com.atproto.sync.getBlob", ownerPds)) 179 186 q := url.Query() 180 187 q.Set("cid", artifact.BlobCid.String()) ··· 312 305 Host: host, 313 306 } 314 307 315 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 308 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 316 309 xrpcBytes, err := tangled.RepoTags(ctx, xrpcc, "", 0, repo) 317 310 if err != nil { 318 311 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil {
+6 -4
appview/repo/blob.go
··· 54 54 xrpcc := &indigoxrpc.Client{ 55 55 Host: host, 56 56 } 57 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Repo.Name) 57 + repo := fmt.Sprintf("%s/%s", f.Did, f.Repo.Name) 58 58 resp, err := tangled.RepoBlob(r.Context(), xrpcc, filePath, false, ref, repo) 59 59 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 60 60 l.Error("failed to call XRPC repo.blob", "err", xrpcerr) ··· 62 62 return 63 63 } 64 64 65 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 66 + 65 67 // Use XRPC response directly instead of converting to internal types 66 68 var breadcrumbs [][]string 67 - breadcrumbs = append(breadcrumbs, []string{f.Name, fmt.Sprintf("/%s/tree/%s", f.OwnerSlashRepo(), url.PathEscape(ref))}) 69 + breadcrumbs = append(breadcrumbs, []string{f.Name, fmt.Sprintf("/%s/tree/%s", ownerSlashRepo, url.PathEscape(ref))}) 68 70 if filePath != "" { 69 71 for idx, elem := range strings.Split(filePath, "/") { 70 72 breadcrumbs = append(breadcrumbs, []string{elem, fmt.Sprintf("%s/%s", breadcrumbs[idx][1], url.PathEscape(elem))}) ··· 107 105 if !rp.config.Core.Dev { 108 106 scheme = "https" 109 107 } 110 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Repo.Name) 108 + repo := fmt.Sprintf("%s/%s", f.Did, f.Repo.Name) 111 109 baseURL := &url.URL{ 112 110 Scheme: scheme, 113 111 Host: f.Knot, ··· 258 256 scheme = "https" 259 257 } 260 258 261 - repoName := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 259 + repoName := fmt.Sprintf("%s/%s", f.Did, f.Name) 262 260 baseURL := &url.URL{ 263 261 Scheme: scheme, 264 262 Host: f.Knot,
+1 -1
appview/repo/branches.go
··· 29 29 xrpcc := &indigoxrpc.Client{ 30 30 Host: host, 31 31 } 32 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 32 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 33 33 xrpcBytes, err := tangled.RepoBranches(r.Context(), xrpcc, "", 0, repo) 34 34 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 35 35 l.Error("failed to call XRPC repo.branches", "err", xrpcerr)
+2 -2
appview/repo/compare.go
··· 36 36 Host: host, 37 37 } 38 38 39 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 39 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 40 40 branchBytes, err := tangled.RepoBranches(r.Context(), xrpcc, "", 0, repo) 41 41 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 42 42 l.Error("failed to call XRPC repo.branches", "err", xrpcerr) ··· 151 151 Host: host, 152 152 } 153 153 154 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 154 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 155 155 156 156 branchBytes, err := tangled.RepoBranches(r.Context(), xrpcc, "", 0, repo) 157 157 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil {
+23 -17
appview/repo/feed.go
··· 11 11 "tangled.org/core/appview/db" 12 12 "tangled.org/core/appview/models" 13 13 "tangled.org/core/appview/pagination" 14 - "tangled.org/core/appview/reporesolver" 15 14 15 + "github.com/bluesky-social/indigo/atproto/identity" 16 16 "github.com/bluesky-social/indigo/atproto/syntax" 17 17 "github.com/gorilla/feeds" 18 18 ) 19 19 20 - func (rp *Repo) getRepoFeed(ctx context.Context, f *reporesolver.ResolvedRepo) (*feeds.Feed, error) { 20 + func (rp *Repo) getRepoFeed(ctx context.Context, repo *models.Repo, ownerSlashRepo string) (*feeds.Feed, error) { 21 21 const feedLimitPerType = 100 22 22 23 - pulls, err := db.GetPullsWithLimit(rp.db, feedLimitPerType, db.FilterEq("repo_at", f.RepoAt())) 23 + pulls, err := db.GetPullsWithLimit(rp.db, feedLimitPerType, db.FilterEq("repo_at", repo.RepoAt())) 24 24 if err != nil { 25 25 return nil, err 26 26 } ··· 28 28 issues, err := db.GetIssuesPaginated( 29 29 rp.db, 30 30 pagination.Page{Limit: feedLimitPerType}, 31 - db.FilterEq("repo_at", f.RepoAt()), 31 + db.FilterEq("repo_at", repo.RepoAt()), 32 32 ) 33 33 if err != nil { 34 34 return nil, err 35 35 } 36 36 37 37 feed := &feeds.Feed{ 38 - Title: fmt.Sprintf("activity feed for %s", f.OwnerSlashRepo()), 39 - Link: &feeds.Link{Href: fmt.Sprintf("%s/%s", rp.config.Core.AppviewHost, f.OwnerSlashRepo()), Type: "text/html", Rel: "alternate"}, 38 + Title: fmt.Sprintf("activity feed for @%s", ownerSlashRepo), 39 + Link: &feeds.Link{Href: fmt.Sprintf("%s/%s", rp.config.Core.AppviewHost, ownerSlashRepo), Type: "text/html", Rel: "alternate"}, 40 40 Items: make([]*feeds.Item, 0), 41 41 Updated: time.UnixMilli(0), 42 42 } 43 43 44 44 for _, pull := range pulls { 45 - items, err := rp.createPullItems(ctx, pull, f) 45 + items, err := rp.createPullItems(ctx, pull, repo, ownerSlashRepo) 46 46 if err != nil { 47 47 return nil, err 48 48 } ··· 50 50 } 51 51 52 52 for _, issue := range issues { 53 - item, err := rp.createIssueItem(ctx, issue, f) 53 + item, err := rp.createIssueItem(ctx, issue, repo, ownerSlashRepo) 54 54 if err != nil { 55 55 return nil, err 56 56 } ··· 71 71 return feed, nil 72 72 } 73 73 74 - func (rp *Repo) createPullItems(ctx context.Context, pull *models.Pull, f *reporesolver.ResolvedRepo) ([]*feeds.Item, error) { 74 + func (rp *Repo) createPullItems(ctx context.Context, pull *models.Pull, repo *models.Repo, ownerSlashRepo string) ([]*feeds.Item, error) { 75 75 owner, err := rp.idResolver.ResolveIdent(ctx, pull.OwnerDid) 76 76 if err != nil { 77 77 return nil, err ··· 80 80 var items []*feeds.Item 81 81 82 82 state := rp.getPullState(pull) 83 - description := rp.buildPullDescription(owner.Handle, state, pull, f.OwnerSlashRepo()) 83 + description := rp.buildPullDescription(owner.Handle, state, pull, ownerSlashRepo) 84 84 85 85 mainItem := &feeds.Item{ 86 86 Title: fmt.Sprintf("[PR #%d] %s", pull.PullId, pull.Title), 87 87 Description: description, 88 - Link: &feeds.Link{Href: fmt.Sprintf("%s/%s/pulls/%d", rp.config.Core.AppviewHost, f.OwnerSlashRepo(), pull.PullId)}, 88 + Link: &feeds.Link{Href: fmt.Sprintf("%s/%s/pulls/%d", rp.config.Core.AppviewHost, ownerSlashRepo, pull.PullId)}, 89 89 Created: pull.Created, 90 90 Author: &feeds.Author{Name: fmt.Sprintf("@%s", owner.Handle)}, 91 91 } ··· 98 98 99 99 roundItem := &feeds.Item{ 100 100 Title: fmt.Sprintf("[PR #%d] %s (round #%d)", pull.PullId, pull.Title, round.RoundNumber), 101 - Description: fmt.Sprintf("@%s submitted changes (at round #%d) on PR #%d in %s", owner.Handle, round.RoundNumber, pull.PullId, f.OwnerSlashRepo()), 102 - Link: &feeds.Link{Href: fmt.Sprintf("%s/%s/pulls/%d/round/%d/", rp.config.Core.AppviewHost, f.OwnerSlashRepo(), pull.PullId, round.RoundNumber)}, 101 + Description: fmt.Sprintf("@%s submitted changes (at round #%d) on PR #%d in @%s", owner.Handle, round.RoundNumber, pull.PullId, ownerSlashRepo), 102 + Link: &feeds.Link{Href: fmt.Sprintf("%s/%s/pulls/%d/round/%d/", rp.config.Core.AppviewHost, ownerSlashRepo, pull.PullId, round.RoundNumber)}, 103 103 Created: round.Created, 104 104 Author: &feeds.Author{Name: fmt.Sprintf("@%s", owner.Handle)}, 105 105 } ··· 109 109 return items, nil 110 110 } 111 111 112 - func (rp *Repo) createIssueItem(ctx context.Context, issue models.Issue, f *reporesolver.ResolvedRepo) (*feeds.Item, error) { 112 + func (rp *Repo) createIssueItem(ctx context.Context, issue models.Issue, repo *models.Repo, ownerSlashRepo string) (*feeds.Item, error) { 113 113 owner, err := rp.idResolver.ResolveIdent(ctx, issue.Did) 114 114 if err != nil { 115 115 return nil, err ··· 122 122 123 123 return &feeds.Item{ 124 124 Title: fmt.Sprintf("[Issue #%d] %s", issue.IssueId, issue.Title), 125 - Description: fmt.Sprintf("@%s %s issue #%d in %s", owner.Handle, state, issue.IssueId, f.OwnerSlashRepo()), 126 - Link: &feeds.Link{Href: fmt.Sprintf("%s/%s/issues/%d", rp.config.Core.AppviewHost, f.OwnerSlashRepo(), issue.IssueId)}, 125 + Description: fmt.Sprintf("@%s %s issue #%d in @%s", owner.Handle, state, issue.IssueId, ownerSlashRepo), 126 + Link: &feeds.Link{Href: fmt.Sprintf("%s/%s/issues/%d", rp.config.Core.AppviewHost, ownerSlashRepo, issue.IssueId)}, 127 127 Created: issue.Created, 128 128 Author: &feeds.Author{Name: fmt.Sprintf("@%s", owner.Handle)}, 129 129 }, nil ··· 152 152 log.Println("failed to fully resolve repo:", err) 153 153 return 154 154 } 155 + repoOwnerId, ok := r.Context().Value("resolvedId").(identity.Identity) 156 + if !ok || repoOwnerId.Handle.IsInvalidHandle() { 157 + log.Println("failed to get resolved repo owner id") 158 + return 159 + } 160 + ownerSlashRepo := repoOwnerId.Handle.String() + "/" + f.Name 155 161 156 - feed, err := rp.getRepoFeed(r.Context(), f) 162 + feed, err := rp.getRepoFeed(r.Context(), &f.Repo, ownerSlashRepo) 157 163 if err != nil { 158 164 log.Println("failed to get repo feed:", err) 159 165 rp.pages.Error500(w)
+2 -2
appview/repo/index.go
··· 179 179 180 180 if err != nil || langs == nil { 181 181 // non-fatal, fetch langs from ks via XRPC 182 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 182 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 183 183 ls, err := tangled.RepoLanguages(ctx, xrpcc, currentRef, repo) 184 184 if err != nil { 185 185 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { ··· 256 256 257 257 // buildIndexResponse creates a RepoIndexResponse by combining multiple xrpc calls in parallel 258 258 func (rp *Repo) buildIndexResponse(ctx context.Context, xrpcc *indigoxrpc.Client, f *reporesolver.ResolvedRepo, ref string) (*types.RepoIndexResponse, error) { 259 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 259 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 260 260 261 261 // first get branches to determine the ref if not specified 262 262 branchesBytes, err := tangled.RepoBranches(ctx, xrpcc, "", 0, repo)
+2 -2
appview/repo/log.go
··· 57 57 cursor = strconv.Itoa(offset) 58 58 } 59 59 60 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 60 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 61 61 xrpcBytes, err := tangled.RepoLog(r.Context(), xrpcc, cursor, limit, "", ref, repo) 62 62 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 63 63 l.Error("failed to call XRPC repo.log", "err", xrpcerr) ··· 174 174 Host: host, 175 175 } 176 176 177 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 177 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 178 178 xrpcBytes, err := tangled.RepoDiff(r.Context(), xrpcc, ref, repo) 179 179 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 180 180 l.Error("failed to call XRPC repo.diff", "err", xrpcerr)
+5 -5
appview/repo/repo.go
··· 864 864 r.Context(), 865 865 client, 866 866 &tangled.RepoDelete_Input{ 867 - Did: f.OwnerDid(), 867 + Did: f.Did, 868 868 Name: f.Name, 869 869 Rkey: f.Rkey, 870 870 }, ··· 902 902 l.Info("removed collaborators") 903 903 904 904 // remove repo RBAC 905 - err = rp.enforcer.RemoveRepo(f.OwnerDid(), f.Knot, f.DidSlashRepo()) 905 + err = rp.enforcer.RemoveRepo(f.Did, f.Knot, f.DidSlashRepo()) 906 906 if err != nil { 907 907 rp.pages.Notice(w, noticeId, "Failed to update RBAC rules") 908 908 return 909 909 } 910 910 911 911 // remove repo from db 912 - err = db.RemoveRepo(tx, f.OwnerDid(), f.Name) 912 + err = db.RemoveRepo(tx, f.Did, f.Name) 913 913 if err != nil { 914 914 rp.pages.Notice(w, noticeId, "Failed to update appview") 915 915 return ··· 930 930 return 931 931 } 932 932 933 - rp.pages.HxRedirect(w, fmt.Sprintf("/%s", f.OwnerDid())) 933 + rp.pages.HxRedirect(w, fmt.Sprintf("/%s", f.Did)) 934 934 } 935 935 936 936 func (rp *Repo) SyncRepoFork(w http.ResponseWriter, r *http.Request) { ··· 1058 1058 uri = "http" 1059 1059 } 1060 1060 1061 - forkSourceUrl := fmt.Sprintf("%s://%s/%s/%s", uri, f.Knot, f.OwnerDid(), f.Repo.Name) 1061 + forkSourceUrl := fmt.Sprintf("%s://%s/%s/%s", uri, f.Knot, f.Did, f.Repo.Name) 1062 1062 l = l.With("cloneUrl", forkSourceUrl) 1063 1063 1064 1064 sourceAt := f.RepoAt().String()
+2 -2
appview/repo/settings.go
··· 194 194 Host: host, 195 195 } 196 196 197 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 197 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 198 198 xrpcBytes, err := tangled.RepoBranches(r.Context(), xrpcc, "", 0, repo) 199 199 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 200 200 l.Error("failed to call XRPC repo.branches", "err", xrpcerr) ··· 292 292 user := rp.oauth.GetUser(r) 293 293 294 294 // all spindles that the repo owner is a member of 295 - spindles, err := rp.enforcer.GetSpindlesForUser(f.OwnerDid()) 295 + spindles, err := rp.enforcer.GetSpindlesForUser(f.Did) 296 296 if err != nil { 297 297 l.Error("failed to fetch spindles", "err", err) 298 298 return
+1 -1
appview/repo/tags.go
··· 31 31 xrpcc := &indigoxrpc.Client{ 32 32 Host: host, 33 33 } 34 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 34 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 35 35 xrpcBytes, err := tangled.RepoTags(r.Context(), xrpcc, "", 0, repo) 36 36 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 37 37 l.Error("failed to call XRPC repo.tags", "err", xrpcerr)
+5 -3
appview/repo/tree.go
··· 9 9 10 10 "tangled.org/core/api/tangled" 11 11 "tangled.org/core/appview/pages" 12 + "tangled.org/core/appview/reporesolver" 12 13 xrpcclient "tangled.org/core/appview/xrpcclient" 13 14 "tangled.org/core/types" 14 15 ··· 40 39 xrpcc := &indigoxrpc.Client{ 41 40 Host: host, 42 41 } 43 - repo := fmt.Sprintf("%s/%s", f.OwnerDid(), f.Name) 42 + repo := fmt.Sprintf("%s/%s", f.Did, f.Name) 44 43 xrpcResp, err := tangled.RepoTree(r.Context(), xrpcc, treePath, ref, repo) 45 44 if xrpcerr := xrpcclient.HandleXrpcErr(err); xrpcerr != nil { 46 45 l.Error("failed to call XRPC repo.tree", "err", xrpcerr) ··· 80 79 result.ReadmeFileName = xrpcResp.Readme.Filename 81 80 result.Readme = xrpcResp.Readme.Contents 82 81 } 82 + ownerSlashRepo := reporesolver.GetBaseRepoPath(r, &f.Repo) 83 83 // redirects tree paths trying to access a blob; in this case the result.Files is unpopulated, 84 84 // so we can safely redirect to the "parent" (which is the same file). 85 85 if len(result.Files) == 0 && result.Parent == treePath { 86 - redirectTo := fmt.Sprintf("/%s/blob/%s/%s", f.OwnerSlashRepo(), url.PathEscape(ref), result.Parent) 86 + redirectTo := fmt.Sprintf("/%s/blob/%s/%s", ownerSlashRepo, url.PathEscape(ref), result.Parent) 87 87 http.Redirect(w, r, redirectTo, http.StatusFound) 88 88 return 89 89 } 90 90 user := rp.oauth.GetUser(r) 91 91 var breadcrumbs [][]string 92 - breadcrumbs = append(breadcrumbs, []string{f.Name, fmt.Sprintf("/%s/tree/%s", f.OwnerSlashRepo(), url.PathEscape(ref))}) 92 + breadcrumbs = append(breadcrumbs, []string{f.Name, fmt.Sprintf("/%s/tree/%s", ownerSlashRepo, url.PathEscape(ref))}) 93 93 if treePath != "" { 94 94 for idx, elem := range strings.Split(treePath, "/") { 95 95 breadcrumbs = append(breadcrumbs, []string{elem, fmt.Sprintf("%s/%s", breadcrumbs[idx][1], url.PathEscape(elem))})
+15 -25
appview/reporesolver/resolver.go
··· 12 12 "strings" 13 13 14 14 "github.com/bluesky-social/indigo/atproto/identity" 15 - securejoin "github.com/cyphar/filepath-securejoin" 16 15 "github.com/go-chi/chi/v5" 17 16 "tangled.org/core/appview/config" 18 17 "tangled.org/core/appview/db" ··· 43 44 return &RepoResolver{config: config, enforcer: enforcer, idResolver: resolver, execer: execer} 44 45 } 45 46 47 + // NOTE: this... should not even be here. the entire package will be removed in future refactor 48 + func GetBaseRepoPath(r *http.Request, repo *models.Repo) string { 49 + var ( 50 + user = chi.URLParam(r, "user") 51 + name = chi.URLParam(r, "repo") 52 + ) 53 + if user == "" || name == "" { 54 + return repo.DidSlashRepo() 55 + } 56 + return path.Join(user, name) 57 + } 58 + 46 59 func (rr *RepoResolver) Resolve(r *http.Request) (*ResolvedRepo, error) { 47 60 repo, ok := r.Context().Value("repo").(*models.Repo) 48 61 if !ok { ··· 78 67 79 68 rr: rr, 80 69 }, nil 81 - } 82 - 83 - func (f *ResolvedRepo) OwnerDid() string { 84 - return f.OwnerId.DID.String() 85 - } 86 - 87 - func (f *ResolvedRepo) OwnerHandle() string { 88 - return f.OwnerId.Handle.String() 89 - } 90 - 91 - func (f *ResolvedRepo) OwnerSlashRepo() string { 92 - handle := f.OwnerId.Handle 93 - 94 - var p string 95 - if handle != "" && !handle.IsInvalidHandle() { 96 - p, _ = securejoin.SecureJoin(fmt.Sprintf("@%s", handle), f.Name) 97 - } else { 98 - p, _ = securejoin.SecureJoin(f.OwnerDid(), f.Name) 99 - } 100 - 101 - return p 102 70 } 103 71 104 72 func (f *ResolvedRepo) Collaborators(ctx context.Context) ([]pages.Collaborator, error) { ··· 158 168 knot := f.Knot 159 169 160 170 repoInfo := repoinfo.RepoInfo{ 161 - OwnerDid: f.OwnerDid(), 162 - OwnerHandle: f.OwnerHandle(), 171 + OwnerDid: f.OwnerId.DID.String(), 172 + OwnerHandle: f.OwnerId.Handle.String(), 163 173 Name: f.Name, 164 - Rkey: f.Repo.Rkey, 174 + Rkey: f.Rkey, 165 175 RepoAt: repoAt, 166 176 Description: f.Description, 167 177 Website: f.Website,