У меня есть рабочая модель для получения набора данных json
с использованием pydantic
.Набор данных модели выглядит следующим образом:
data = {'thing_number': 123,
'thing_description': 'duck',
'thing_amount': 4.56}
Я хотел бы иметь список файлов json
в качестве набора данных и иметь возможность проверить их.В конечном итоге список будет преобразован в записи в pandas
для дальнейшей обработки.Моя цель состоит в том, чтобы проверить произвольно длинный список json
записей, который выглядит примерно так:
bigger_data = [{'thing_number': 123,
'thing_description': 'duck',
'thing_amount': 4.56},
{'thing_number': 456,
'thing_description': 'cow',
'thing_amount': 7.89}]
Основная настройка, которую я сейчас имею, заключается в следующем.Обратите внимание, что добавление class ItemList
является частью попытки заставить работать произвольную длину.
from typing import List
from pydantic import BaseModel
from pydantic.schema import schema
import json
class Item(BaseModel):
thing_number: int
thing_description: str
thing_amount: float
class ItemList(BaseModel):
each_item: List[Item]
Затем базовый код выдаст то, что я ищу, в объекте массива, который будет приниматьItem
объекты.
item_schema = schema([ItemList])
print(json.dumps(item_schema, indent=2))
{
"definitions": {
"Item": {
"title": "Item",
"type": "object",
"properties": {
"thing_number": {
"title": "Thing_Number",
"type": "integer"
},
"thing_description": {
"title": "Thing_Description",
"type": "string"
},
"thing_amount": {
"title": "Thing_Amount",
"type": "number"
}
},
"required": [
"thing_number",
"thing_description",
"thing_amount"
]
},
"ItemList": {
"title": "ItemList",
"type": "object",
"properties": {
"each_item": {
"title": "Each_Item",
"type": "array",
"items": {
"$ref": "#/definitions/Item"
}
}
},
"required": [
"each_item"
]
}
}
}
Установка работает на передаваемом отдельном элементе json:
item = Item(**data)
print(item)
Item thing_number=123 thing_description='duck' thing_amount=4.56
Но когда я пытаюсь передать один элемент в ItemList
модель, онвозвращает ошибку:
item_list = ItemList(**data)
---------------------------------------------------------------------------
ValidationError Traceback (most recent call last)
<ipython-input-94-48efd56e7b6c> in <module>
----> 1 item_list = ItemList(**data)
/opt/conda/lib/python3.7/site-packages/pydantic/main.cpython-37m-x86_64-linux-gnu.so in pydantic.main.BaseModel.__init__()
/opt/conda/lib/python3.7/site-packages/pydantic/main.cpython-37m-x86_64-linux-gnu.so in pydantic.main.validate_model()
ValidationError: 1 validation error for ItemList
each_item
field required (type=value_error.missing)
Я также попытался передать bigger_data
в массив, думая, что он должен начинаться как список.это также возвращает ошибку - - Хотя я, по крайней мере, лучше понимаю ошибку словаря, которую я не могу понять, как ее устранить.
item_list2 = ItemList(**data_big)
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
<ipython-input-100-8fe9a5414bd6> in <module>
----> 1 item_list2 = ItemList(**data_big)
TypeError: MetaModel object argument after ** must be a mapping, not list
Спасибо.
Другие вещи, которые я пробовал
Я попытался передать данные в конкретный ключ с еще большей удачей (может быть?).
item_list2 = ItemList(each_item=data_big)
---------------------------------------------------------------------------
ValidationError Traceback (most recent call last)
<ipython-input-111-07e5c12bf8b4> in <module>
----> 1 item_list2 = ItemList(each_item=data_big)
/opt/conda/lib/python3.7/site-packages/pydantic/main.cpython-37m-x86_64-linux-gnu.so in pydantic.main.BaseModel.__init__()
/opt/conda/lib/python3.7/site-packages/pydantic/main.cpython-37m-x86_64-linux-gnu.so in pydantic.main.validate_model()
ValidationError: 6 validation errors for ItemList
each_item -> 0 -> thing_number
field required (type=value_error.missing)
each_item -> 0 -> thing_description
field required (type=value_error.missing)
each_item -> 0 -> thing_amount
field required (type=value_error.missing)
each_item -> 1 -> thing_number
field required (type=value_error.missing)
each_item -> 1 -> thing_description
field required (type=value_error.missing)
each_item -> 1 -> thing_amount
field required (type=value_error.missing)