簡體   English   中英

Invoke-WebRequest Canvas LMS API 分頁

[英]Invoke-WebRequest Canvas LMS API pagination

我似乎找不到關於這個主題的任何例子,我想知道如何去做。 任何人都可以向我展示一個示例或指向我如何使用 Invoke web-request 在 powershell 中進行分頁的鏈接? 我面臨的挑戰是我正在對一次只返回 100 行的服務器進行 API 調用。 為了獲得更多行,我必須再次調用服務器。 我不知道該怎么做。 如果有幫助,這里是 Canvas LMS 提供的鏈接和我目前擁有的代碼。

分頁

分頁

默認情況下,返回多個項目的請求將分頁為 10 個項目。 您可以使用 ?per_page 參數設置自定義的每頁數量。 您可以將 per_page 設置為多大有一個未指定的限制,因此請務必始終檢查鏈接標頭。

要檢索其他頁面,應使用返回的鏈接標頭。 這些鏈接應被視為不透明。 它們將是絕對 url,包括檢索所需的當前、下一頁、上一頁、第一頁或最后一頁所需的所有參數。 一個例外是,如果發送 access_token 參數進行身份驗證,則不會包含在返回的鏈接中,必須重新附加。

鏈接標頭中提供了分頁信息:

 Link: <https://<canvas>/api/v1/courses/:id/discussion_topics.json?opaqueA>; rel="current", <https://<canvas>/api/v1/courses/:id/discussion_topics.json?opaqueB>;> rel="next", <https://<canvas>/api/v1/courses/:id/discussion_topics.json?opaqueC>;> rel="first", <https://<canvas>/api/v1/courses/:id/discussion_topics.json?opaqueD>;> rel="last"

可能的 rel 值是:

當前 - 鏈接到當前結果頁面。 next - 鏈接到下一頁結果。 prev - 鏈接到上一頁結果。 first - 鏈接到第一頁的結果。 last - 鏈接到結果的最后一頁。 僅當它們相關時才會包含這些內容。 例如,結果的第一頁將不包含 rel="prev" 鏈接。 如果在每個請求上計算總計數太昂貴,也可以排除 rel="last" 。

開始的產品

$curlly=""
$url_main="https://[instance].instructure.com/api/v1/accounts/1/courses?per_page=1"
$security_token="imhungry"
$header = @{"Authorization"="Bearer "+ $security_token; "rel"="last"}
$curlly=Invoke-WebRequest -Headers $header   -Method Get   -Uri $url_main   
$curlly = ConvertFrom-Json $curlly.Content
foreach($course in $curlly)
{
    $course.name
}
$curlly.Count

最終產品

 ##This is an example on how to use pagination in powershell
$url_main="https://[instance].instructure.com/api/v1/accounts/1/courses?per_page=100"
$security_token="boyimhungry"
$header = @{"Authorization"="Bearer "+ $security_token}
$purlly=Invoke-WebRequest -Headers $header   -Method Get   -Uri $url_main   
$curlly = ConvertFrom-Json $purlly.Content
$url_main = $purlly.Headers.Link.Split(",")[1].Replace("<","").Replace(">","") ## you can get away with just doing one replace("<","") but it looks neater this way
while( !$url_main.Contains("prev"))
{
$purlly=Invoke-WebRequest -Headers $header   -Method Get   -Uri $url_main   
$curlly += ConvertFrom-Json $purlly.Content
$url_main = $purlly.Headers.Link.Split(",")[1].Replace("<","").Replace(">","")
cls
$curlly.Count
$url_main
}
foreach($course in $curlly)
{
    $course.name
}
$curlly.Count

我知道你已經接受了一個答案,但我想我會給出我的代碼示例,以防萬一有人需要。 這個例子是獲取我們所有 Canvas 用戶的列表。 不是一個糟糕的過程——大部分工作都是用 4 行 do..while 循環完成的。

$token = "YOUR_ACCESS_TOKEN"
$headers = @{"Authorization"="Bearer "+$token}
$allCanvasUsers = New-Object System.Collections.ArrayList @()
$pageNumber = 1

Function RequestPageOfUsers($page) {
    $script:resultsPage = Invoke-WebRequest -Method GET -Headers $headers -Uri "https://$domain/api/v1/accounts/self/users?per_page=100&search_term=P00&page=$page"
    $usersPage = ConvertFrom-Json $resultsPage.Content

    foreach ($user in $usersPage) {
        $script:allCanvasUsers.Add($user)
    }
}

do {
    RequestPageOfUsers $pageNumber
    $pageNumber++
} while ($resultsPage.Headers.Link.Contains('rel="next"'))

大衛貝克的回答太棒了,幾乎對我有用,但只返回了一頁。 不知道為什么,但是 CONTAINS('...') 測試總是返回 FALSE。

為了讓它起作用,我不得不對 WHILE 條件做一個小改動。 對我來說,ResultsPage 對象返回一個名為 RelationLink 的屬性,它是一個包含鍵值對的字典。 分頁結果集中的最后一頁沒有“下一頁”鍵。 因此,我的 DO-WHILE 循環一直運行,直到發現“Next”值為空。

$Token = '<YOUR-TOKEN>'
$headers = @{"Authorization"="Bearer "+$token}
$allCanvasUsers = New-Object System.Collections.ArrayList @()
$pageNumber = 1

Function RequestPageOfUsers($page) {

    $script:resultsPage = Invoke-WebRequest `
        -Method GET `
        -Headers $headers `
        -Uri "https://<DOMAIN>:443/api/v1/accounts/self/users?per_page=100&page=$page"
    $usersPage = ConvertFrom-Json $resultsPage.Content

    foreach ($user in $usersPage) { 
        $script:allCanvasUsers.Add($user)
    }
}

do {
    RequestPageOfUsers $pageNumber
    $pageNumber++
} while ($resultsPage.RelationLink.Next -NE $NULL)

這看起來真的很痛苦。

對於每個分頁請求,您將返回一個Link標頭,其中包含它們描述的一個或多個鏈接。

出於您的目的(順序閱讀每個結果),您只需要真正關心鏈接rel=next鏈接。 你會一直調用那個直到不再有rel=next ,這就是你知道你在最后一頁的方式。

您不提供 rel 部分; 這不是標題。 它可以讓您確定要使用哪個鏈接,然后按原樣使用該鏈接。

因此,您需要做的基本概述:

  1. 提出第一個請求。
  2. 通讀返回的Link標頭,找到與rel=next對應的標頭(如果不存在,則完成)。
  3. 直接向您找到的鏈接發出下一個請求。
  4. 再次解析Link頭,重復。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM