Search code examples
pythonpydantic

Why do I get "Validators defined with incorrect fields" when trying to validate JSON data using pydantic?


I am trying to parse a JSON object to pydantic validator and it's giving a compiler error.

pydantic.errors.ConfigError: Validators defined with incorrect fields: validate_grade

{
  "grade": "A"
  "subject": [
    {
      "physics": "PHY",
      "chemistry": "CHE",
      "classTime": {
    "date": "2024-03-25",
    "time": null
      },
      "labTime":null
      }
    }
  ]
}

The implementation code:

class Grade(BaseModel):
    @validator("grade")
    def validate_grade(cls, val):
        if (val == None):
            raise ValueError("grade is null")     

class subject(BaseModel): 
    @validator("classTime", pre=True, always=True)
    def validate_classTime(cls, value, values):
        date_str = value.get('date', '')
        time_str = value.get('time', '')

The above implementation is throwing the error after adding the section:

class Grade(BaseModel):     

I also want to get the "grade" inside the class subject. I tried different options after referring to the similar implementations, but there is no luck.


Solution

  • There is no model that contains grade and subject fields.

    from pydantic import BaseModel, validator
    from typing import List, Optional
    from datetime import date, time
    
    
    class ClassTime(BaseModel):
        date: Optional[date]
        time: Optional[time]
    
    
    class Subject(BaseModel):
        physics: str
        chemistry: str
        classTime: Optional[ClassTime]
        labTime: Optional[str]
    
    
    class Student(BaseModel):
        grade: str
        subject: List[Subject]
    
        @validator("grade")
        def validate_grade(cls, val):
            if val is None:
                raise ValueError("grade is null")
            return val
    
        @validator("subject", each_item=True)
        def validate_subject(cls, val):
            if val.classTime:
                if not val.classTime.date:
                    raise ValueError("classTime.date is null")
            return val
    
    
    json_data = {
        "grade": "A",
        "subject": [
            {
                "physics": "PHY",
                "chemistry": "CHE",
                "classTime": {
                    "date": "2024-03-25",
                    "time": None
                },
                "labTime": None
            }
        ]
    }
    
    student = Student(**json_data)
    print(student)
    

    Output:

    grade='A' subject=[Subject(physics='PHY', chemistry='CHE', classTime=ClassTime(date=datetime.date(2024, 3, 25), time=None), labTime=None)]