1package xrpc
2
3import (
4 "fmt"
5 "net/http"
6
7 "tangled.org/core/knotserver/git"
8 "tangled.org/core/types"
9 xrpcerr "tangled.org/core/xrpc/errors"
10)
11
12func (x *Xrpc) RepoCompare(w http.ResponseWriter, r *http.Request) {
13 repo := r.URL.Query().Get("repo")
14 repoPath, err := x.parseRepoParam(repo)
15 if err != nil {
16 writeError(w, err.(xrpcerr.XrpcError), http.StatusBadRequest)
17 return
18 }
19
20 rev1 := r.URL.Query().Get("rev1")
21 if rev1 == "" {
22 writeError(w, xrpcerr.NewXrpcError(
23 xrpcerr.WithTag("InvalidRequest"),
24 xrpcerr.WithMessage("missing rev1 parameter"),
25 ), http.StatusBadRequest)
26 return
27 }
28
29 rev2 := r.URL.Query().Get("rev2")
30 if rev2 == "" {
31 writeError(w, xrpcerr.NewXrpcError(
32 xrpcerr.WithTag("InvalidRequest"),
33 xrpcerr.WithMessage("missing rev2 parameter"),
34 ), http.StatusBadRequest)
35 return
36 }
37
38 gr, err := git.PlainOpen(repoPath)
39 if err != nil {
40 writeError(w, xrpcerr.RepoNotFoundError, http.StatusNoContent)
41 return
42 }
43
44 commit1, err := gr.ResolveRevision(rev1)
45 if err != nil {
46 x.Logger.Error("error resolving revision 1", "msg", err.Error())
47 writeError(w, xrpcerr.NewXrpcError(
48 xrpcerr.WithTag("RevisionNotFound"),
49 xrpcerr.WithMessage(fmt.Sprintf("error resolving revision %s", rev1)),
50 ), http.StatusBadRequest)
51 return
52 }
53
54 commit2, err := gr.ResolveRevision(rev2)
55 if err != nil {
56 x.Logger.Error("error resolving revision 2", "msg", err.Error())
57 writeError(w, xrpcerr.NewXrpcError(
58 xrpcerr.WithTag("RevisionNotFound"),
59 xrpcerr.WithMessage(fmt.Sprintf("error resolving revision %s", rev2)),
60 ), http.StatusBadRequest)
61 return
62 }
63
64 rawPatch, formatPatch, err := gr.FormatPatch(commit1, commit2)
65 if err != nil {
66 x.Logger.Error("error comparing revisions", "msg", err.Error())
67 writeError(w, xrpcerr.NewXrpcError(
68 xrpcerr.WithTag("CompareError"),
69 xrpcerr.WithMessage("error comparing revisions"),
70 ), http.StatusBadRequest)
71 return
72 }
73
74 response := types.RepoFormatPatchResponse{
75 Rev1: commit1.Hash.String(),
76 Rev2: commit2.Hash.String(),
77 FormatPatch: formatPatch,
78 Patch: rawPatch,
79 }
80
81 writeJson(w, response)
82}