Question: I have two Pydantic models: from typing import List, Union from pydantic import BaseModel class Students: class Student(BaseModel): StudentName: str StudentAge: int class StudentRequest(BaseModel): Class: int UUID: str Students: Union[List[Student], None]  For the above class at Students: Union[List[Student], None], I get the error Unresolved reference 'Student'. Can we not define a model under a class and use it for segregating them? The code below works, but I want to get an understanding whether the above BaseModel nested under a class will work or not: class Student(BaseModel): StudentName: str StudentAge: int class StudentRequest(BaseModel): Class: int UUID: str Students: Union[List[Student], None] 

Answer: You need to understand that as long as the outer class is not fully constructed (when you are still setting up things inside its namespace), you will inevitably have to deal with forward references. So there are two mandatory things (and one optional) you need to remember, when doing this. 1) Use the qualified class name OuterClass.InnerClass The Python interpreter itself will have no trouble with a forward reference to another inner class in an annotation. That is simply because it does not actually do anything with those annotations by default. So you could just do this: from pydantic import BaseModel class OuterClass: class Student(BaseModel): name: str age: int class StudentRequest(BaseModel): ... students: list["Student"]  But this will fall apart with Pydantic models because those actually use those annotations to construct objects based off of them. As you will see in the next section, at some point Pydantic will have to actually resolve the refernce to Student so get the actual underlying class at runtime. And since that will inevitably happen outside the scope of the OuterClass, without the qualified name, it will run into a NameError. So you have to do it like this: ... class OuterClass: class Student(BaseModel): ... class StudentRequest(BaseModel): ... students: list["OuterClass.Student"]  2) Update forward references after the outer class is constructed An annotation as shown above is internally stored as a ForwardRef object. As mentioned above, Pydantic will have to resolve those forward references eventually, for you to be able to actually use those models. However it is not always able to do so automatically. To quote the documentation:  In some cases, a ForwardRef won't be able to be resolved during model creation. [...] When this happens, you'll need to call update_forward_refs after the model has been created before it can be used.  But with a setup like yours, when the model is nested in the namespace of an outer class, you cannot just do so after the model is created. You must do that after the outer class is created. So with that setup, you will have to do this: from pydantic import BaseModel class OuterClass: class Student(BaseModel): name: str age: int class StudentRequest(BaseModel): ... students: list["OuterClass.Student"] OuterClass.StudentRequest.update_forward_refs()  Notice that the call happens outside of OuterClass after it is created. 3) Enable postponed evaluation of annotations (optional) Since PEP 563 you can do from __future__ import annotations at the top of your module and then omit the quotes from your forward references. This just improves readability and makes things generally easier to code. So in total, your code should look like this: from __future__ import annotations from pydantic import BaseModel class OuterClass: class Student(BaseModel): name: str age: int class StudentRequest(BaseModel): ... students: list[OuterClass.Student] OuterClass.StudentRequest.update_forward_refs()  Demo: print(OuterClass.StudentRequest.schema_json(indent=4)) obj = OuterClass.StudentRequest.parse_obj({ "students": [ {"name": "foo", "age": 18}, {"name": "bar", "age": 19}, ] }) print(obj.json(indent=4))  Output: { "title": "StudentRequest", "type": "object", "properties": { "students": { "title": "Students", "type": "array", "items": { "$ref": "#/definitions/Student" } } }, "required": [ "students" ], "definitions": { "Student": { "title": "Student", "type": "object", "properties": { "name": { "title": "Name", "type": "string" }, "age": { "title": "Age", "type": "integer" } }, "required": [ "name", "age" ] } } }  { "students": [ { "name": "foo", "age": 18 }, { "name": "bar", "age": 19 } ] }