使用逻辑目录简化您的 Transfer Family 目录结构 - Amazon Transfer Family
Amazon Web Services 文档中描述的 Amazon Web Services 服务或功能可能因区域而异。要查看适用于中国区域的差异,请参阅 中国的 Amazon Web Services 服务入门 (PDF)

本文属于机器翻译版本。若本译文内容与英语原文存在差异,则一律以英文原文为准。

使用逻辑目录简化您的 Transfer Family 目录结构

要简化 Amazon Transfer Family 服务器目录结构,可以使用逻辑目录。使用逻辑目录,可以构造一个使用用户友好名称的虚拟目录结构,当用户连接到 Amazon S3 存储桶或 Amazon EFS 文件系统时,可以导航这些名称。使用逻辑目录时,可以避免向最终用户泄露绝对目录路径、Amazon S3 存储桶名称和 EFS 文件系统名称。

注意

您应该使用会话策略,以便您的最终用户只能执行您允许他们执行的操作。

您应该使用逻辑目录为最终用户创建用户友好的虚拟目录,并抽象存储桶名称。逻辑目录映射仅允许用户访问其指定的逻辑路径和子目录,禁止使用遍历逻辑根目录的相对路径。

Transfer Family 会验证可能包含相对元素的每条路径,并在我们将这些路径传递给 Amazon S3 之前主动阻止解析这些路径;这样可以防止您的用户超越其逻辑映射。

尽管 Transfer Family 会阻止您的最终用户访问其逻辑目录之外的目录,但我们也建议您使用唯一的角色或会话策略在存储级别强制执行最低权限。

通过执行所谓的chroot操作,您可以使用逻辑目录将用户的根目录设置为存储层次结构中的所需位置。在此模式下,用户无法导航到您为其配置的主目录或根目录之外的目录。

例如,尽管 Amazon S3 用户的范围已缩小为仅限访问/mybucket/home/${transfer:UserName},但有些客户端允许用户向上遍历文件夹至/mybucket/home。在这种情况下,用户只有在注销并再次登录 Transfer Family 服务器后才会重新进入其预期的主目录。执行chroot操作可以防止这种情况的发生。

您可以跨存储桶和前缀创建自己的目录结构。如果您的工作流程需要一个无法通过存储桶前缀复制的特定目录结构,则此功能适用。您还可以链接到 Amazon S3 中的多个非连续位置,类似于在 Linux 文件系统中创建符号链接,其中您的目录路径引用文件系统中的不同位置。

逻辑目录文件映射

HomeDirectoryMapEntry数据类型现在包括一个Type参数。在此参数存在之前,您可能已经创建了以文件为目标的逻辑目录映射。如果您之前创建过任何此类逻辑目录映射,则必须将显式设置TypeFILE,否则这些映射将无法正常运行。

一种方法是调用 UpdateUser API,并将现有映射TypeFILE的设置为。

使用逻辑目录的规则

在构建逻辑目录映射之前,应了解以下规则:

  • 如果Entry"/",则只能有一个映射,因为不允许重叠路径。

  • 逻辑目录支持最大 2.1 MB 的映射(对于服务管理用户,此限制为 2,000 个条目)。也就是说,包含映射的数据结构的最大大小为 2.1 MB。如果您有很多映射,则可以按如下方式计算映射的大小:

    1. 用格式写出一个典型的映射{"Entry":"/entry-path","Target":"/target-path"},其中entry-pathtarget-path是你将要使用的实际值。

    2. 计算该字符串中的字符,然后添加一 (1)。

    3. 将该数字乘以服务器的近似映射数。

    如果您在步骤 3 中估计的数字小于 2.1 MB,则您的映射在可接受的限制范围内。

  • 如果存储桶或文件系统路径已根据用户名参数化,则目标可以使用该${transfer:UserName}变量。

  • 目标可以是不同存储桶或文件系统中的路径,但您必须确保映射的 Amazon Identity and Access Management (IAM) 角色(响应中的Role参数)提供对这些存储桶或文件系统的访问权限。

  • 不要指定HomeDirectory参数,因为当你使用HomeDirectoryType参数的值时,EntryTarget成对会暗示这个LOGICAL值。

  • 目标必须以正斜杠 (/) 字符开头,但在指定时不要使用尾部的正斜杠 (/)。Target例如,/DOC-EXAMPLE-BUCKET/images可以接受DOC-EXAMPLE-BUCKET/images,但不/DOC-EXAMPLE-BUCKET/images/是。

  • Amazon S3 是一个对象存储,这意味着文件夹是一个虚拟概念,没有实际的目录层次结构。如果您的应用程序从客户端发出stat操作,则当您使用 Amazon S3 进行存储时,所有内容都将归类为文件。亚马逊简单存储服务用户指南中的使用文件夹在 Amazon S3 控制台中组织对象中描述了此行为。如果您的应用程序要求stat准确显示某物是文件还是文件夹,则可以使用亚马逊弹性文件系统(Amazon EFS)作为 Transfer Family 服务器的存储选项。

  • 如果您为用户指定逻辑目录值,则使用的参数取决于用户的类型:

    • 对于服务托管的用户,请在HomeDirectoryMappings中提供逻辑目录值。

    • 对于自定义身份提供商用户,请在中提供逻辑目录值HomeDirectoryDetails

