flipped-aurora/gin-vue-admin · error
创建编译目录失败: %w
Error message
创建编译目录失败: %w
What it means
After creating the build root, compileCliBinary allocates a per-build temp directory with os.MkdirTemp(absBuildRoot, "cli-"). Failure here (wrapped in this error) means a new temp subdir could not be created even though the root exists — typically a race, permission change, or filesystem full condition.
Source
Thrown at server/plugin/ai/service/sys_cli_build.go:94
return s.compileCliBinary(cli, manifestBytes, goos, goarch)
}
// compileCliBinary 把 manifest 内嵌进 gva 源码副本并交叉编译,返回二进制文件名与内容。
func (s *cliService) compileCliBinary(cli autoModel.SysCli, manifestBytes []byte, goos, goarch string) (string, []byte, error) {
if _, err := exec.LookPath("go"); err != nil {
return "", nil, fmt.Errorf("服务器未安装 Go 工具链,无法编译: %w", err)
}
absBuildRoot, err := filepath.Abs(cliBuildDir)
if err != nil {
return "", nil, fmt.Errorf("解析编译目录失败: %w", err)
}
if err := os.MkdirAll(absBuildRoot, 0o755); err != nil {
return "", nil, fmt.Errorf("创建编译根目录失败: %w", err)
}
buildDir, err := os.MkdirTemp(absBuildRoot, "cli-")
if err != nil {
return "", nil, fmt.Errorf("创建编译目录失败: %w", err)
}
defer os.RemoveAll(buildDir)
if err := copyCliSources(cliSourceDir, buildDir); err != nil {
return "", nil, err
}
if err := writeEmbeddedManifest(buildDir, manifestBytes); err != nil {
return "", nil, err
}
binaryName := sanitizeSingleSegmentSlug(cli.Command)
if binaryName == "" {
binaryName = "cli"
}
binaryName += cliBinaryExt(goos)
binaryPath := filepath.Join(buildDir, binaryName)
if err := runGoBuild(buildDir, binaryPath, goos, goarch); err != nil {View on GitHub (pinned to 3136500ef3)
Solutions
- Check disk space and inodes (df -h / df -i) on the volume holding the build dir and free space
- Clean up stale cli-* directories left by crashed builds
- Ensure no external cleanup job deletes the build root while builds run; scope cleanup to old dirs only
- Grant the server user write permission on the build root again if it changed
- If a previous build crashed, note MkdirTemp dirs are removed via defer os.RemoveAll only on clean returns — sweep orphans periodically
Example fix
# find and remove orphaned build dirs older than a day
find /var/lib/gva/cli-build -maxdepth 1 -name 'cli-*' -mtime +1 -exec rm -rf {} + Defensive patterns
Strategy: retry
Validate before calling
if st, err := os.Stat(cliBuildDir); err != nil || !st.IsDir() {
return errors.New("build root missing or not a directory")
} Try / catch
bin, content, err := svc.BuildCliBinary(cli, manifest, goos, goarch)
if err != nil {
if strings.Contains(err.Error(), "创建编译目录失败") && isTransient(err) {
time.Sleep(500 * time.Millisecond)
return svc.BuildCliBinary(cli, manifest, goos, goarch) // one retry
}
return err
} Prevention
- Monitor disk space/inodes on the build volume
- Periodically sweep orphaned cli-* temp dirs from crashed builds
- Scope cleanup jobs to old directories only, never delete the root mid-build
When it happens
Trigger: Disk full or inode exhaustion on the partition holding absBuildRoot; permissions changed on the build root between MkdirAll and MkdirTemp; concurrent cleanup scripts deleting the root mid-build; quota limits on the volume.
Common situations: Long-running servers whose build dir filled up with stale cli-* temp dirs; monitoring jobs or cron cleaning the build root while a build is in flight; small tmpfs volume allocated for the build directory.
Related errors
AI-assisted analysis of flipped-aurora/gin-vue-admin@3136500ef3 (2026-08-31).
Data as JSON: /api/errors/3243039e380d17db.
Report an issue: GitHub.