在Golang中,判断一个目录是否可写的跨平台方法是什么?

huangapple go评论78阅读模式
英文:

Cross-Platform Way to See if a Directory is Writeable in Golang?

问题

我有一个程序,它试图使用Golang将文件写入目录。我希望它能在MacOS、Linux和Windows(至少)上工作。

Golang提供了以下测试,但它似乎只适用于Linux(来自下面链接的SO问题):

func IsWritable(path string) (isWritable bool, err error) {
    isWritable = false
    info, err := os.Stat(path)
    if err != nil {
        fmt.Println("路径不存在")
        return
    }

    err = nil
    if !info.IsDir() {
        fmt.Println("路径不是目录")
        return
    }

    // 检查文件权限中的用户位是否启用
    if info.Mode().Perm() & (1 << (uint(7))) == 0 {
        fmt.Println("用户没有设置该文件的写权限位")
        return
    }

    var stat syscall.Stat_t
    if err = syscall.Stat(path, &stat); err != nil {
        fmt.Println("无法获取stat")
        return
    }

    err = nil
    if uint32(os.Geteuid()) != stat.Uid {
        isWritable = false
        fmt.Println("用户没有写入该目录的权限")
        return
    }

    isWritable = true
    return
}

我看到了这个答案[1],但自从那个问题有活动以来已经过去了10年,有没有比条件编译更好的方法来实现这个?

总结:我只想让Go进程知道它是否能够写入给定的目录。

[1] https://stackoverflow.com/questions/20026320/how-to-tell-if-folder-exists-and-is-writable

英文:

I have a program which is attempting to write a file to a directory using Golang. I need this to be able to work in MacOS, Linux, and Windows (at a minimum).

Golang offers the following test - but it appears to be Linux only (from the linked SO question below):

func IsWritable(path string) (isWritable bool, err error) {
    isWritable = false
    info, err := os.Stat(path)
    if err != nil {
        fmt.Println(&quot;Path doesn&#39;t exist&quot;)
        return
    }

    err = nil
    if !info.IsDir() {
        fmt.Println(&quot;Path isn&#39;t a directory&quot;)
        return
    }

    // Check if the user bit is enabled in file permission
    if info.Mode().Perm() &amp; (1 &lt;&lt; (uint(7))) == 0 {
        fmt.Println(&quot;Write permission bit is not set on this file for user&quot;)
        return
    }

    var stat syscall.Stat_t
    if err = syscall.Stat(path, &amp;stat); err != nil {
        fmt.Println(&quot;Unable to get stat&quot;)
        return
    }

    err = nil
    if uint32(os.Geteuid()) != stat.Uid {
        isWritable = false
        fmt.Println(&quot;User doesn&#39;t have permission to write to this directory&quot;)
        return
    }

    isWritable = true
    return
}

I saw this answer[1], but it's been 10 years since that question had activity, is there any better way to accomplish this than conditional compiling?

Summary: I just want the go process to understand whether or not it can write to a given directory.

[1] https://stackoverflow.com/questions/20026320/how-to-tell-if-folder-exists-and-is-writable

答案1

得分: 3

这是我在没有条件编译的情况下实现目标的方法,因为权限和特权可能因操作系统而异。

  • 我尝试通过使用os.CreateTemp在该目录中创建临时文件来实现。如果该函数没有返回错误,说明路径或权限没有问题,并且我们能够在该目录中创建文件。

以下是代码示例:

func IsWritable(path string) (bool, error) {
    tmpFile := "tmpfile"

    file, err := os.CreateTemp(path, tmpFile)
    if err != nil {
        return false, err
    }

    defer os.Remove(file.Name())
    defer file.Close()

    return true, nil
}


func main() {
    path := "绝对目录路径"

    isWritable, err := IsWritable(path)
    if err != nil {
        panic(err)
    }

    if isWritable {
        // 执行相关操作
    }
}

请将absolute-directory-path替换为实际的绝对目录路径。

英文:

This is how I achieved the goal when I had the same without conditional compiling, due to the fact that permissions and privileges may differ between operating systems.

  • I Tried by creating a temporary file in that directory with os.CreateTemp. If there is no error returned by the function, which indicates there is no issue with the path or permission and we are able to create files in that directory.

Here is the code

func IsWritable(path string) (bool, error) {
	tmpFile := &quot;tmpfile&quot;

	file, err := os.CreateTemp(path, tmpFile)
	if err != nil {
		return false, err
	}

	defer os.Remove(file.Name())
	defer file.Close()

	return true, nil
}


func main() {
     path := &quot;absolute-directory-path&quot;

 	isWritable, err := IsWritable(path)
    if err != nil {
	   panic(err)
 	}

    if isWritable {
	  // statements
 	}

}

答案2

得分: -1

请记住,Stat方法可能会遇到许多错误。因此,我们需要检查是否是文件不存在的错误。

英文:

Keep in mind that the Stat method can encounter many errors. Hence, we need to check if it is a file that does not exist error.

huangapple
  • 本文由 发表于 2023年5月19日 07:21:11
  • 转载请务必保留本文链接:https://go.coder-hub.com/76285066.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定