重要

除非您选择优化 Amazon S3 目录的性能(创建或更新服务器时),否则根目录必须在启动时存在。对于 Amazon S3,这意味着您必须已经创建了一个以正斜杠 (/) 结尾的零字节对象才能创建根文件夹。避免这个问题是考虑优化 Amazon S3 性能的理由。

实现逻辑目录和 chroot

要使用逻辑目录和chroot功能,您必须执行以下操作:

为每个用户开启逻辑目录。为此,请在创建或更新用户时将HomeDirectoryType参数设置为LOGICAL

"HomeDirectoryType": "LOGICAL"

chroot

对于chroot,创建一个由每个用户的单个EntryTarget配对组成的目录结构。根文件夹是Entry重点,Target是存储桶或文件系统中要映射到的位置。

Example for Amazon S3
[{"Entry": "/", "Target": "/mybucket/jane"}]
Example for Amazon EFS
[{"Entry": "/", "Target": "/fs-faa1a123/jane"}]

您可以像前面的示例一样使用绝对路径,也可以使用${transfer:UserName}动态替换用户名,如下例所示。

[{"Entry": "/", "Target": "/mybucket/${transfer:UserName}"}]

在前面的示例中,用户被锁定到其根目录,且无法在层次结构中向上移动。

虚拟目录结构

对于虚拟目录结构,只要用户的 IAM 角色映射有权访问它们,您就可以创建多个EntryTarget配对,目标位于您的 S3 存储桶或 EFS 文件系统的任意位置,包括跨多个存储桶或文件系统。

在以下虚拟结构示例中,当用户登录 Amazon SFTP 时,他们位于根目录中,子目录为/pics/doc/reporting、和。/anotherpath/subpath/financials

注意

除非您选择优化 Amazon S3 目录的性能(当您创建或更新服务器时),否则如果目录尚不存在,则用户或管理员需要创建这些目录。避免这个问题是考虑优化 Amazon S3 性能的理由。

对于 Amazon EFS,您仍然需要管理员来创建逻辑映射或/目录。

[ {"Entry": "/pics", "Target": "/bucket1/pics"}, {"Entry": "/doc", "Target": "/bucket1/anotherpath/docs"}, {"Entry": "/reporting", "Target": "/reportingbucket/Q1"}, {"Entry": "/anotherpath/subpath/financials", "Target": "/reportingbucket/financials"}]

注意

您只可以将文件上传到映射的特定文件夹。这意味着,在前面的示例中,您不能上传到/anotherpathanotherpath/subpath目录;只有anotherpath/subpath/financials。您也无法直接映射到这些路径,因为不允许重叠路径。

例如,假设您创建以下映射:

{ "Entry": "/pics", "Target": "/mybucket/pics" }, { "Entry": "/doc", "Target": "/mybucket/mydocs" }, { "Entry": "/temp", "Target": "/mybucket" }

您只可以将文件上传到这些存储桶中。当您首次通过sftp连接时,您会被放到根目录中/。如果您尝试将文件上传到该目录,则上传将失败。以下命令显示了一个示例序列:

sftp> pwd Remote working directory: / sftp> put file Uploading file to /file remote open("/file"): No such file or directory

要上传到任何directory/sub-directory,必须将路径明确映射到sub-directory

有关为用户配置逻辑目录的更多信息(包括可供下载和chroot使用的 Amazon CloudFormation 模板),请参阅 Amazon 存储博客中的使用 chroot 和逻辑目录简化 Amazon SFTP 结构

