+17
appview/pages/pages.go
+17
appview/pages/pages.go
···
634
634
return p.execute("repo/pulls/patch", w, params)
635
635
}
636
636
637
+
type PullPatchUploadParams struct {
638
+
RepoInfo RepoInfo
639
+
}
640
+
641
+
func (p *Pages) PullPatchUploadFragment(w io.Writer, params PullPatchUploadParams) error {
642
+
return p.executePlain("fragments/pullPatchUpload", w, params)
643
+
}
644
+
645
+
type PullCompareBranchesParams struct {
646
+
RepoInfo RepoInfo
647
+
Branches []types.Branch
648
+
}
649
+
650
+
func (p *Pages) PullCompareBranchesFragment(w io.Writer, params PullCompareBranchesParams) error {
651
+
return p.executePlain("fragments/pullCompareBranches", w, params)
652
+
}
653
+
637
654
type PullResubmitParams struct {
638
655
LoggedInUser *auth.User
639
656
RepoInfo RepoInfo
+46
appview/pages/templates/fragments/pullCompareBranches.html
+46
appview/pages/templates/fragments/pullCompareBranches.html
···
1
+
{{ define "fragments/pullCompareBranches" }}
2
+
<div id="patch-upload">
3
+
<label for="targetBranch" class="dark:text-white">configure branches</label>
4
+
<div class="flex flex-wrap gap-2 items-center">
5
+
<select
6
+
required
7
+
name="targetBranch"
8
+
class="p-1 border border-gray-200 bg-white dark:bg-gray-700 dark:text-white dark:border-gray-600"
9
+
>
10
+
<option disabled selected>target branch</option>
11
+
{{ range .Branches }}
12
+
<option value="{{ .Reference.Name }}" class="py-1">
13
+
{{ .Reference.Name }}
14
+
</option>
15
+
{{ end }}
16
+
</select>
17
+
18
+
{{ i "move-left" "w-5 h-5" }}
19
+
20
+
<select
21
+
name="sourceBranch"
22
+
class="p-1 border border-gray-200 bg-white dark:bg-gray-700 dark:text-white dark:border-gray-600"
23
+
>
24
+
<option disabled selected>source branch</option>
25
+
{{ range .Branches }}
26
+
<option value="{{ .Reference.Name }}" class="py-1">
27
+
{{ .Reference.Name }}
28
+
</option>
29
+
{{ end }}
30
+
</select>
31
+
32
+
<span class="text-sm">
33
+
... or upload a patch
34
+
<button
35
+
class="btn text-sm"
36
+
hx-get="/{{ .RepoInfo.FullName }}/pulls/new/patch-upload"
37
+
hx-swap="outerHTML"
38
+
hx-target="#patch-upload"
39
+
>
40
+
upload patch
41
+
</button>
42
+
</span>
43
+
</div>
44
+
45
+
</div>
46
+
{{ end }}
+26
appview/pages/templates/fragments/pullPatchUpload.html
+26
appview/pages/templates/fragments/pullPatchUpload.html
···
1
+
{{ define "fragments/pullPatchUpload" }}
2
+
<div id="patch-upload">
3
+
<label for="patch" class="dark:text-white">paste your patch here</label>
4
+
<textarea
5
+
name="patch"
6
+
id="patch"
7
+
rows="10"
8
+
class="w-full resize-y font-mono dark:bg-gray-700 dark:text-white dark:border-gray-600"
9
+
placeholder="Paste your git diff output here."
10
+
></textarea>
11
+
12
+
{{ if .RepoInfo.Roles.IsPushAllowed }}
13
+
<div class="mt-4 text-sm">
14
+
you can also submit a pull request from a branch
15
+
<button
16
+
class="btn text-sm"
17
+
hx-get="/{{ .RepoInfo.FullName }}/pulls/new/compare-branches"
18
+
hx-swap="outerHTML"
19
+
hx-target="#patch-upload"
20
+
>
21
+
compare branches
22
+
</button>
23
+
</div>
24
+
{{ end }}
25
+
</div>
26
+
{{ end }}
+5
-51
appview/pages/templates/repo/pulls/new.html
+5
-51
appview/pages/templates/repo/pulls/new.html
···
35
35
></textarea>
36
36
</div>
37
37
38
-
<div>
39
-
<label for="targetBranch" class="dark:text-white">configure branches</label>
40
-
<div class="flex flex-wrap gap-2 items-center">
41
-
<select
42
-
required
43
-
name="targetBranch"
44
-
class="p-1 border border-gray-200 bg-white dark:bg-gray-700 dark:text-white dark:border-gray-600"
45
-
>
46
-
<option disabled selected>target branch</option>
47
-
{{ range .Branches }}
48
-
<option value="{{ .Reference.Name }}" class="py-1">
49
-
{{ .Reference.Name }}
50
-
</option>
51
-
{{ end }}
52
-
</select>
53
-
54
-
{{ if .RepoInfo.Roles.IsPushAllowed }}
55
-
{{ i "move-left" "w-5 h-5" }}
56
-
<select
57
-
name="sourceBranch"
58
-
class="p-1 border border-gray-200 bg-white dark:bg-gray-700 dark:text-white dark:border-gray-600"
59
-
>
60
-
<option disabled selected>source branch</option>
61
-
{{ range .Branches }}
62
-
<option value="{{ .Reference.Name }}" class="py-1">
63
-
{{ .Reference.Name }}
64
-
</option>
65
-
{{ end }}
66
-
</select>
67
-
{{ end }}
68
-
69
-
</div>
70
-
</div>
71
-
72
-
<div class="mt-4">
73
-
{{ $label := "paste your patch here" }}
74
-
{{ $rows := 10 }}
75
-
{{ if .RepoInfo.Roles.IsPushAllowed }}
76
-
{{ $label = "or paste your patch here" }}
77
-
{{ $rows = 4 }}
78
-
{{ end }}
79
-
80
-
<label for="patch" class="dark:text-white">{{ $label }}</label>
81
-
<textarea
82
-
name="patch"
83
-
id="patch"
84
-
rows="{{$rows}}"
85
-
class="w-full resize-y font-mono dark:bg-gray-700 dark:text-white dark:border-gray-600"
86
-
placeholder="Paste your git diff output here."
87
-
></textarea>
88
-
</div>
38
+
{{ if not .RepoInfo.Roles.IsPushAllowed }}
39
+
{{ template "fragments/pullPatchUpload" . }}
40
+
{{ else }}
41
+
{{ template "fragments/pullCompareBranches" . }}
42
+
{{ end }}
89
43
90
44
<div class="flex justify-end items-center gap-2">
91
45
<button type="submit" class="btn">create</button>
+53
appview/state/pull.go
+53
appview/state/pull.go
···
643
643
}
644
644
}
645
645
646
+
func (s *State) PatchUploadFragment(w http.ResponseWriter, r *http.Request) {
647
+
user := s.auth.GetUser(r)
648
+
f, err := fullyResolvedRepo(r)
649
+
if err != nil {
650
+
log.Println("failed to get repo and knot", err)
651
+
return
652
+
}
653
+
654
+
s.pages.PullPatchUploadFragment(w, pages.PullPatchUploadParams{
655
+
RepoInfo: f.RepoInfo(s, user),
656
+
})
657
+
}
658
+
659
+
func (s *State) CompareBranchesFragment(w http.ResponseWriter, r *http.Request) {
660
+
user := s.auth.GetUser(r)
661
+
f, err := fullyResolvedRepo(r)
662
+
if err != nil {
663
+
log.Println("failed to get repo and knot", err)
664
+
return
665
+
}
666
+
667
+
us, err := NewUnsignedClient(f.Knot, s.config.Dev)
668
+
if err != nil {
669
+
log.Printf("failed to create unsigned client for %s", f.Knot)
670
+
s.pages.Error503(w)
671
+
return
672
+
}
673
+
674
+
resp, err := us.Branches(f.OwnerDid(), f.RepoName)
675
+
if err != nil {
676
+
log.Println("failed to reach knotserver", err)
677
+
return
678
+
}
679
+
680
+
body, err := io.ReadAll(resp.Body)
681
+
if err != nil {
682
+
log.Printf("Error reading response body: %v", err)
683
+
return
684
+
}
685
+
686
+
var result types.RepoBranchesResponse
687
+
err = json.Unmarshal(body, &result)
688
+
if err != nil {
689
+
log.Println("failed to parse response:", err)
690
+
return
691
+
}
692
+
693
+
s.pages.PullCompareBranchesFragment(w, pages.PullCompareBranchesParams{
694
+
RepoInfo: f.RepoInfo(s, user),
695
+
Branches: result.Branches,
696
+
})
697
+
}
698
+
646
699
func (s *State) ResubmitPull(w http.ResponseWriter, r *http.Request) {
647
700
user := s.auth.GetUser(r)
648
701
f, err := fullyResolvedRepo(r)
+2
appview/state/router.go
+2
appview/state/router.go