You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用纯Go代码验证指定目录并非Git子模块?

用go-git检查Git仓库并验证是否为子模块

我可以通过go-git的PlainOpen方法检查指定路径是否为Git仓库:

package main

import (
    "errors"
    "fmt"
    "os"
    
    "github.com/go-git/go-git/v5"
)

func errAndExit(err error) {
    fmt.Printf("\n%v\n", err)
    os.Exit(1)
}

func main() {
    path := os.Args[1]
    fmt.Println("given path =", path)
    pathInfo, err := os.Stat(path)
    if err != nil {
        errAndExit(err)
    }
    if !pathInfo.IsDir() {
        errAndExit(
            fmt.Errorf(
                "‘%s’ is not a directory",
                pathInfo.Name(),
            ),
        )
    }
    rep, err := git.PlainOpen(path)
    if err != nil {
        if errors.Is(err, git.ErrRepositoryNotExists) {
            errAndExit(
                fmt.Errorf(
                    "we should be prepared for: %w",
                    err,
                ),
            )
        }
        errAndExit(err)
    }
    fmt.Printf("\n%#v\n", rep)
}

有没有纯Go的优雅方法,可以验证指定路径指向的Git仓库并非子模块?

以下是我想规避的临时方案:通过Git CLI执行git rev-parse --show-superproject-working-tree命令,检查输出结果:

package gitcli

import (
    "bytes"
    "fmt"
    "os/exec"
    "strings"
)

const (
    newLine             = "\n"
    pathToGitExecutable = "/usr/bin/git"
)

func callRevParse(dPath, rpCommand string) (string, error) {
    gitRevParse := exec.Command(
        pathToGitExecutable,
        "rev-parse",
        rpCommand,
    )
    gitRevParse.Dir = dPath
    var out bytes.Buffer
    gitRevParse.Stdout = &out
    err := gitRevParse.Run()
    if err != nil {
        err = fmt.Errorf(
            "failed to invoke `git rev-parse %s` command in ‘%s’ path: %w",
            rpCommand,
            dPath,
            err,
        )
    }
    return out.String(), err
}

func verifyIsNotSubmodule(dPath string) error {
    rpSSWT, err := callRevParse(dPath, "--show-superproject-working-tree")
    if err != nil {
        return err
    }
    if len(strings.Trim(rpSSWT, newLine)) > 0 {
        return fmt.Errorf(
            "‘%s’ is a git submodule",
            dPath,
        )
    }
    return nil
}

我知道有go-git-cmd-wrapper这个工具,但上面的实现更直接高效。

内容的提问来源于stack exchange,提问作者Kacper Perschke

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.15 23:38:26