Python — запись в CSV из нескольких файлов JSON

#python #json #pandas #api #csv

#python #json #панды #API #csv

Вопрос:

Я весь день безуспешно пытался написать несколько файлов JSON, которые я извлекаю из nys.gov веб-сайт с данными о COVID для одного (или нескольких) Файлы CSV.

Я могу успешно объединить файлы JSON, но не смог объединить их вместе в формате, который я могу использовать для построения графиков. Я знаю, что проблема где-то в моем цикле for, но после многих попыток я не нашел успешного метода либо добавления данных в один csv, либо создания нескольких csv-файлов, с которыми я мог бы затем работать в pandas. Вот мой код, в настоящее время кажется, что он перебирает циклы и сбрасывает окончательный json в мой csv…

 import csv
import datetime 
import json
import pandas as pd
import urllib.request as request

one_day = datetime.datetime.today() - datetime.timedelta(days=1)
two_days = datetime.datetime.today() - datetime.timedelta(days=2)
thr_days = datetime.datetime.today() - datetime.timedelta(days=3)
for_days = datetime.datetime.today() - datetime.timedelta(days=4)
fiv_days = datetime.datetime.today() - datetime.timedelta(days=5)
six_days = datetime.datetime.today() - datetime.timedelta(days=6)
sev_days = datetime.datetime.today() - datetime.timedelta(days=7)
egt_days = datetime.datetime.today() - datetime.timedelta(days=8)

one_day_str = one_day.strftime("%Y-%m-%dT00:00:00.000")
two_day_str = two_days.strftime("%Y-%m-%dT00:00:00.000")
thr_day_str = thr_days.strftime("%Y-%m-%dT00:00:00.000")
for_day_str = for_days.strftime("%Y-%m-%dT00:00:00.000")
fiv_day_str = fiv_days.strftime("%Y-%m-%dT00:00:00.000")
six_day_str = six_days.strftime("%Y-%m-%dT00:00:00.000")
sev_day_str = sev_days.strftime("%Y-%m-%dT00:00:00.000")
egt_day_str = egt_days.strftime("%Y-%m-%dT00:00:00.000")

url_one = 'https://health.data.ny.gov/resource/xdss-u53e.json?test_date='   one_day_str
url_two = 'https://health.data.ny.gov/resource/xdss-u53e.json?test_date='   two_day_str
url_thr = 'https://health.data.ny.gov/resource/xdss-u53e.json?test_date='   thr_day_str
url_for = 'https://health.data.ny.gov/resource/xdss-u53e.json?test_date='   for_day_str
url_fiv = 'https://health.data.ny.gov/resource/xdss-u53e.json?test_date='   fiv_day_str
url_six = 'https://health.data.ny.gov/resource/xdss-u53e.json?test_date='   six_day_str
url_sev = 'https://health.data.ny.gov/resource/xdss-u53e.json?test_date='   sev_day_str
url_egt = 'https://health.data.ny.gov/resource/xdss-u53e.json?test_date='   egt_day_str

url_lst = [url_one,url_two,url_thr, url_for, url_fiv, url_six, url_sev, url_egt]

d = []

def write_json(data, filename='data.json'):
    with open(filename,'w') as f: 
        json.dump(data, f, indent=4)

for url in url_lst:
    with request.urlopen(url) as response:
        #   print(url)
        source = response.read()
        data = json.loads(source)

    if len(data) == 0:
        continue

    with open ("covid.json", 'w') as outfile:
        json.dump(data, outfile)

    with open('covid.json') as json_data:
        j = json.load(json_data)
        d.append(j)
        write_json(d)  
    
    filename = "County Stats.csv"
    fields = ["Date","County", "New Positives", "All Positives", "New Tests", "All Tests"]
    with open(filename, 'w') as fw:
        cf = csv.writer(fw, lineterminator='n')
        # write the header
        cf.writerow(fields)
        
        for counties in data:
            date = counties['test_date']
            cnty = counties['county']
            new_pos = counties['new_positives']
            cum_pos = counties['cumulative_number_of_positives']
            new_tests = counties['total_number_of_tests']
            cum_tests = counties['cumulative_number_of_tests']
            cf.writerow([date,cnty, new_pos, cum_pos, new_tests, cum_tests])

 

Я, вероятно, где-то между новичком и средним уровнем с python, поэтому, пожалуйста, простите любые плохие методы кодирования. Заранее благодарю.

  • Конор

Комментарии:

1. без примера данных или файла мы не сможем помочь.

2. если вы запустите код, он извлечет данные, он использует библиотеку запросов для доступа к nys.gov API

3. код создаст файлы data.json, covid.json и County Stats.csv

4. в файле data.json вы найдете данные за 7 дней, которые я пытаюсь объединить.

5. Похоже, вы записываете заголовки в CSV несколько раз. fields содержит шесть элементов, тогда как строк данных всего пять. Я не знаю, может ли какой-либо из них быть вашей проблемой.

Ответ №1:

Хорошо, с помощью моего бывшего профессора и доверенного лица я понял это!

Пара вещей:

  1. Я не индексировал цикл for, добавление переменной index перед циклом и приращение индекса (index =1) создали итерацию для имени файла csv.
  2. Затем с помощью fstring имя файла csv обновляется каждый раз, когда выполняется цикл, создавая отдельный файл для каждого из извлекаемых ресурсов JSON.
 d = []
def write_json(data, filename='data.json'):
    with open(filename,'w') as f: 
        json.dump(data, f, indent=4)
 
index = 0
for url in url_lst:
    index  =1
    with request.urlopen(url) as response:
        source = response.read()
        data = json.loads(source)
 
        if len(data) == 0:
            continue

        with open ("covid.json", 'w') as outfile:
            json.dump(data, outfile)

        with open('covid.json') as json_data:
            j = json.load(json_data)
            d.append(j)
            write_json(d)  
        
        print(index)    
        fields = ["Date","County", "New Positives", "All Positives", "New Tests", "All Tests"]
        filename = f"County Stats {index}.csv"
        with open(filename, 'w') as fw:
            cf = csv.writer(fw, lineterminator='n')
            # write the header
            cf.writerow(fields)
            for counties in data:   
                date = counties['test_date']
                cnty = counties['county']
                new_pos = counties['new_positives']
                cum_pos = counties['cumulative_number_of_positives']

                new_tests = counties['total_number_of_tests']
                cum_tests = counties['cumulative_number_of_tests']
                cf.writerow([date,cnty, new_pos, cum_pos, new_tests, cum_tests])