Skip to content

Commit

Permalink
Use Git information instead of a HTTP probe.
Browse files Browse the repository at this point in the history
  • Loading branch information
jmalloc committed Jan 29, 2025
1 parent 71c4be6 commit 45f0a01
Show file tree
Hide file tree
Showing 2 changed files with 38 additions and 36 deletions.
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,11 @@
# Changelog

## 0.7.6 (2025-01-29)

- **[IMPROVED]** Use local Git information instead of an HTTP probe to determine
if a branch has been pushed to the remote, as the HTTP probe would fail for
private repositories.

## 0.7.5 (2025-01-29)

- **[IMPROVED]** `grit browse` (aka `open`) now checks if the remote URL exists
Expand Down
68 changes: 32 additions & 36 deletions cmd/grit/browse.go
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
package main

import (
"net/http"
"net/url"
"path"
"strings"
Expand Down Expand Up @@ -41,54 +40,51 @@ func browse(cfg grit.Config, idx *index.Index, c *cli.Context) error {
Path: strings.TrimSuffix(ep.Path, ".git"),
}

r, err := git.PlainOpen(dir)
if err != nil {
if err := injectGitHubTreeViewPath(&u, dir); err != nil {
return err
}

// If we can determine the "HEAD" of the local clone, open the tree view for
// that commit. Otherwise, open the repository's root.
if head, err := r.Head(); err == nil {
// If the head's name is "HEAD", it's a detached HEAD. If the HEAD
// refers to a branch, the name will be the reference to that branch.
if head.Name() == "HEAD" {
// In this case, we check to see if there is a singular tag that
// refers to the commit, and if so open the tree for the tag name.
//
// This is purely for UX, as the user probably expects to see the
// tag name in the URL.
head = resolveUniqueTag(r, head)
}
writef(c, "opening %s", u.String())

// If we still have a detached head, load the tree view for the commit
// hash; we have no more user-friendly tag or branch name.
ref := head.Name().Short()
if ref == "HEAD" {
ref = head.Hash().String()
}
return open.Run(u.String())
}

orig := u.Path
u.Path = path.Join(u.Path, "tree", ref)
func injectGitHubTreeViewPath(u *url.URL, dir string) error {
// HACK: Assume anything with github in the host is either GitHub.com or a
// GitHub Enterprise Server installation.
if !strings.Contains(u.Host, "github") {
return nil
}

// Check if the target URL actually exists, and if not, revert to the
// original path.
res, err := http.Head(u.String())
if err != nil || res.StatusCode < http.StatusOK || res.StatusCode >= http.StatusBadRequest {
u.Path = orig
}
r, err := git.PlainOpen(dir)
if err != nil {
return err
}

writef(c, "opening %s", u.String())
head, err := r.Head()
if err != nil {
// Most likely a repository with no commits, but we don't want this to
// prevent the user from opening the repository in the browser.
return nil
}

return open.Run(u.String())
if branch, err := r.Branch(head.Name().Short()); err == nil {
if branch.Remote != "" {
u.Path = path.Join(u.Path, "tree", branch.Name)
}
} else if tag, ok := resolveUniqueTag(r, head); ok {
u.Path = path.Join(u.Path, "tree", tag.Name().Short())
}

return nil
}

// resolveUniqueTag returns the reference to a tag that refers to ref, if
// exactly one exists; otherwise, it returns ref.
func resolveUniqueTag(r *git.Repository, ref *plumbing.Reference) *plumbing.Reference {
func resolveUniqueTag(r *git.Repository, ref *plumbing.Reference) (*plumbing.Reference, bool) {
tags, err := r.Tags()
if err != nil {
return ref
return ref, false
}
defer tags.Close()

Expand All @@ -111,8 +107,8 @@ func resolveUniqueTag(r *git.Repository, ref *plumbing.Reference) *plumbing.Refe
)

if len(refs) == 1 {
return refs[0]
return refs[0], true
}

return ref
return ref, false
}

0 comments on commit 45f0a01

Please sign in to comment.