lima-vm/lima · error

repository %s/%s has no default branch

Error message

repository %s/%s has no default branch

What it means

getGitHubDefaultBranch queries https://api.github.com/repos/ORG/REPO and unmarshals the default_branch field. When the API returns HTTP 200 but the default_branch field is empty or missing, Lima rejects the repository with "repository ORG/REPO has no default branch". This happens because the repo exists (or the API claims success) yet has no branch HEAD to resolve github: URLs against.

Source

Thrown at pkg/limatmpl/github.go:144

	}
	defer resp.Body.Close()

	body, err := io.ReadAll(resp.Body)
	if err != nil {
		return "", fmt.Errorf("failed to read GitHub API response: %w", err)
	}
	if resp.StatusCode != http.StatusOK {
		return "", fmt.Errorf("GitHub API returned status %d: %s", resp.StatusCode, string(body))
	}

	var repoData struct {
		DefaultBranch string `json:"default_branch"`
	}
	if err := json.Unmarshal(body, &repoData); err != nil {
		return "", fmt.Errorf("failed to parse GitHub API response: %w", err)
	}
	if repoData.DefaultBranch == "" {
		return "", fmt.Errorf("repository %s/%s has no default branch", org, repo)
	}
	return repoData.DefaultBranch, nil
}

// resolveGitHubSymlink checks if a file at the given path is a symlink/redirect to another file.
// If the file contains a single line without newline, space, or colon then it's treated as a path to the actual file.
// Returns a URL to the redirect path if found, or a URL for original path otherwise.
func resolveGitHubSymlink(ctx context.Context, org, repo, branch, filePath, origBranch string) (string, error) {
	resp, err := getGitHubUserContent(ctx, org, repo, branch, filePath)
	if err != nil {
		return "", fmt.Errorf("failed to fetch file: %w", err)
	}
	defer resp.Body.Close()

	// Special rule for branch/tag propagation for github:ORG// requests.
	if resp.StatusCode == http.StatusNotFound && repo == org {
		defaultBranch, err := getGitHubDefaultBranch(ctx, org, repo)
		if err == nil {

View on GitHub (pinned to dd909d0973)

Solutions

  1. Verify the repository exists and has at least one commit so GitHub assigns a default branch
  2. Pass an explicit branch in the URL (github:ORG/REPO@main) to skip the default-branch lookup entirely
  3. Check the actual API response with `curl https://api.github.com/repos/ORG/REPO` to see what default_branch contains
  4. If on GitHub Enterprise or behind a proxy, ensure the /repos/ORG/REPO endpoint returns the standard schema

Example fix

// before
branch, err := transformGitHubURL(ctx, "github:empty-org/empty-repo")
// after
branch, err := transformGitHubURL(ctx, "github:empty-org/empty-repo@main")
Defensive patterns

Strategy: validation

Validate before calling

resp, err := http.Get("https://api.github.com/repos/" + org + "/" + repo)
if err != nil { return err }
var meta struct{ DefaultBranch string `json:"default_branch"`; Size int `json:"size"` }
json.NewDecoder(resp.Body).Decode(&meta)
if resp.StatusCode != 200 || meta.DefaultBranch == "" || meta.Size == 0 {
    return fmt.Errorf("repo %s/%s is empty or has no default branch; pass an explicit @branch", org, repo)
}

Type guard

func hasDefaultBranch(meta struct{ DefaultBranch string `json:"default_branch"` }) bool {
    return meta.DefaultBranch != ""
}

Try / catch

branch, err := transformGitHubURL(ctx, ref)
var hintErr error
if err != nil && strings.Contains(err.Error(), "has no default branch") {
    hintErr = fmt.Errorf("%w (hint: repository may be empty; specify github:ORG/REPO@BRANCH explicitly)", err)
}

Prevention

When it happens

Trigger: Calling transformGitHubURL with a github:ORG/REPO... URL lacking an explicit @BRANCH, which triggers getGitHubDefaultBranch; the GitHub API returns 200 with an empty default_branch (e.g. an empty repository with no commits, or an API response shape that omits default_branch).

Common situations: Referencing a freshly created GitHub repo that has no commits yet; a repository where the default branch was deleted; a proxy or GitHub Enterprise mirror returning 200 with a stripped/empty JSON body; rate-limit or auth pages that happen to parse as JSON without default_branch.

Related errors


AI-assisted analysis of lima-vm/lima@dd909d0973 (2026-09-01). Data as JSON: /api/errors/fa64769f5278e1a2. Report an issue: GitHub.