Typescript Interfaces – Part 2 Nested Interfaces

 

If you are new to interfaces, go and checkout part 1 of series of articles on typescript interfaces.

In this part, you’ll learn how use interfaces in arrays and nested interfaces.

So lets take from the previous post, our iPerson interface. Now lets say we want to have an array of people. How would this look? Well, as each individual person should stay the same, we don’t need to change the interface, just how the variable is typed. There are two ways we can do this. One is called simple typing, and the other complex typing. Simple typing is where you have a predefined interface, and
it can used with ending the interface name with a pair of square brackets, like so.


declare interface iPerson {
    name: string;
    age?: number;
 }

let people: iPerson[] = [];
let john: iPerson = {
    name: 'John'
}
people.push(john);

So just to run over what we did. First we declared an interface, iPerson. Next we made a new variable and made it of type array of iPerson and assigned to it, a new instance of an array. You could also have used ‘= new Array()’ instead of ‘= []’. You should read {link here} explanation onto the differences. Now we have an array, we just create a new person object, and push it to the array. Now when ever you look at an element within that array, it will have the type iPerson.

You can use it as a complex type, and typescript doesn’t usually mind, however tslint does. A complex type is one where you don’t usual use an interface, such as


let people: Array<{name: string, age?: number}> = []; // no interface
let people: Array = []; // complex with interface
let people: iPerson[] = []; // simple with interface

let john: { name: string, age?: number} = {
    name: 'john'
}

Though there is nothing technically wrong with the above, it does make a rod for your own back, especially for larger projects. You end up copying and pasting
a lot to save you the time of writing an interface. But in reality, it doesn’t save much time at all.
It’s also worth noting, that it is possible to mix and match simple and complex styles, but what ever your style, just try to stick to one.

Now lets take a quick look at nesting interfaces. Lets assume you have a car, and in the car you can have multiple people. We should create an interface to describe the properties
of the car, and use the already defined iPerson array to describe each person in the car.


declare interface iCar {
    people: iPerson[];
    make: string;
    model: string;
    color?: number;
}

So lets go and make a new car object, and put some people into the car.


let porche: iCar = {
    people: [
        john
    ],
    make: 'Porche',
    model: 'GT',
    color: 'Black'
}

So we just made an object of type car, and gave it an array of people. Now when ever you access the car.people[x] element, they will have the
type of iPerson, just as above.

So that’s just about it for nested interfaces. You can continue to extending interfaces in the next article.