【问题标题】:Directory permissions created by HTTP handler, accessed by user由 HTTP 处理程序创建的目录权限,由用户访问
【发布时间】:2013-12-21 07:47:41
【问题描述】:

更新:我最初发布的“in”目录位于 C: 上。它实际上在 E: 上。 D: 和 E: 是 RAID 上的卷。我不希望这会有所作为,但如果我知道发生了什么,我就不必问这个问题了。

我遇到了目录的 ACL 权限问题,该目录必须由 Web 服务和本地用户控制。这是我第一个涉及目录安全和 ACL 的项目,所以我担心我认为这一切都是错误的。我愿意接受提供点修复的答案,以及那些建议对我的安全模型进行大修的答案。

我正在开发一个 Windows Server 2012 R2 Web 服务,该服务从多个用户(节点)捕获数据,然后对其进行处理。我有每个节点目录(例如 E:\in\node1、E:\in\node2 等)来保存传入的数据,然后我使用一个 C# 控制台应用程序作为非管理本地用户(LocalUser ) 将文件移动到具有更深目录结构的更大卷中,以反映控制台应用程序完成的分类。

最初,我会以 LocalUser 的身份为每个节点创建目录,但为了便于管理,我创建了一个 Web 服务(POST 处理程序)来创建节点目录,因为每个节点都被配置和配置。

我现在有一个文件系统,其中一些目录由 LocalUser 创建,一些由 DefaultAppPool 通过 Web 服务创建。两种类型的目录都按预期接收文件。当我以 LocalUser 身份运行控制台应用程序时,LocalUser 创建的目录一切正常,但是当我尝试将 File.Move() 从 Web 创建的节点目录转移到 Web 创建的分类目录时,我得到了 UnauthorizedAccessException。当我查看 ACL 时,我发现问题在于 Creator(以及具有完全控制权的帐户)与运行控制台应用程序的帐户不同。此外,ACL 页面说 E:\in\node2 继承自 E: ,而不是 E:\in 。

Web 配置的全部意义在于使系统自动化,因此我不想触摸所有新目录来添加 LocalUser(或包含 LocalUser 的组)。我还希望系统在其他经过身份验证的用户尝试运行控制台应用程序时工作(例如,从未在任何地方创建任何目录的 LocalUser2)。

似乎我必须解决此问题的两个机会是 1) 当 Web 服务创建目录时,或 2) 当 LocalUser 运行脚本时。不幸的是,我担心这两个帐户(DefaultAppPool、LocalUser)都无权授予(在情况 1)或夺取(在情况 2)有问题的目录的完全控制权。

最终,我计划从 Web 服务运行控制台应用程序,这将使一切都作为 DefaultAppPool 运行,但在开发过程中,作为手动维护操作,我希望能够按需运行控制台应用程序作为 LocalUser 或 LocalUser2。我在想有可能在运行控制台应用程序时制作某种模拟 DefaultAppPool 的“垫片”,但据我所知,进行这种模拟的唯一方法是让网络服务来做。

总之,我怎样才能有一个系统,其中 Web 服务创建目录,然后由特定组中的用户控制?

