【问题标题】:Accessing Microsoft Graph With PowerShell使用 PowerShell 访问 Microsoft Graph
【发布时间】:2018-01-31 17:11:34
【问题描述】:

我一直在尝试使用 PowerShell 访问 Microsoft Graph。

首先我尝试使用authorization flowInvoke-WebRequestInvoke-RestMethod,我都无法开始工作。

然后我找到了this blog,它展示了如何使用 PowerShell 和几个 Azure 模块进行操作。下面是我正在使用的代码(直接从该博客中提取),但每次我到达 Invoke-RestMethod(在 do-while 循环中)而不是得到查询结果时,我都会得到 403 Forbidden error

Invoke-RestMethod : 远程服务器返回错误:(403) Forbidden。

Function GetAuthToken {
    Param (
        [Parameter()]
        $TenantName
    )
    Import-Module Azure
    $clientId = "1950a258-227b-4e31-a9cf-717495945fc2"
    $resourceAppIdURI = "https://graph.microsoft.com"
    $authority = "https://login.microsoftonline.com/$TenantName"
    $authContext = New-Object "Microsoft.IdentityModel.Clients.ActiveDirectory.AuthenticationContext" -ArgumentList $authority
    $Credential = Get-Credential
    $AADCredentialUser = New-Object "Microsoft.IdentityModel.Clients.ActiveDirectory.UserCredential" -ArgumentList $credential.UserName, $credential.Password
    $authResult = $authContext.AcquireToken($resourceAppIdURI, $clientId, $AADCredentialUser)
    Write-Output $authResult
}

Function GetAllObjectOfType {
    param
    (
        [Parameter(Mandatory = $true)]
        $Tenant,
        [Parameter(Mandatory = $true)]
        $Type,
        [Parameter(Mandatory = $false)]
        $BatchSize = 100,
        [Parameter(Mandatory = $false)]
        $Version = 'Beta'
    )

    #------Get the authorization token------#
    $token = GetAuthToken -TenantName $tenant

    #------Building Rest Api header with authorization token------#
    $authHeader = @{
        'Content-Type'  = 'application/json'
        'Authorization' = $token.CreateAuthorizationHeader()
    }

    #------Initial URI Construction------#
    #$uritest = "https://graph.microsoft.com/v1.0/users/user@contoso.com/mailFolders/Inbox/childFolders"
    $uritest = "https://graph.microsoft.com/v1.0/me/mailFolders/Inbox"
    #Join-Path -Path ''
    $ObjCapture = @()
    do {
        $users = Invoke-RestMethod -Uri $uritest -Headers $authHeader -Method Get
        $FoundUsers = ($Users.value).count
        write-host "URI" $uri " | Found:" $FoundUsers
        #------Batched URI Construction------#
        $uri = $users.'@odata.nextlink'
        $ObjCapture = $ObjCapture + $users.value

    }until ($uri -eq $null)
    $ObjCapture
}

我可以从 Graph Explorer 运行同样的查询 (/v1.0/me/mailFolders/Inbox),它运行得非常好,没有错误。

GetAuthToken 似乎正在工作,因为我确实得到了一个带有过期、刷新令牌等的令牌,$token.CreateAuthorizationHeader() 也返回了正确的Authorization = Bearer token

我以前从未对 Microsoft Graph 做过任何事情,所以我确信我做错了什么,但我终生无法弄清楚是什么。

【问题讨论】:

  • 您能否添加您收到的令牌以及您为获得clientId 所采取的步骤(包括范围/权限)?
  • @MarcLaFleur-MSFT 实际上,clientId 与我从中获得步骤的文章中使用的相同(所以我假设这是不正确的)。我不确定我可以添加令牌是什么意思。将其添加到评论中?

标签: powershell microsoft-graph-api


【解决方案1】:

您不能重复使用该博文中的 clientid。您需要通过注册您的应用程序来获取您自己的clientid。有关如何注册您的应用程序的详细信息,请参阅Register your app with the Azure AD v2.0 endpoint

【讨论】:

  • 即使我使用自己的凭据访问图表,是否也需要注册应用程序?我在 Azure 门户中创建了一个应用程序,并尝试将其中的 clientidclientsecretMicrosoft.IdentityModel.Clients.ActiveDirectory.ClientCredential 对象一起使用。然后使用该对象使用$authContext.AcquireToken($resourceAppIdURI,$AADCredentialApps) 创建身份验证令牌,但我也无法使其正常工作,它返回相同的错误消息。
  • 每个应用程序都需要一个应用程序/客户端 ID 才能对其进行授权。为了使用客户凭证,您将需要客户 ID/秘密管理员同意书。请参阅 developer.microsoft.com/en-us/graph/docs/concepts/… 了解其工作原理。
  • 如果我不使用 v2 端点进行身份验证,我可以通过 Azure 门户中的 Azure AD 刀片授予管理员同意,我可以不吗?我想也许我不理解的是上面的代码使用的是 v2 端点。那准确吗?如果是这样,我必须通过 Microsoft 应用注册门户来创建应用并授予权限...
【解决方案2】:

这似乎是在同一来源的follow-up blog post 中回答的。

当一个应用程序被创建时,默认情况下它只有权访问它的数据 通过“登录并阅读用户”使用该帐户登录的用户 个人资料”委派的权限。如果您尝试执行使用它的脚本 AppID/ClientID 查询 Azure AD 以获取目录中所有用户的列表, 您会收到一条错误消息,说明 (403) Forbidden 因为它没有 足够的权限来执行该活动。

【讨论】:

    【解决方案3】:

    把这个放在这里,以防任何其他流浪的开发者像我一样遇到这个帖子。这是我用来从租户获取访问令牌的 powershell 函数。 ClientId 和 Secret 是在 Azure 应用注册中创建的,就像其他人提到的那样。

    $clientId = $args[0]
    $secret = $args[1]
    $redeemURI = "https://login.microsoftonline.com/{tenantGuid}/oauth2/v2.0/token"
    
    $body = "client_id=$clientId&scope=https%3A%2F%2Fgraph.microsoft.com%2F.default&client_secret=$secret&grant_type=client_credentials"
    
    $response = Invoke-RestMethod -Method Post -Uri $redeemURI -Body $body -ContentType "application/x-www-form-urlencoded"
    
    return $response.access_token
    

    用法:

    $token = ./GetAccessToken.ps1 "{clientId}" "{secret}"
    

    【讨论】:

      【解决方案4】:

      我认为它需要 AD Azure Premium 2 许可证 enter link description here

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2020-07-21
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-04-01
        • 2021-12-29
        相关资源
        最近更新 更多