In this article, we are going learn about How you can use typescript in functions. And How to restrict the function to take different types of values than define parameters. It will be a basic introduction to functions as we go in-depth in this series you will learn so much more about functions such as How you can use Type Aliases or Interface to define custom types for Functions.
This is going to be a full series of typescript where you will learn from basic topics like string, boolean to more complex like Type Aliases, enums, Interface, generics, and etc.
Table of Contents
Functions
Writing function is a piece of cake when you know the JS but it gets a little bit complex in typescript. Don’t worry, we will take every aspect of that. We need to define the types of two things in function Parameters & Return Types.
Parameters
Function parameters are the names listed in the function's definition. I'll take an old example that I've mentioned before:
// This is a norma JS Function that take two number and returns the sum
// Problem is when you call the function you can pass any value
// It won't show error because the variable does not have any kind of type
function increaseScore(currentScore, increaseBy){
return currentScore + increaseBy;
}
// Now we define that both parameters have `number` type and it will only take the number
// otherwise it will throw an error
function increaseScore(currentScore: number, increaseBy: number) {
return currentScore + increaseBy;
}
Following is an example of the error it will show when you pass the wrong value to the function:
function increaseScore(currentScore:number, increaseBy:number){
console.log(currentScore + increaseBy);
}
increaseScore(10, 2) // ✅ Correct
increaseScore(10, "2"); // ❌ Error
increaseScore(10, [2,3,4]) // ❌ Error
Return Types
Return types matter. Because In typescript there are many return types. For example, you already know boolean
, number
and string
. But the question here is how we defined which type should return from the function. You can do that by the following syntax.
// Syntax
function funcName(para: paraType): returnType {
//........
}
// For Example:
function greetings(name: string): string {
return "hello" + name;
}
greetings("john"); // ✅
greetings(true); // ❌ ERROR: Expected String
// greet is 'string' type because greetings() return stirng type
let greet = greetings("Don");
greet = 2; // ❌ ERROR: because type is 'string'
Other Types
void
void
represents the return value of functions that don’t return a value. It’s the inferred type any time a function doesn’t have any return
statements or doesn’t return any explicit value from those return statements.
// This function doesn't return anything thus its return type is void
function sayHi(name: string): void {
console.log("Hi! " + name);
}
never
The never
type represents values that are never observed. In a return type, this means that the function throws an exception or terminates the execution of the program.
function handleError(errMsg: string): never {
throw new Error(errMsg);
}
There are a lot more other types you can take a look at the documentation for further use.
Optional Parameters
When you define parameters, sometimes you don't need to pass the parameters. So for that, you can add ?
next to the parameter as shown in the following code:
function doSomething(num?: number) {
// ...
}
doSomething(); // ✅ OK
doSomething(10); // ✅ OK
Note: If you are using
num
as an optional parameter, and if you don't pass it as an argument, then it would be undefined by default. So, you can detect that by simply checking(typeof num !== 'undefined')
.
Working with Object
In typescript working with objects could make you feel a little weird. Why? You will know why at the end of this section. There are many instances where you can use objects. Let's look at them one by one-
Passing Object as Parameter
Passing an object as a Parameter could be a little tricky. You need to define the types of each property you are passing as shown in the following code:
// Destructuring an Object
function signUp({email, password}: {email: string, password: string}): void{
console.log(email);
}
// You can also define the signUp function like the following
function signUp(user: {email: string, password: string}): void{
console.log(user.email);
}
signUp(); // ❌ ERROR: need to pass an object
signUp({}); // ❌ ERROR: to pass an object with email & password ,
signUp({email: "hello@gmail.com", password: "12345678"}); // ✅ Correct
Now, what if you want to pass an object with more than these two parameters:
function signUp(user: { email: string; password: string }): void {
console.log(user);
}
// Passing name in the signUp function
// ❌ ERROR: 'name' does not exist
signUp({ email: "hello@j471n.in", password: "12345678", name: "Johnny" });
// Creating a separate object and then passing it with the name
// ✅ Correct and No Error, But if you use 'name' in the signUp function then you'll get an error
let newUser = { email: "hello@j471n.in", password: "12345678", name: "Johnny" };
signUp(newUser);
Returning Object from Function
You can return an object through many ways from a function some of them are shown in the following code along with whether is it correct or not.
// ❌ ERROR: A function whose declared type is neither 'void' nor 'any' must return a value
// As function needs to return an object with name & age properties
function getInfo():{name: string, age: number}{}
// ❌ ERROR: Property 'age' is missing
// Function must have all the properties as specified (name, age)
// And It only returns the name that's why it throws an error
function getInfo():{name: string, age: number}{
return {name: "John"};
}
// ✅ CORRECT
// No Error Because all the things are correct
function getInfo():{name: string, age: number}{
return {name: "John", age: 29};
}
// ❌ ERROR: 'lastName' does not exist
// As function should return only 'name' and 'age'
// And it returns 'lastName' too
function getInfo():{name: string, age: number}{
return {name: "John", age: 29, lastName: "Doe"};
}
// ✅ CORRECT
// You can assign an object to some variable and then return it
// Even if it has more properties as described
function getInfo():{name: string, age: number}{
let user = {name: "John", age: 29, lastName: "Doe"}
return user;
}
// ❌ ERROR: A function whose declared type is neither 'void' nor 'any' must return a value
// As you can see it has two {}
// First {} shows that it should return an object
// Second {} is function definition
// It should return an object
function getInfo():{}{}
// ✅ CORRECT
// It returns and object that's why it works, It can have any properties because we haven't specified
function getInfo():{}{
return {name: "John"}
}
The above code example might be scary to look at but we can achieve these things with Type Aliases as well. We'll look at it in the next article.
Wrapping up
In this article, I explained How you can use typescript in functions. And How to restrict the function to take different types of values than define parameters. It will be a basic introduction to functions as we go in-depth in this series you will learn so much more about functions such as How you can use Type Aliases or Interface to define custom types for Functions.
This is a series of Typescript that will help you to learn Typescript from the scratch. If you enjoyed this article, then don't forget to give ❤️ and Bookmark 🏷️for later use and if you have any questions or feedback then don't hesitate to drop them in the comments below. I'll see in the next one.
Connect with me
Top comments (9)
Nice addition: Function types can be used standalone.
You can define a function type like this:
Then use it for multiple functions like this, and both the parameters and return type should be typed.
This is mostly useful when they are made available in open source packages, so you can include it and make sure your function is shaped like it is expected. It's also useful when you have multiple functions that behave the same, or if you have a function as a property of an interface.
Good luck on the series!
That's a nice addition. I was going to cover that later in this series. But that works too. Thanks mate.
Whoops! didn't mean to get ahead of you. Keep it up :D
Congratulations for your content! I just started using TypeScript in my projects and I'm really enjoying it. Controll the types of function parameters and returns make your code so much reliable and manutainable. Everyday I learn something new about TypeScript.
Thanks man.
This is so true. 😂
Nice article. On optional parms ... would be a good idea to show how you can identify if the parm was sent or not (typeof x !== 'undefined'). Just a thought
That's actually a correct thing. I have updated the content. Thanks.
keep it up :D Ur doing great work!!!
Thanks Hudson 😊