I created a union type of objects. They all have a field role
to differentiate them.
Here we have teacher and student:
type User =
{
role: "student";
followClasses: string[];
} |
{
role: "teacher";
since: number;
};
Then I wanted to create a function to generate a default student:
const defaultStudent = (): User => ({
role: "student",
followClasses: [],
});
But since the return type is the union type User, typescript doesn't know that it's a student, and throw me a warning when I type this:
const student = defaultStudent();
console.log(student.followClasses);
// Warning here ⮥
How to make the function defaultStudent
have a constrained return type (student)?
Extract the two members of the unions as individual types
type Student = {
role: "student"
followClasses: string[]
}
type Teacher = {
role: "teacher"
since: number
}
and define your union from them directly
type User = Student | Teacher
At this point, you can say that your defaultStudent
function doesn't just return a User
, you can be more precise than that. It returns a Student
.
const defaultStudent = (): Student => ({
role: "student",
followClasses: [],
})
const student = defaultStudent()
console.log(student.followClasses) // <-- OK