os.MkDir和os.MkDirAll权限值?

时间:2013-01-10 01:33:50

标签: go

我正在尝试在程序开始时创建一个日志文件。

如果没有创建目录,我需要检查“/ log”目录是否存在,然后继续创建日志文件。

我尝试使用os.Mkdir(以及os.MkDirAll),但无论我在第二个参数中放入什么值,我都会获得一个没有权限的锁定文件夹。为了获得用户文件夹的读/写,这应该是什么值?我以为它会是0x700,但它似乎不起作用。

谢谢!

5 个答案:

答案 0 :(得分:70)

您可以直接使用八进制表示法:

os.Mkdir("dirname", 0700)


权限位

+-----+---+--------------------------+
| rwx | 7 | Read, write and execute  |
| rw- | 6 | Read, write              |
| r-x | 5 | Read, and execute        |
| r-- | 4 | Read,                    |
| -wx | 3 | Write and execute        |
| -w- | 2 | Write                    |
| --x | 1 | Execute                  |
| --- | 0 | no permissions           |
+------------------------------------+

+------------+------+-------+
| Permission | Octal| Field |
+------------+------+-------+
| rwx------  | 0700 | User  |
| ---rwx---  | 0070 | Group |
| ------rwx  | 0007 | Other |
+------------+------+-------+

A Unix Permission Primer


常见权限用法

0755 常用于网络服务器。所有者可以读,写,执行。其他人都可以阅读和执行但不能修改文件。

0777 每个人都可以阅读写入和执行。在Web服务器上,建议不要对文件和文件夹使用“777”权限,因为它允许任何人向您的服务器添加恶意代码。

0644 只有所有者才能读写。其他人只能阅读。没有人可以执行该文件。

0655 只有所有者才能读写,但不能执行该文件。其他人都可以阅读和执行,但不能修改文件。

www.maketecheasier.com/file-permissions-what-does-chmod-777-means/


Linux上的目录权限

在Linux上对目录应用权限时,权限位与常规文件具有不同的含义。 (source

读取位用户可以读取目录中包含的文件名 写入位如果执行位也设置,用户可以{添加,重命名,删除}文件名。
执行位用户可以进入目录并访问其中的文件。

https://unix.stackexchange.com/a/21252

权限计算器

permissions calculator

方便的permissions calculator

答案 1 :(得分:20)

@ Daniel在他的回答中的陈述并不是真的正确,而且它也谈到一个十进制数,然后使用八进制数,正如@SashaCrofter在他的评论中正确指出的那样。

实际上,只要它表示合理的Unix权限, form 你的权限值是什么并不重要。

由于POSIX文件系统上的权限位是三位的 - 所有者,组和其他访问的三位,加上三位修饰符(例如粘滞位), - 习惯上使用八进制数来表示每个权限八进制数中的 digit 表示三位值。

因此,当您在Go代码中使用0700时,前导0被剥离并且仅在那里告诉解析器它看到八进制数字文字,并且以下三个字母代表所有者,组和其他权限,在此订购。比方说,如果你想要设置组粘滞位以及使文件系统对象组可读和可执行,你可以指定02750等等。

请注意,文件系统对象获取的实际权限将由创建对象的进程的活动umask进一步调整。

为了更好地掌握这些主题,最好阅读有关类Unix操作系统的chmod手册页和一般文献。

答案 2 :(得分:7)

您可以将umask重置为0。我将其称为主文件中的第一件事

syscall.Umask(0)

示例

_ = os.MkdirAll("/tmp/dirs/1", 0664)
syscall.Umask(0)
_ = os.MkdirAll("/tmp/dirs/2", 0664)

结果

/tmp/dirs$ stat -c '%A %a %n' *
drw-r--r-- 644 1
drw-rw-r-- 664 2

答案 3 :(得分:4)

除了其他答案,请记住,在Unix和Linux风格的操作系统上,所有程序都使用 umask 设置运行。 umask在许多情况下默认为022或有时为002,是系统将从文件和目录创建请求中自动删除的权限集。

这意味着大多数程序(此规则有几个例外)应使用模式0666创建文件,并使用模式0777创建目录。在运行过程中记录的用户配置指出要带走这些权限中的哪一个。如果用户的设置为022,并且我们以模式0666创建了文件,则实际得到的设置为rw-r--r--:对用户的读写,对组的只读,对其他人只读。

如果用户希望将可写性扩展到他们的组,则只需将其umask设置为2:现在,他们取消了对其他人的写许可,但将其保留给他们的组。现在以模式rw-rw-r--创建新文件。 程序不会改变:它的模式仍使用0666。但是文件是使用模式0664创建的。

类似地,如果您用os.Mkdir调用os.MkdirAll0777,则umask将删除不需要的权限,而为您保留正确的权限。

但是我提到有例外。这些程序包括复制仅适用于用户的敏感信息的程序:这些程序通常应将模式0700用于目录,将0600用于文件。它们 可能包含长时间运行的服务器,它们充当系统用户,而不是任何个人……尽管这些服务器可以以正确的umask运行,在这种情况下, 07770666很好。

您必须在此处做出一些判断。那些特别注重安全性的程序(例如ssh或类似程序)可能希望使用有限的权限,甚至可能想要检查(使用os.Lstat或类似权限)对重要目录的权限是否适当严格。

(请注意,umask 不适用于 os.Chmod个呼叫。在这里直接选择模式。)

答案 4 :(得分:1)

一种确保无需设置八进制复杂计算即可设置所需权限的方法是使用软件包FileMode中非常方便的os常量:< / p>

https://golang.org/pkg/os/#FileMode

我通常将os.ModePerm(实际上编码为0777)用于完全许可的目录,例如高速缓存或临时文件所需的目录,但是您的行程可能会有所不同。如@kostix所述,要设置其他位(粘性等),必须处理Go中标志的八进制表示形式,您可以始终使用类似以下内容:

if err := os.MkdirAll("my/tmp/dir", os.ModeSticky|os.ModePerm); err != nil {
  fmt.Println("Directory(ies) successfully created with sticky bits and full permissions")
}

Go playground

一如既往,值得一提的是 ,这些权限是通过设置的umask来“过滤”的。