Spread types may only be created from object types in TypeScript – How to fix it?

Spread types may only be created from object types in TypeScript

Knowing how to fix the error “Spread types may only be created from object types” in TypeScript will be very helpful to you while you are working with Typescript

The reason for the error “Spread types may only be created from object types” in TypeScript

The error happens when we try to use the spread operator with not an object type value object.

type examDetail = {
    name: string,
    time: number,
    amount: number,
    level: number,
    form: string,
    pointBase: number
}
  
const saveExamDetail = (examDetail: examDetail| string) => {
  
    // Spread types may only be created from object types
    return {...examDetail}
  
}

Here the error happens because the set type for examDetail can both have an object type and string type, but the spread operator only allows for the object type, so I get the error.

I use the spread operator with some types that do not have an object type.

// Spread types may only be created from object types
console.log({...10})

const condition = false

// Spread types may only be created from object types
console.log({...condition? {} : 10})

Here I get an error because I am trying to use the spread operator with number type.

The solution for this error

The most obvious solution is to always make sure you use spread with object type only.

Use type assertion

The type assertion with as keyword can be very helpful to you set type for the variable. Like when the compiler cannot know what type will be passed in parameters, but if you know, you can set the type for it.

Example:

type examDetail = {
    nameSubject: string,
    amount: number,
    time: number,
    typeExam: string,
    formExam: string,
    level: string
};
  
const returnExam = (examDetail: examDetail | string) => {
    return { ...(examDetail as object) };
};
  
console.log(
    returnExam({
        nameSubject: "Math",
        amount: 100,
        time: 90,
        typeExam: "End Mid-Term",
        formExam: "Multiple choice exams",
        level: "hard",
    })
);

Output:

[LOG]: { "nameSubject": "Math",
"amount": 100, "time": 90, "typeExam": "End
Mid-Term", "formExam": "Multiple choice exams",
"level": "hard" }

Here I use type assertion to set type for examDetail to an object that can use the spread operator.

Use type guard

You can make a check logic to manipulate the parameter value as a type guard check if the value is valid, then use the spread operator.

Example:

type examDetail = {
    nameSubject: string;
    amount: number;
    time: number;
    typeExam: string;
    formExam: string;
    level: string;
};
  
const returnExam = (examDetail: examDetail | string) => {
    if (typeof examDetail === "object") {
        return { ...examDetail };
    } else {
        return "Invalid input";
    }
};
  
console.log(
    returnExam({
        nameSubject: "Math",
        amount: 100,
        time: 90,
        typeExam: "End Mid-Term",
        formExam: "Multiple choice exams",
        level: "hard",
    })
);
  
console.log(returnExam("9"));

Output:

[LOG]: { "nameSubject": "Math", "amount": 100, "time": 90, "typeExam": "End Mid-Term", "formExam": "Multiple choice exams", "level": "hard" } 
[LOG]: "Invalid input"

Summary

In this article, I showed you how to solve the error “spread types may only be created from object types” in Typescript. You can use type assertion to set your variable to an object if you can ensure it or make type guard always check the value before using the spread operator.

Maybe you are interested:

Leave a Reply

Your email address will not be published. Required fields are marked *