Как получить все записи в COVID-19 Data Lake linelistrecords - PullRequest
3 голосов
/ 11 апреля 2020

Я бы хотел использовать https://api.c3.ai/covid/api/1/linelistrecord/fetch API, но вернул только 2000 записей. Я знаю, что существует более 2000 записей - как их получить?

Вот мой код в R:

library(tidyverse)
library(httr)
library(jsonlite)

resp <- POST(
  "https://api.c3.ai/covid/api/1/linelistrecord/fetch",
  body = list(
    spec = {}
  ) %>% toJSON(auto_unbox = TRUE),
  accept("application/json")
)

length(content(resp)$objs)

Я получаю 2000 записей.

Ответы [ 2 ]

4 голосов
/ 11 апреля 2020

spec, который вы передаете, имеет следующие дополнительные поля, среди прочего:

  • limit // максимальное количество возвращаемых объектов
  • offset / / смещение, используемое для постраничного чтения

Значение по умолчанию limit равно 2000.

Возвращаемый результат выборки имеет логическое поле вместе с массивом объектов, называется hasMore, что указывает, есть ли еще записи в базовом хранилище данных.

Вы можете написать al oop, который заканчивается, когда hasMore ложно. Начните с offset, равного 0, и ограничьте n (скажем, n=2000), а затем итеративно увеличивайте смещение на n.

library(tidyverse)
library(httr)
library(jsonlite)

limit <- 2000
offset <- 0
hasMore <- TRUE
all_objs <- c()

while(hasMore) {
  resp <- POST(
    "https://api.c3.ai/covid/api/1/linelistrecord/fetch",
    body = list(
      spec = list(
        limit = limit,
        offset = offset,
        filter = "contains(location, 'California')" # just as an example, to cut down on the dataset
      )
    ) %>% toJSON(auto_unbox = TRUE),
    accept("application/json")
  )
  hasMore <- content(resp)$hasMore
  offset <- offset + limit
  all_objs <- c(all_objs, content(resp)$objs)
}

length(all_objs)
1 голос
/ 16 апреля 2020

Вы также можете сделать что-то подобное в Python. Вот фрагмент кода для того же самого в Python

import requests
headers = {'Accept': 'application/json'}
import io
import pandas as pd

def read_data(url, payload, headers = headers):

    df_list = []
    has_more = True
    offset = 0
    payload['spec']['offset'] = offset
    while has_more:
        response = requests.post('https://api.c3.ai/covid/api/1/linelistrecord/fetch', json=payload, headers = headers)
        df = pd.DataFrame.from_dict(response.json()['objs'])
        has_more = response.json()['hasMore']
        payload['spec']['offset'] += df.shape[0]
        df_list.append(df)
    df = pd.concat(df_list)

    return df
url = 'https://api.c3.ai/covid/api/1/linelistrecord/fetch'
payload = {
    "spec":{
        "filter": "exists(hospitalAdmissionDate)",
        "include": "caseConfirmationDate, outcomeDate, hospitalAdmissionDate, age"
    }
}
df = read_data(url, payload)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...