【问题标题】:Hadoop client Username and Password access problem to the Azure Data Lake Gen2Hadoop 客户端对 Azure Data Lake Gen2 的用户名和密码访问问题
【发布时间】:2020-01-09 12:39:15
【问题描述】:

尝试通过控制台中的 Hadoop 客户端使用用户名和密码身份验证类型连接到 Azure Data Lake Storage Gen2 并收到错误

java.lang.NullPointerException
        at org.apache.hadoop.fs.azurebfs.oauth2.AzureADAuthenticator.consumeInputStream(AzureADAuthenticator.java:341)
        at org.apache.hadoop.fs.azurebfs.oauth2.AzureADAuthenticator.getTokenSingleCall(AzureADAuthenticator.java:271)
        at org.apache.hadoop.fs.azurebfs.oauth2.AzureADAuthenticator.getTokenCall(AzureADAuthenticator.java:212)
        at org.apache.hadoop.fs.azurebfs.oauth2.AzureADAuthenticator.getTokenUsingClientCreds(AzureADAuthenticator.java:95)
        at org.apache.hadoop.fs.azurebfs.oauth2.UserPasswordTokenProvider.refreshToken(UserPasswordTokenProvider.java:54)
        at org.apache.hadoop.fs.azurebfs.oauth2.AccessTokenProvider.getToken(AccessTokenProvider.java:50)
        at org.apache.hadoop.fs.azurebfs.services.AbfsClient.getAccessToken(AbfsClient.java:546)
        at org.apache.hadoop.fs.azurebfs.services.AbfsRestOperation.executeHttpOperation(AbfsRestOperation.java:150)
        at org.apache.hadoop.fs.azurebfs.services.AbfsRestOperation.execute(AbfsRestOperation.java:124)
        at org.apache.hadoop.fs.azurebfs.services.AbfsClient.getFilesystemProperties(AbfsClient.java:197)
        at org.apache.hadoop.fs.azurebfs.AzureBlobFileSystemStore.getIsNamespaceEnabled(AzureBlobFileSystemStore.java:181)
        at org.apache.hadoop.fs.azurebfs.AzureBlobFileSystemStore.getFileStatus(AzureBlobFileSystemStore.java:454)
        at org.apache.hadoop.fs.azurebfs.AzureBlobFileSystem.getFileStatus(AzureBlobFileSystem.java:395)
        at org.apache.hadoop.fs.Globber.getFileStatus(Globber.java:65)
        at org.apache.hadoop.fs.Globber.doGlob(Globber.java:294)
        at org.apache.hadoop.fs.Globber.glob(Globber.java:149)
        at org.apache.hadoop.fs.FileSystem.globStatus(FileSystem.java:2016)
        at org.apache.hadoop.fs.shell.PathData.expandAsGlob(PathData.java:353)
        at org.apache.hadoop.fs.shell.Command.expandArgument(Command.java:250)
        at org.apache.hadoop.fs.shell.Command.expandArguments(Command.java:233)
        at org.apache.hadoop.fs.shell.FsCommand.processRawArguments(FsCommand.java:104)
        at org.apache.hadoop.fs.shell.Command.run(Command.java:177)
        at org.apache.hadoop.fs.FsShell.run(FsShell.java:327)
        at org.apache.hadoop.util.ToolRunner.run(ToolRunner.java:76)
        at org.apache.hadoop.util.ToolRunner.run(ToolRunner.java:90)
        at org.apache.hadoop.fs.FsShell.main(FsShell.java:390)

做了什么:

  1. 使用https://docs.microsoft.com/en-us/azure/storage/blobs/data-lake-storage-quickstart-create-account创建的存储帐户

  2. 使用 https://docs.microsoft.com/en-us/azure/active-directory/develop/howto-create-service-principal-portal 创建 Azure AD 应用程序

  3. 将 AD 用户作为访问控制 (IAM) 中的 STORAGE BLOB DATA OWNER 添加到存储帐户。

根据Apache documentation我创建了一个控制台命令

hadoop fs -Dfs.azure.ssl.channel.mode=Default_JSSE
-Dfs.azure.account.auth.type=OAuth
-Dfs.azure.account.oauth.provider.type=org.apache.hadoop.fs.azurebfs.oauth2.UserPasswordTokenProvider
-Dfs.azure.account.oauth2.client.endpoint=https://login.microsoftonline.com/<TENANT ID>/oauth2/v2.0/authorize
-Dfs.azure.account.oauth2.user.name=<USER_NAME@mail.com>
-Dfs.azure.account.oauth2.user.password=<PASSWORD>
-ls abfss://<CONTAINER NAME>@<STORAGE ACCOUNT>.dfs.core.windows.net/

