Skip to content

TS Interfaces

notes

  • interfaces does not exist in javascript.
  • interfaces are typescript only feature.
  • interfaces describe classes or objects.
  • interfaces can be used to type objects, and interfaces used as types in this case.
  • interfaces can extend other interfaces.
  • one interface can extend multiple interfaces.
  • interfaces does not get compiled to javascript output files.

type vs interface

  • they both describe objects or type them.
  • type is more flexible in typing.
  • in other languages, interfaces are used to be shape classes, where a class implements and interface.
  • interface is more clearer that it does type an object (since object is an instance of Object).
  • interfaces can be implemented by classes.
  • a class can implement multiple interfaces, and it can have more logic than the interface it implements.
  • both type and interface can use readonly modifiers.
  • both can be used to type functions.
  • both can have optional properties.
Type Interface
describe object describe class or object
more flexible in typing -
- describe classes, where classes can implement interfaces
- clearer in typing objects (object is an instance of Object or other class)
- can be used to share implementation between classes since a class can implement multiple interfaces
you can use readonly modifier you can use readonly modifier
- interfaces can extend other interfaces
used to type functions used to type functions
types can have optional properties interfaces can have optional properties
  • example, implement:
interface Greetable {
    name: string;
    greet(phrase: string): void;
}

class Person implements Greetable {
    name: string;
    constructor(name: string) {
        this.name = name;
    }
    greet(phrase: string) {
        console.log(`${phrase} ${this.name}`);
    }
}

const greet1: Greetable = {
    // Greetable is an interface, so we can type it as an object
    name: "Max",
    greet(phrase: string) {
        console.log(`${phrase} ${this.name}`);
    },
};

const greet2: Greetable = new Person("Max"); // Person implements Greetable
  • example, readonly modifier:
interface PersonI {
    readonly name: string;
}

type PersonT = {
    readonly name: string;
};

class Person implements PersonI {
    name: string; // Person implements PersonI, so name is readonly
    constructor(name: string) {
        this.name = name;
    }
}

const person1: PersonI = { name: "Max" };
const person2: PersonT = { name: "Max" };
const person3 = new Person("Max");

person1.name = "Anna"; // error, readonly, person1 implements PersonI, so it can not be reassigned
person2.name = "Anna"; // error, readonly, person2 implements PersonT, so it can not be reassigned
person3.name = "Anna"; // error, readonly, person3 is an instance of Person class that implements PersonI, so it can not be reassigned
  • example, extending interfaces:
interface Named {
    name: string;
}

interface Aged {
    age: number;
}

interface Greetable extends Named, Aged {
    // extends multiple interfaces
    // now Greetable can have name property and age property
    greet(phrase: string): void;
}
  • example typing a function:
interface DoubleValueFunc {
    // interface that describe function, syntax: function(arg: type): return type
    (number1: number, number2: number): number;
}

let myDoubleFunction: DoubleValueFunc;
myDoubleFunction = function (value1: number, value2: number) {
    return (value1 + value2) * 2;
};

type DoubleValueFuncType = (number1: number, number2: number) => number; // type of function
let myDoubleFunctionType: DoubleValueFuncType;
myDoubleFunctionType = function (value1: number, value2: number) {
    return (value1 + value2) * 2;
};
  • example, optional properties:
interface SquareConfig {
    color?: string;
    height: number;
}

type SquareConstructorParams = {
    color?: string;
    height: number;
};

class Square implements SquareConfig {
    color?: string; // making color optional
    height: number;
    constructor(config: SquareConstructorParams) {
        this.color = config.color;
        this.height = config.height;
    }
}

// or
class Square implements SquareConfig {
    color?: string; // making color optional
    height: number;
    constructor(height: number, color?: string) {
        // color is optional in the constructor function definition
        if (config) {
            this.color = config.color;
            this.height = config.height;
        }
    }
}