配置逻辑目录示例

在此示例中,我们创建一个用户并分配两个逻辑目录。以下命令使用逻辑目录picsdoc创建新用户(适用于现有的 Transfer Family 服务器)。

aws transfer create-user --user-name marymajor-logical --server-id s-11112222333344445 --role arn:aws:iam::1234abcd5678:role/marymajor-role --home-directory-type LOGICAL \ --home-directory-mappings "[{\"Entry\":\"/pics\", \"Target\":\"/DOC-EXAMPLE-BUCKET1/pics\"}, {\"Entry\":\"/doc\", \"Target\":\"/DOC-EXAMPLE-BUCKET2/test/mydocs\"}]" \ --ssh-public-key-body file://~/.ssh/id_rsa.pub

如果marymajor是现有用户并且她的主目录类型是PATH,则您可以使用与前一个命令类似的命令将其更改为LOGICAL

aws transfer update-user --user-name marymajor-logical \ --server-id s-11112222333344445 --role arn:aws:iam::1234abcd5678:role/marymajor-role \ --home-directory-type LOGICAL --home-directory-mappings "[{\"Entry\":\"/pics\", \"Target\":\"/DOC-EXAMPLE-BUCKET1/pics\"}, \ {\"Entry\":\"/doc\", \"Target\":\"/DOC-EXAMPLE-BUCKET2/test/mydocs\"}]"

请注意以下几点:

  • 如果目录/DOC-EXAMPLE-BUCKET1/pics/DOC-EXAMPLE-BUCKET2/test/mydocs尚未存在,则用户(或管理员)需要创建这些目录。

  • marymajor连接到服务器并运行ls -l命令时,她会看到以下内容:

    drwxr--r-- 1 - - 0 Mar 17 15:42 doc drwxr--r-- 1 - - 0 Mar 17 16:04 pics
  • marymajor无法在此级别创建任何文件或目录。但是,在picsdoc中,她可以添加子目录。

  • 她添加到picsdoc的文件分别添加到 AmazonS3 路径/DOC-EXAMPLE-BUCKET1/pics/DOC-EXAMPLE-BUCKET2/test/mydocs

  • 在此示例中,我们指定两个不同的存储桶来说明这种可能性。但是,您可以将同一个存储桶用于为用户指定的多个或所有逻辑目录。

为 Amazon EFS 配置逻辑目录

如果 Transfer Family 服务器使用 Amazon EFS,则必须先创建具有读写访问权限的用户主目录,然后用户才能在其逻辑主目录中工作。用户无法自己创建此目录,因为他们将缺乏mkdir对逻辑主目录的权限。

如果用户的主目录不存在,并且他们运行了ls命令,则系统会按如下方式做出响应:

sftp> ls remote readdir ("/"): No such file or directory

对父目录具有管理访问权限的用户需要创建该用户的逻辑主目录。

自定义 Amazon Lambda 响应

您可以将逻辑目录与连接到自定义身份提供商的 Lambda 函数一起使用。为此,在 Lambda 函数中,将HomeDirectoryType指定为LOGICAL,并为 HomeDirectoryDetails 参数添加EntryTarget值。例如:

HomeDirectoryType: "LOGICAL" HomeDirectoryDetails: "[{\"Entry\": \"/\", \"Target\": \"/DOC-EXAMPLE-BUCKET/theRealFolder"}]"

以下代码是来自自定义 Lambda 身份验证调用的成功响应示例。

aws transfer test-identity-provider --server-id s-1234567890abcdef0 --user-name myuser { "Url": "https://a1b2c3d4e5.execute-api.us-east-2.amazonaws.com/prod/servers/s-1234567890abcdef0/users/myuser/config", "Message": "", "Response": "{\"Role\": \"arn:aws:iam::123456789012:role/bob-usa-role\",\"HomeDirectoryType\": \"LOGICAL\",\"HomeDirectoryDetails\": \"[{\\\"Entry\\\":\\\"/myhome\\\",\\\"Target\\\":\\\"/DOC-EXAMPLE-BUCKET/theRealFolder\\\"}]\",\"PublicKeys\": \"[ssh-rsa myrsapubkey]\"}", "StatusCode": 200 }
注意

仅当您使用 API Gateway 方法作为自定义身份提供商时,才会返回该"Url":行。