如果尝试使用这个端点

https://login.microsoftonline.com/<TENANT ID>/oauth2/v2.0/token

输出是

ls: AADToken: HTTP connection failed for getting token from AzureAD. Http response: 400 Bad Request

所以下面的命令应该显示容器中的文件夹和文件的列表。命令或 Azure 中的容器配置有问题?请指教。

【问题讨论】:

    标签: azure hadoop azure-data-lake


    【解决方案1】:

    无论您使用的是 Azure AD 用户还是服务主体,您都必须使用 OAuth2 V1 令牌端点,因为它受 Authenticator 类的支持。这是令牌端点 URL:

    https://login.microsoftonline.com/{TENANT_ID}/oauth2/token
    

    Here你可以找到V1和V2端点的区别。

    话虽如此,您必须使用的控制台命令变为:

    hadoop fs -Dfs.azure.ssl.channel.mode=Default_JSSE \
    -Dfs.azure.account.auth.type=OAuth \
    -Dfs.azure.account.oauth.provider.type=org.apache.hadoop.fs.azurebfs.oauth2.UserPasswordTokenProvider \
    -Dfs.azure.account.oauth2.client.endpoint=https://login.microsoftonline.com/{TENANT_ID}/oauth2/token \
    -Dfs.azure.account.oauth2.user.name={USER_NAME@mail.com} \
    -Dfs.azure.account.oauth2.user.password={PASSWORD} \
    -ls abfss://{CONTAINER NAME}@{STORAGE_ACCOUNT}.dfs.core.windows.net/
    

    根据您的问题,您似乎还想使用服务主体进行身份验证,在这种情况下,您必须使用 ClientCredsTokenProvider 而不是 UserPasswordTokenProvider,如下所示:

    hadoop fs -Dfs.azure.ssl.channel.mode=Default_JSSE \
    -Dfs.azure.account.auth.type=OAuth \
    -Dfs.azure.account.oauth.provider.type=org.apache.hadoop.fs.azurebfs.oauth2.ClientCredsTokenProvider \
    -Dfs.azure.account.oauth2.client.endpoint=https://login.microsoftonline.com/{TENANT_ID}/oauth2/token \
    -Dfs.azure.account.oauth2.client.id={CLIENT_ID} \
    -Dfs.azure.account.oauth2.client.secret={SECRET_KEY} \
    -ls abfss://{CONTAINER NAME}@{STORAGE_ACCOUNT}.dfs.core.windows.net/
    

    您还可以将身份验证信息存储在 core-site.xml 文件中,如 hadoop docs 中所述。如果您想使用多个存储帐户,您可以将属性名称更改为以 dfs 端点结尾,如下例所示:

    <property>
      <name>fs.azure.account.auth.type.{STORAGE_ACCOUNT}.dfs.core.windows.net</name>
      <value>OAuth</value>
      <description>
      Use OAuth authentication
      </description>
    </property>
    <property>
      <name>fs.azure.account.oauth.provider.type.{STORAGE_ACCOUNT}.dfs.core.windows.net</name>
      <value>org.apache.hadoop.fs.azurebfs.oauth2.ClientCredsTokenProvider</value>
      <description>
      Use client credentials
      </description>
    </property>
    <property
      <name>fs.azure.account.oauth2.client.endpoint.{STORAGE_ACCOUNT}.dfs.core.windows.net</name>
      <value>https://login.microsoftonline.com/{TENANT_ID}/oauth2/token</value>
      <description>
      URL of OAuth endpoint
      </description>
    </property>
    <property>
      <name>fs.azure.account.oauth2.client.id.{STORAGE_ACCOUNT}.dfs.core.windows.net</name>
      <value>{CLIENT_ID}</value>
      <description>
      Client ID
      </description>
    </property>
    <property>
      <name>fs.azure.account.oauth2.client.secret.{STORAGE_ACCOUNT}.dfs.core.windows.net</name>
      <value>{SECRET_KEY}</value>
      <description>
      Secret
      </description>
    </property>
    

    对不起,如果为时已晚,我刚刚遇到了这个问题,这个问题正在寻找解决方案的过程中,当我开始工作时,我认为有人可能会觉得这很有帮助。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2019-09-10
      • 2021-03-03
      • 2019-05-22
      • 2020-09-22
      • 1970-01-01
      • 2020-07-21
      • 2020-06-14
      • 1970-01-01
      相关资源
      最近更新 更多