【问题讨论】:

    标签: c# security acl iis-8 windows-server-2012-r2


    【解决方案1】:

    我是这样理解你的问题的:

    • 您在 DefaultAppPool 中运行了一个 Web 服务,该服务在需要时创建目录并将数据存储在这些目录中的文件中
    • 您有一个由本地用户运行的控制台应用程序,它处理目录中的数据并将结果存储在不同的卷上
    • 您计划让 Web 服务同时运行控制台应用程序,这意味着它将使用与 AppPool 相同的身份访问文件系统
    • 某些节点目录由本地用户创建,其他由网络服务创建
    • 您的控制台应用程序无法访问由 web 服务创建的节点目录中的文件

    在您的问题中,您列出了示例节点目录 *c:\in\node1*、*c:\in\node2* 等。目录 *c:\in* 将是所有节点目录的父级。权限通常是自动继承的。在 *c:\in* 中创建的节点目录应该从 *c:\in* 继承权限。

    webservice 是否手动为其创建的节点目录设置访问权限?

    如果是这样,这有必要吗?如果您设置 c:\in\ 的权限,例如 IIS APPPOOL\DefaultAppPool 和组 Users 可以完全控制在 c:\in\ 中创建的所有目录自动继承这些权限,从而使您摆脱这个问题。 (据我所知,所有本地用户都自动成为 Users 组的成员。)

    如果webservice必须手动设置访问权限,那么在新建节点目录时为组Users添加所需的权限如何?这样,控制台应用程序将能够访问该目录,而不管是谁启动的。

    网络服务/控制台应用程序是否需要对每个目录进行“完全控制”?我理解您的问题的方式,修改读取写入列出文件夹内容的权限就足够了。也许我错过了什么......

    如果您只需要限制对某些用户的访问,您可以创建一个新的安全组并只允许该组访问节点目录树。然后可以将需要访问权限的本地用户添加到该组中。 Web 服务的应用程序池标识也需要是该组的成员。在这种情况下,添加一个仅用于 Web 服务的新应用程序池可能会很有用。是否更改此应用程序池的标识是一个选择问题。

    【讨论】:

    • 谢谢,你把问题重述好了。
    • 我将编辑问题以添加更多细节。当我说 in 目录根目录是 c:\in 时,我过于简化了,它实际上在 e: 上。当我查看 ACL 时,它们是从 e:\ 继承的,而不是 e:\in 。那是出乎意料的。一旦我可以确定我正在查看最新的代码,我将发布创建目录的 sn-p。我还将再次检查父目录的当前 ACL,并再次尝试查看是否可以创建具有正确继承的目录。
    • 您已经写到卷 D: 和 E: 在 RAID 上。它们是否位于可能不是 Windows 系统的外部存储系统上?我问是因为外部系统可能会负责设置和继承实际访问权限。 Windows 服务器会以它期望的方式感知权限的模拟。如果是这种情况,可能值得仔细研究一下存储系统如何处理访问权限。
    • 看起来 RAID 是一个红鲱鱼。通过转到 D: 和 E: 中的父目录并授予用户修改访问权限,我能够让我的脚本工作。我再做一个测试,看看新创建的目录是否继承了Users ACL,如果是,我们就有答案了!
    • 新创建的目录不起作用。即使父文件夹具有修改权限,也不会被继承。读/写/执行确实如此,但我认为我需要像 FileSystemRights.DeleteSubdirectoriesAndFiles 这样的东西来允许移动工作。我将更新问题以包含那些代码 sn-ps。
    【解决方案2】:

    好的,这是交易:

    File.Move() 需要目标的写入权限和源的 DeleteSubdirectoriesAndFiles。这是一个高级权限,因此您必须对其进行挖掘(感谢http://www.codeproject.com/Questions/181198/File-I-O-permissions-the-C-way 引用File handling with non-administrative user 以识别需求)。

    1. 选择有问题的父目录(最好不要 子目录,因为递归地应用权限可能会失败并且 要求您点击“继续”很多次)。
    2. 右键单击->[菜单]属性->[选项卡]安全->[按钮]高级
    3. 这会显示“[目录] 的高级安全设置”
    4. 添加或选择所需的主体(在我的例子中为“用户”)。
    5. [按钮]编辑
    6. 这会显示“[目录] 的权限条目”
    7. [蓝色文字]显示高级权限
    8. 选中“删除子文件夹和文件”框。
    9. (验证您想要的读写属性可能是一个不错的选择 想法在这里)
    10. 单击应用和/或确定,直到所有窗口都消失。

    然后由程序创建的子目录继承,每个人都得到蛋糕。

    感谢 @roadkill 让我走上正轨,感谢 CodeProject.com 为我找到的第一个解决方案提供了帮助,感谢 @Powerlord 提供了 Lukeer 使用的 StackOverflow 解决方案。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-03-01
      • 2019-05-31
      • 1970-01-01
      • 1970-01-01
      • 2015-08-22
      • 1970-01-01
      相关资源
      最近更新 更多