Monorepo for Tangled tangled.org
6

Configure Feed

Select the types of activity you want to include in your feed.

at icy/yovxsu 5.3 kB View raw
1package pulls 2 3import ( 4 "context" 5 "encoding/json" 6 "io" 7 "log/slog" 8 "net/http" 9 "net/http/httptest" 10 "testing" 11 "time" 12 13 "github.com/bluesky-social/indigo/atproto/syntax" 14 "tangled.org/core/api/tangled" 15 "tangled.org/core/appview/config" 16 "tangled.org/core/appview/models" 17 "tangled.org/core/appview/pages" 18) 19 20const ( 21 resubmitTestOwnerDID = "did:plc:boltless" 22 resubmitTestRepoDID = "did:plc:akshay" 23 resubmitTestBranch = "feature" 24 resubmitTestSourceRev = "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa" 25) 26 27func newKnotmirrorStub(t *testing.T, hash string) *httptest.Server { 28 t.Helper() 29 return httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { 30 if r.URL.Path != "/xrpc/"+tangled.GitTempGetBranchNSID { 31 t.Errorf("unexpected path %q", r.URL.Path) 32 http.Error(w, "wrong path", http.StatusNotFound) 33 return 34 } 35 repoQuery := r.URL.Query().Get("repo") 36 if _, err := syntax.ParseDID(repoQuery); err != nil { 37 t.Errorf("repo param %q is not a DID: %v", repoQuery, err) 38 http.Error(w, "repo must be a DID", http.StatusBadRequest) 39 return 40 } 41 if got := r.URL.Query().Get("name"); got != resubmitTestBranch { 42 t.Errorf("name param = %q, want %q", got, resubmitTestBranch) 43 } 44 w.Header().Set("Content-Type", "application/json") 45 _ = json.NewEncoder(w).Encode(tangled.GitTempGetBranch_Output{ 46 Name: resubmitTestBranch, 47 Hash: hash, 48 When: time.Now().UTC().Format(time.RFC3339), 49 }) 50 })) 51} 52 53func newPullsFromKnotURL(url string) *Pulls { 54 return &Pulls{ 55 logger: slog.New(slog.NewTextHandler(io.Discard, nil)), 56 config: &config.Config{ 57 KnotMirror: config.KnotMirrorConfig{Url: url}, 58 }, 59 } 60} 61 62func newForkPull(state models.PullState) (*models.Pull, *models.Repo, models.Stack) { 63 sourceRepoDid := syntax.DID(resubmitTestRepoDID) 64 pull := &models.Pull{ 65 State: state, 66 OwnerDid: resubmitTestOwnerDID, 67 TargetBranch: "main", 68 Submissions: []*models.PullSubmission{ 69 {SourceRev: resubmitTestSourceRev}, 70 }, 71 PullSource: &models.PullSource{ 72 Branch: resubmitTestBranch, 73 RepoDid: &sourceRepoDid, 74 }, 75 } 76 repo := &models.Repo{RepoDid: resubmitTestRepoDID} 77 stack := models.Stack{pull} 78 return pull, repo, stack 79} 80 81func TestResubmitCheck_BranchAdvanced(t *testing.T) { 82 srv := newKnotmirrorStub(t, "bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb") 83 defer srv.Close() 84 85 s := newPullsFromKnotURL(srv.URL) 86 req := httptest.NewRequest(http.MethodGet, "/", nil) 87 pull, repo, stack := newForkPull(models.PullOpen) 88 89 got := s.resubmitCheck(req, repo, pull, stack) 90 if got != pages.ShouldResubmit { 91 t.Errorf("resubmitCheck() = %v, want ShouldResubmit", got) 92 } 93} 94 95func TestResubmitCheck_BranchUpToDate(t *testing.T) { 96 srv := newKnotmirrorStub(t, resubmitTestSourceRev) 97 defer srv.Close() 98 99 s := newPullsFromKnotURL(srv.URL) 100 req := httptest.NewRequest(http.MethodGet, "/", nil) 101 pull, repo, stack := newForkPull(models.PullOpen) 102 103 got := s.resubmitCheck(req, repo, pull, stack) 104 if got != pages.ShouldNotResubmit { 105 t.Errorf("resubmitCheck() = %v, want ShouldNotResubmit", got) 106 } 107} 108 109func TestResubmitCheck_MergedReturnsUnknown(t *testing.T) { 110 s := newPullsFromKnotURL("http://unused") 111 req := httptest.NewRequest(http.MethodGet, "/", nil) 112 pull, repo, stack := newForkPull(models.PullMerged) 113 114 if got := s.resubmitCheck(req, repo, pull, stack); got != pages.Unknown { 115 t.Errorf("resubmitCheck() = %v, want Unknown for merged pull", got) 116 } 117} 118 119func TestResubmitCheck_PatchBasedReturnsUnknown(t *testing.T) { 120 s := newPullsFromKnotURL("http://unused") 121 req := httptest.NewRequest(http.MethodGet, "/", nil) 122 pull, repo, stack := newForkPull(models.PullOpen) 123 pull.PullSource = nil 124 125 if got := s.resubmitCheck(req, repo, pull, stack); got != pages.Unknown { 126 t.Errorf("resubmitCheck() = %v, want Unknown for patch-based pull", got) 127 } 128} 129 130func TestResubmitCheck_KnotUnreachableReturnsUnknown(t *testing.T) { 131 s := newPullsFromKnotURL("http://127.0.0.1:1") 132 ctx, cancel := context.WithTimeout(context.Background(), 200*time.Millisecond) 133 defer cancel() 134 req := httptest.NewRequest(http.MethodGet, "/", nil).WithContext(ctx) 135 pull, repo, stack := newForkPull(models.PullOpen) 136 137 if got := s.resubmitCheck(req, repo, pull, stack); got != pages.Unknown { 138 t.Errorf("resubmitCheck() = %v, want Unknown when knot unreachable", got) 139 } 140} 141 142func TestResubmitCheck_NonForkUsesRepoDid(t *testing.T) { 143 const targetRepoDID = "did:plc:scallop" 144 srv := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { 145 if got := r.URL.Query().Get("repo"); got != targetRepoDID { 146 t.Errorf("repo param = %q, want %q for non-fork pull", got, targetRepoDID) 147 } 148 w.Header().Set("Content-Type", "application/json") 149 _ = json.NewEncoder(w).Encode(tangled.GitTempGetBranch_Output{ 150 Name: resubmitTestBranch, 151 Hash: resubmitTestSourceRev, 152 When: time.Now().UTC().Format(time.RFC3339), 153 }) 154 })) 155 defer srv.Close() 156 157 s := newPullsFromKnotURL(srv.URL) 158 req := httptest.NewRequest(http.MethodGet, "/", nil) 159 pull, _, stack := newForkPull(models.PullOpen) 160 pull.PullSource.RepoDid = nil 161 repo := &models.Repo{RepoDid: targetRepoDID} 162 163 if got := s.resubmitCheck(req, repo, pull, stack); got != pages.ShouldNotResubmit { 164 t.Errorf("resubmitCheck() = %v, want ShouldNotResubmit", got) 165 } 166}