【问题标题】:golang os.Create cause "no such file or directory" errorgolang os.Create 导致“没有这样的文件或目录”错误
【发布时间】:2017-04-11 02:53:31
【问题描述】:

一定很简单,但我似乎无法弄清楚。我不断收到“没有这样的文件或目录”错误。以为 Create 函数是创建一个新文件?

package main

import (
    "log"
    "os"
)

func main() {
    f, err := os.Create("~/golang-server.log")
    defer f.Close()
    if err != nil {
        panic(err.Error())
    }
    log.SetOutput(f)
}

【问题讨论】:

  • 这通常意味着目标目录不存在。

标签: file go


【解决方案1】:

您不能使用~$HOME 之类的环境变量来指定文件路径,它们是字符串文字,表示实际路径。你得到的错误是因为它将~/golang-server.log视为当前目录的相对路径,并且当前目录中没有目录~

使用手动创建的子目录~,您的代码将成功:

 ~/test/ mkdir \~
 ~/test/ go run t.go
 ~/test/ ls \~
golang-server.log

因此需要将absolute pathrelative path 传递给os.Create

【讨论】:

    【解决方案2】:

    您可以使用os.ExpandEnv 处理“~”,这仅在 sh/bash 上下文中才有意义。

    os.Create(os.ExpandEnv("$HOME/golang-server.log"))
    

    在更复杂的情况下,您需要确保基目录存在,因为os.Create 不会处理它。

    这就是os.Create("~/golang-server.log") 会失败的原因,因为基本目录不存在并且os.Create 不会自动为您创建它。你需要像这样自己做:

    func EnsureBaseDir(fpath string) error {
        baseDir := path.Dir(fpath)
        info, err := os.Stat(baseDir)
        if err == nil && info.IsDir() {
           return nil
        }
        return os.MkdirAll(baseDir, 0755)
    }
    

    注意:

    • $HOME 并不总是存在,例如该程序作为系统级别的systemd 服务运行。所以你最好不要在生产环境中使用$HOME
    • os.Create 的限制不仅仅存在于 Go 中。它是由操作系统内核引起的,广泛存在于其他语言/stdlib 中。

    【讨论】:

      猜你喜欢
      • 2020-09-25
      • 1970-01-01
      • 1970-01-01
      • 2017-04-18
      • 1970-01-01
      • 2017-05-09
      • 2021-05-15
      • 2014-10-31
      • 2022-01-11
      相关资源
      最近更新 更多