Trailer for the talk
Here's a sneak peek of the talk: Learn the benefits and fundamentals of TypeScript with Sylvana through this live coding session.
About the talk
When React developers first adopt TypeScript into their projects, it can feel more like a burden than a help. In this talk, we’ll break down the fundamentals of TypeScript and demonstrate how it can increase productivity, enforce self-documentation, encourage best practices, and help you refactor with confidence.
This talk will cover
- Basics like type inferences, type annotations, and interfaces
- How TypeScript catches bugs in your code and provides smart suggestions
- Live coding to demonstrate how to build out a React component using TypeScript
About the speaker
After working as a science teacher, Sylvana transitioned into web dev to provide quality education to all learners. After graduating from a coding bootcamp, she began an apprenticeship at Codecademy and is now a software engineer at the company.
Transcript
Darren: So as you can see our topic today is React with TypeScript - Build a React component together. Our speaker is Sylvana Santos, she started out as a science teacher. Now she's a software engineer at Codecademy, but her passion for teaching has not changed as what we see today. And that's why I really believe she's going to give a very helpful talk and demo for us. So. All right. So without further ado, Savannah, please take it away.
Sylvana: Hi everyone, thank you for that lovely introduction, Darren. Let me go ahead and share my screen and please yell at me if I'm not sharing it because I did have one experience where I wasn't sharing for like 10 minutes and no one told me. But I think I'm good right now. Okay, cool. So, thank you all for joining me here today. As Darren said, my name is Sylvana Santos and I will be talking to you all about React with TypeScript and it will include a demo portion where we code a React component together.
Sylvana: And I will spare you the introduction to myself since Darren already did that. But yeah, I have been at Codecademy for about a year and a half now. And so I've been able to build up some experience with React, Redux, Next.js, and of courseTypeScript. So I hope to share my knowledge with you all here today.
Sylvana: So a quick run-through of today's agenda. We'll start with an intro into what TypeScript is and the types of problems that it solves. Then we'll get into the fundamental concepts of TypeScript, and then we'll see how those concepts can be applied to React, to make building a React component a lot easier. And then we'll end with a quick recap of what we learned. And I'll also share some resources that you can use to continue your learning journey with TypeScript.
Sylvana: So let's get right into it. What is TypeScript and what problem does it solve? So, TypeScript is actually two things. It is a language and it is a set of tools. So the language is actually a superset of JavaScript, meaning that it builds on top of Javascript. And it allows you to add type definitions to your code. But TypeScript is also a set of tools. it surfaces errors in your code while you're developing. So it makes writing good code a lot easier. And we'll see that in action today.
Sylvana: So at this point you might be thinking, well, I'm already writing React applications with pure JavaScript and it's going just fine. So why do I need to go through the trouble of adding TypeScript to my progress? Well, let's take a look at a scenario that you might have run into. So let's say that we have this function called ‘welcome’, it doesn't take in any parameters and it just logs a greeting, which in this case is just ‘welcome’. And so then somewhere in our code, we call this function, we don't give it any parameters and all is good working as expected. But let's say further down the line, an engineer comes along and they refactor our welcome function. And so they add this new parameter called (hasAccess). And depending on whether (hasAccess) is true or false, we'll either log ‘welcome!’ or we'll log ‘go away!’ A very aggressive message.
Sylvana: So somewhere in our code, we have called ‘welcome’ and our engineer who refactored our function forgot to update that use case. And so they run the application. But they don't get any output. There's no crash on the app. There's no errors. So they assume that everything is fine. But I think we can all agree that this would result in some unintended behavior because we would always be logging ‘go away.’ We would never log ‘welcome’ because we're not giving it that parameter. So this isn't great. So if we just added TypeScript to our project and made this a TypeScript file, we would immediately, as we're coding, get some feedback. TypeScriptwould give us an error that says expected one argument, but got zero and argument for (hasAccess) was not provided.
Sylvana: So just with this simple scenario, you can immediately appreciate that TypeScript makes coding a lot faster. It catches bugs in your code and it allows you to refactor your code with a lot more confidence.
Sylvana: Cool. So at this point you might be thinking, well, I want to see it in action. How can I use TypeScript to see this error that you're talking about. So for that, we're actually going to take like a minute or so just to clone the repo that we'll be using later on. So that I can show you how we run TypeScript. So let me go ahead and drop the URL in the chat.
Sylvana: So if you go to that URL, you will see that there is a README with some setup instructions there. So we're just going to take a minute or so to set that up. They're pretty straightforward. You will need to have Git and node installed on your computer to run this, but basically all you're going to do is clone the repo somewhere on your computer. Then you'll go into the folder. You'll type npmi which just installs some node packages that we'll need for the application. And then you can open up the repo in whatever editor you would like. I will be using VS code, but whatever you prefer is just fine. So I'll give you like 30 seconds or so to set that up, I'll also say this is totally optional. I try to make it interactive, but if you would prefer to just listen, you can always explore the repo on your own after our session.
Sylvana: Cool. So let me just pause for like 15 seconds or so. if you want to take the moment to set that up, and as I said, the instructions are in the README. So if you've forgotten everything, I've said, all of the steps are there.
Sylvana: Cool. And I'm actually going to switch over, get rid of this. Let me just clear my terminal here. And I'm just going to give you a quick tour of this repo. So this was actually created using a command line tool called create React app, which is really useful. It automatically sets up a React application for you. And the way that I set it up, it also has TypeScript set up for us already as well. So the two folders that we will be focusing on today are the source folder and the utils folder. The source folder is where all of our React components live. So we'll look at that later on during the demo.
Sylvana: For now I want to focus in on this utils folder. If you open it up, you can see that it contains a bunch of different files and each of those files contains the examples that I'll be referencing throughout this presentation. So after the presentation, if you want to go back and look at the examples that I have on the slides there are here, you can interact with them and play around with them.
Sylvana: So as you can see, I already have over here on the right hand side. I have the welcome.ts file open. And that contains the function that I was just talking about this welcome function. So let's take a look at how we can run TypeScript on this file to get the error that I was talking about. So let me quickly jump back to the slides. So there are two options for running TypeScript on a file. The first is to use the command line. So if you want to use the command line, you'll have to install TypeScript. So I have the command here. You can put that in a terminal and it'll install TypeScript on your computer globally. Then once you've done that, it'll give you access to this command called TSC. And if you type that command followed by the path to your file, it's going to compile that file from TypeScript to JavaScript. And as it does that, it'll also output any errors that it finds.
Sylvana: So, let me just quickly jump back into my VS code to demonstrate that for you. So I can do, I just have this saved somewhere here, so I'm going to go up to it. So I have TSC and then followed by the path to this file, which in this case is utils, since that's the folder it's in and then welcome, which is the name of our file. So if I type that in or enter that.
Sylvana: You can see that I'm getting the error that we were talking about before. Brian, I see your chat there. Totally fine, if you're not fully set up. You'll have a chance to like play around with this on your own. and I can also, like, if you're running into any questions in the Q & A session, I can help you out as well.
Sylvana: But cool. Yeah. I just want to show you right now. So this command followed by the path will output the air that I was talking about before. And I just want to point out that there is also another way that we can run this, which is also in the slides here. You can see that this one is very similar, but it also has the w flag. And so all that does is it runs the same thing, but in watch mode. So let me demonstrate that for you as well. Okay. So if we run it with the w flag here, I hit enter. Might take a second or two.
Sylvana: You can see that it still outputs the same file. So it looks exactly the same. It's telling us that welcome should be having one argument, but we're not providing it with any. But you can see down here that it says watching for file changes. So what it's happening is it's compiling, but if we were to change our file, it would update the output, the errors. So you can see that if I just went back to my file. I got rid of hasAccess. In the inputs, I click save. You can see that it reloaded and now I'm getting a completely different error. So this is really nice. You don't have to keep typing it in every time you change your file, it's just automatically waiting for changes.
Sylvana: So let me go ahead and clear my console. Get rid of that. Cool. So this is one way that you can run TypeScript on a file. But it is a little annoying. Right? so another option is to use the built-in intellisense for your editor. So an editor like VS code will run a TypeScript language service in the background, and that service will analyze your code and give you some cool features like code completion or quick info. So let me show you what that looks like.
Sylvana: And you might've actually already noticed it. So let me go ahead and close my terminal here. and let me revert these changes. So if I go back here, you can see that I'm getting these squiggly lines down here, these red squiggly lines. And if I hover over it, I'm getting the same error as before, right? It's telling me I'm expecting an argument and argument for hasAccess was not provided, right? So this is a lot faster. It's very convenient. You didn't have to write any commands in the terminal. It just automatically gave you feedback.
Sylvana: So this is what I will be using moving forward in the presentation. And if your editor has something like this, I highly encourage you to use this, it’s very useful. Cool. So let's keep on moving.
Sylvana: Onto the basics of TypeScript. So we're going to get into the fundamentals, concepts of TypeScript. So TypeScript is really smart. It can use the initial values of your variables to infer the types for that variable. And then it uses that knowledge to determine whether or not you're using your variable properly. So let's look at this example. So I've set up this constant called myBoolean and its value in this case is false, right? Because two is not greater three.
Sylvana: So now based on this initial value, TypeScript knows that myBoolean has a type boolean. So now if I tried to do something like call to uppercase on myBoolean TypeScript is going to yell at me. Right. It's going to tell me the type boolean doesn't have a two uppercase method on it. Right. So you would get immediate feedback that you're doing something wonky here. Similarly, if you try to add 10 to myBoolean, TypeScript would tell you, I can't add a boolean and a number. So you would get immediate feedback there as well.
Sylvana: Cool. But sometimes TypeScript does not have enough knowledge to accurately infer the type of our variable. So we have to help TypeScript out by providing it with type annotations. So let's see what that looks like.
Sylvana: So one case where you might have to add a type annotation is if you're using let and you're not giving it an initial value. Right? So for example here, I created this variable called myAnnotatedBoolean and I'm not giving it an initial value. But what I am doing is I'm using this colon to tell TypeScript myAnnotatedBoolean has a type boolean, right? So now if I were to go and try to set myAnnotatedBoolean to a string, it's going to yell at me. TypeScript is going to say, string is not the same as a boolean. You told me this was a boolean, and now you're trying to set it to a string. Cool.
Sylvana: And another case where you might have to use a type annotation is for function parameters. So sometimes TypeScript can't infer that hasAccess is a boolean. So again, we can use that same syntax to tell TypeScript that the hasAccess parameter has a type boolean.
And so then if we were to call this function and try to give it something like a number, TypeScript again, would yell at us and tell us, gey, hasAccess to supposed to be a boolean. You're giving me a number here. Awesome.
Sylvana: So, so far we've seen examples of some simple types, right? We've seen boolean, we've seen string, we've seen number, but we can create some more complex types using TypeScript. So one example is tight unions. So this is used to tell TypeScript that a variable can be one thing or another. So for example, let's say I have a function called my union function. And it takes in an error and the error can either be a string or it can be undefined, right? So then inside of the function, if I try to call something like toUpperCase on error, TypeScript is going to yell at me. Cause it's going to say, error can sometimes be undefined, so I may not be able to call toUpperCase on it. So in that case, I need to add an if statement to make sure that whenever I'm calling toUpperCase, error is not undefined. Cool.
Sylvana: So as you would expect, if I now try to call my union function with no problem. TypeScript is going to yell at me. if I call it with a string TypeScript’s all good. If I try to call it, call it with an undefined parameter. TypeScript is still okay with that.
Sylvana: And another way that we can specify a type is using literal types. So you might use this when you want to tell TypeScript that a variable has to have an exact value. So it has a string has to have an exact string value or a number has to have an exact number value. So for example, if I have a variable called my favorite number, maybe I want its value to only either be 10, 14, or 19. So I can use this syntax here. So this sort of combines a literal type and a union type, right? I'm saying my favorite number can only have a value of 10 or 14 or 19. So then if I try to set my favorite number to something like to 2, TypeScript will yell at me. And then you can see here. If I try to set it to 14, perfectly fine.
Sylvana: Similarly, I can do this with strings. So if I have a variable called my suit, I can say that it's value can only be clubs, diamonds, hearts, and spades. So then if I try to set my suit to something like koalas, TypeScript is going to be very confused and yell at us again, but if I try to set it to spades, it's okay.
Sylvana: Great. So another type that you can use in your type annotations is called function types. And as the name implies, this is the type that you would want to use for a function variable. So for example, if we revisit the example from before our welcome function, We can give it a function type using this syntax. So this is saying I have a variable it's called annotatedWelcome, and it's type is a function and that function takes in a boolean and then returns void. So now if I go and try to give annotatedWelcome a value, I don't have to specify that hasAccess is a boolean because it already knows that from the function types that I gave it.
Sylvana: Another example here, let's say I have a variable called lengthCalculator, and I tell TypeScript lengthCalculator has a type function. And that function should take in a string and output a number. So a okay value for lengthCalculator would be something like this. I take in a word and then I output the length. Length gives us a number, so it's returning a number.
Sylvana: Another example is error logger here. So I'm telling TypeScript, error logger is a function. It doesn't take anything in and it returns void. So that's also important. You can also say that your function doesn't take in any parameters. And so an example value for this would be just a function that logs, whoops for us.
Sylvana: Great. And the last tool that I'll talk about today is called interfaces. So interfaces allow us to describe the shape of an object. So for example here, I've created an interface called Hero. And all this is saying is Hero is an object that has a property name and a property superpower. The name property should have a value that is a string and the superpower property should have a value that is a function and that function doesn't take anything in and returns void.
Sylvana: Cool. So we're just describing the shape of an object using this Hero interface. So then I could create a variable named ironMan. And I could say the type for IronMan is Hero. So if I try to set Ironman to an object, whose name is 17 TypeScript is going to yell at me. It's going to say, you told me that Hero has a property named name and that value should be a string, but you're trying to set it to number. Similarly, if we try to set superpower to false, TypeScript is going to say a boolean is not a function. This is not correct.
Sylvana: So an okay value for Ironman would look something like this. I have an object. The name is Tony Stark, which is a string. So that's okay. And then superpower is just a function that logs, I am Ironman. So that's okay. According to our interface up here.
Sylvana: So before I move on to the React demo, I know I just like threw a bunch of different things at you and it's totally okay if you're still digesting things. I hope that the demo will help some of these things stick also it's hard to like take in a whole bunch of information and have it stick just in general. But I want to take a moment to pause and see if anyone has any clarifying questions I can go back to any of these examples. Any questions so far? I'll take like 30 seconds to let you drop it in the chat.
Sylvana: Also, if you have a really long question and maybe don't feel like typing it out, I'm totally fine if you want to unmute and just yell at me.
Darren: If somebody wants to speak it out loud, just raise their hand and we can, we can unmute you so.
Darren: Okay. So, yeah, I think here's a question, Sylvana do you see it?
Sylvana: So someone asks, so if we don't use TypeScript, we won't see the errors. Yeah, exactly. So, like the example that I had earlier, right. If you to like, have a function where you, as a developer are expecting an input, you won't get an error, unless you try to do something weird with it and like cause an error, like let's say, you tried to call two uppercace on the input, right?
Then you might get an error, but for the most part, if something is silently erroring out, you won't get any output.
Sylvana: Any other questions?
Sylvana: That is true. You can add unit tests to sort of make sure that your functions are behaving the way you want to. This is very true. I think someone wants to unmute themselves. Is that okay, Darren?
Darren: Yeah, of course. Just give me a second.
Attendee: So quick question about the interface. You mentioned that, interfaces like an object. I would like to clarify what's the difference between an interface and like an object? And also is this similar to a class and when, in what kind of situation will you prefer to use an interface?
Sylvana: Yeah. So an interface is sort of like a type that you would want to use for an object, right? Like let's say, and hopefully during the React demo, you'll see exactly why this is really useful because we're going to use this for our React component. But let's say that you want to set, you know, you have a variable, right? And the value for that variable is just an object that has a property name, text on it. So if you want to add an annotation to that variable, you can create an interface to tell TypeScript what the shape of that variable should look like.
Sylvana: So if I go back to, let me go back to my, this example here. So. If you, if we didn't define an interface here, if we didn't define the Hero interface here, how would we tell TypeScript the type for ironMan, right? The way we do that is with an interface. Does that make sense? It might also get a little bit clearer when we do the React demo, but you can unmute yourself and let me know if that doesn't make sense.
Sylvana: Do we have any other questions in the chat?
Darren: And yeah, we have a few more, would you want to keep answering? Maybe it will be clear as we move on to the demo.
Sylvana: I can do one more and then we can move on to the demo.
Darren: Okay. This person is Tejas, sorry if I pronounced it wrong, he or she is asking any other tools apart from TSC and language services that are out there.
Sylvana: I'm going to assume that this person means like, does TypeScript provide any other tools? The tools that are provided, at least that I know of, it's very possible that there are other things out there that I'm unaware of. But when I'm referring to the tools provided by TypeScript, one is the command and then the language service that sort of provides us with things like this, right? Like the welcome or the error message here. So those are the main things. You can sort of build upon this. So if you have TypeScript running on your CI/CD checks, like let's say you run TypeScript on all of your repo before someone is allowed to deploy, that's really useful because if you have TypeScript errors, you can prevent people from deploying their code. So you can sort of build up on these to make sure that your team isn't shipping out any bugs that might be caught by TypeScript.
Darren: Okay. Cool. Awesome. Yeah, there's a few more, but I think, yeah, maybe we can move on to this demo and save those for later.
Sylvana: Hopefully I clear up some of these along the way but I also just want to plus one, I don't know who put in the chat. Be patient with yourself. TypeScript is really hard to wrap your head around, especially all in one go. So if you can just get a few nuggets here and there, I think you can call this a successful one and you can always revisit the concepts here and they'll stick with you the more and more you chip away at it. Okay, cool.
Sylvana: So let's get back into the presentation. So now we're going to take a look at how we can use these concepts in our React applications and use them to build our React components. So this might help you understand why TypeScript is so useful, especially if you've already been building React applications. So let's refresh our memory with what React looks like with pure javascript. So let's say I have this component named syllabus header, right? It's a functional component. It takes in a props object. And then here, all we're doing is we're getting a bunch of properties off of the props object, right? So we're getting this isPro, courseType, courseName, onClick, and projects. These are all properties on our props object that we expect to get from the parent component.
Sylvana: And then we use these to render some components. So for example, isPro seems like it is a boolean. If it's true, then we render this span here and then we're just rendering the courseType in a
tag and then courseName we're rendering that in a header. Then we're also taking this projects field and if it returns something, then we render it in a header, followed by the word projects. And then we also have a button and we give it whatever onClick we get from the parent component here. Right. So this is what React looks like in pure JavaScript.
Sylvana: And if we wanted to render this component, we would do something like this. So let's say we have this app component and this app component is just going to render our syllabus header component. So we would want to give them. isPro right? Since our syllabus header is expecting to get isPro in the props and we would give it a value of true. We would give it a courseType and a courseName, which are both strings. We would give it an onClick because the syllabus header is expecting an onClick for the button. And then we're also going to give it a projects prop, which is just a number. And so if we gave it all these props, our component would render something that looks like this. Right? So everything is working as we would expect.
Sylvana: But you can run into a lot of problems here, so we could. Maybe instead of giving isPro a boolean, we could just give it a string that says yep, we're pro. You could also, for courseType, you might give it something that just doesn't make sense in your application.
Sylvana: Right. Of courseType is something like a skill path or a career path. Right. In our case at Codecademy is not a courseType that we support. Right. So this is technically not a wrong type, but it just doesn't really make sense with our context. Per title, we could give it, or we could try to give it a proper name title, but if I go back two slides, our syllabus header component isn't expecting a prop name, title. So that's a problem. And then maybe I accidentally mistype onClick and I forget to capitalize the C here. Right. So all of these would results in errors or unintended behavior, right? So from this example, you can see that with pure JavaScript, it's pretty easy to, you know, send down a prop that the child doesn't expect or forget to send down a prop that it expects.
Sylvana: You can also send down values that just don't make sense for our context. You can miss type the name of little prop, or send the wrong type for a problem. So there's a lot of different things that can go wrong. And to be fair for a lot of these, you would actually get error messages, right? Once you build up the application, you run it, you would probably get an error message in your browser. Right. But with TypeScript, we can catch these before we even run the application. We can catch them as we are typing our code.
Sylvana: So that's exactly what we're going to do. We are going to add TypeScript to this example. So at this point we can switch over to the repo. This is where we'll be doing the demo. So I'll make sure to give extra time to set this up since this will be more of a code along. So if you go over to the repo, let me open up the file system. I'm going to go ahead and close the utils folder. And then I’ll opened up the source folder where all of our React components are. And I'm also going to open up my terminal. Cool. So if we can go ahead, let's open the app .psx file, which I have open on the left-hand side here. And then we're also going to go into this components folder and open up the syllabus header, which I have open here. And let me just go ahead and close this. Cool. So at this point you should have the Rebo open. You'll have the app .psx file open on one side, and then the syllabus header opened on the other side.
Sylvana: Cool. So we'll go ahead and take a look at the code in a second, but, if you have the repo, the first thing that you'll want to do so that we can run our React application is do npmi or npm install. Those were in the setup instructions, but in case anyone didn't have time to do that, you can run that. And again, that is just going to add all of the dependencies that we need for our application.
Sylvana: So I've already done that. So I don't, I'm going to skip that step, but if you haven't done it, go ahead and do that now. And then that might take a little bit, once that's all been installed, you should just be able to do yarn start to start up the application. So I'm going to go ahead and do that. You can see that it's running.
Sylvana: And that'll automatically run our application at localhost 3000. And the way that the code is right now, you should be getting an error here, which is expected. Don't fret if that is the case, we are going to fix it. You can also use npm start. Yeah. So anytime I have a command that's like yarn start or yarn build or anything like that, you can replace it with a npm. Yeah. That's totally fine. Thank you for pointing that out.
Sylvana: Cool. Going to give it like 30 seconds, just to make sure that everyone is good to go. If you're having any trouble, please drop it in the chat and I'll try to debug. Hopefully.
Sylvana: All right, I'm going to go ahead and move on. Alright, so let's add TypeScript. So the first thing that we're going to do, we're going to go to the repo and I'm actually just going to get rid of this code. We're going to start from scratch and do this together. So, let me go ahead and if you're following along, you can just comment out what I have here. And I'm also just going to get rid of the terminal here so that it's not in our way and maybe zoom in one more time. That's a bit too much. Cool.
Sylvana: So we're going to go ahead and get rid of that component here and then a pause on the app .psx, I know there's an error there right now, but all I'm going to do is I'm just going to export font, syllabus, header, basically gonna rewrite this, but it's just going to be an empty component right now. That's just going to return, let's say a
tag and I'm just going to make it say hello. Cool. So just take a moment there to create a very simple functional component. It doesn't take in any parameters and it just returns a
tag that has hello in it.
Sylvana: Cool. And because we did that. Because now our component is not taking in any props. I'm going to go ahead and just comment out our props over here and act up .psx. So let's go ahead and save that. All right. And let's go here. Cool. We have a very impressive app that just says hello on it, but hopefully we're all on the same page.
Sylvana: All right, I'm just gonna pause here for a quick second.
Sylvana: Cool. So we have a very simple component. And now what we're going to try to do is we're going to try to get back to this component that we have here, but we're going to build it using TypeScript. So the first thing that we'll want to do is that we're going to want to specify a type for syllabus header. Right? So you and I know that the type four syllabus header is a functional component. So a function that may or may not take in some props and then return a React node. Right. So you and I can verbalize that, but how do we explain that to TypeScript? How do we tell TypeScript? Well, for that, we are going to use, a Type called React.FC, which is actually provided by React.
Sylvana: So using this syntax, we can tell TypeScript that text in this case, that's the name of the component that I have here. We're telling TypeScript that text is a functional React component, right? So I won't go too into detail about React.FC, but all you need to know is that it tells TypeScript that this variable is a React functional component.
Sylvana: So all we're doing is adding that type annotation. So let's go ahead and go back to the code and add that annotation here. So syllabus header is a React functional component. Let's go ahead and save that. Let's just verify that it didn't break anything. Cool. Everything's looking good. All right.
Sylvana: So now we have to start adding some props. We have to start telling this con we have to start bringing in props into this component so that we can properly render the component. Right. So let's go ahead and take a look at how we can do that. So I don't remember who asked this earlier, but someone asked, like, why would we ever want to use interfaces can you explain to me a use case? React props is why you would want to use interfaces. So we know that for our text component, let's say that our, we want our text component to take in a prop called text. Right. So props is just an object. And we're going to say that for this component, the props object needs to have a text property on it. Right. So we're going to define an interface called text props. And we're going to say text props needs to be an object that has a property called text on it, and text needs to have a value that is a string. Cool. So we've defined our interface, text props. So then. We can use this React.FC type to say, we want the functional component to take in a type text props.
Sylvana: Right? So this is saying text is a React functional component and it takes in a props object that has this shape here. Right?
Sylvana: Oh, can't see the changes. Can someone else drop in the chat if you're not seeing the changes. If you did miss it. The only thing that I did, oh, okay. You're not seeing my IDE that's a, that's an issue. Let's see. Let me stop sharing for a second and make sure that sharing all my screens. Can you see it now? Can someone drop in the chat if you're seeing it now? Awesome. Cool. Thank you for calling that out. Zoom can be very confusing. I think I might've clicked on the wrong window. Cool. Thank you.
Sylvana: So let me go ahead and recap that. So all I did is that I commented out the syllabus header component. That's there by default and I replaced it with just a simple syllabus header component. I use this type annotation React.FC to tell TypeScript that syllabus header is a React functional component and that's just a function that returns a
tag. So I basically just got rid of whatever was there for the syllabus header and just created like a simple functional component that just returns one
tag. And then because I made that change, I went over into the app .psx file, and got rid of all of the props that we were passing into it since now our component isn't expecting any props. So hopefully that gives you a recap of where you're, where I am. I'm sorry that I wasn't sharing my ID.
Sylvana: Cool. so hopefully we can all get on the same page there. And now what we're exploring is how do we tell TypeScript that syllabus header needs to take in some props, it needs to take it in a props object. So for that, we were looking at the slides, which I assume that you can see, And so, we can use an interface to tell TypeScript what the shape of the props object should look like. And we use this syntax here. So I'm going to go ahead and switch over to my VS code. And I'm going to use that syntax here.
Sylvana: So let's go ahead and create an interface. So I'm going to type interface. I'm going to call it SyllabusHeaderProps. And because it's an object I'm going to use the curly bracelets, hit enter. For now I'm just going to say, I'm going to have, add one prop to it. So let's say isPro we're going to add that for now. So our SyllabusHeaderProps needs to have an isPro property on it. And the type for isPro is boolean. Great.
Sylvana: So now I've defined my interface up here. So now we need to tell TypeScript that syllabus header is going to take in a props object that follows this shape here. So in order to do that, I'm going to add a greater than, and less than sign, to the React.FC. That's a bit of an advanced concept in TypeScript, so I won't get into it, but it just says that this function is going to take in this type. So I'm going to put in SyllabusHeaderProps here. Another thing that is really useful about adding TypeScript as you can see here, I was typing in syllabus header, and it recommended to me what I might want to add. So I didn't have to finish adding that in, it just auto completes it for me. So that's also like a nice feature of TypeScript.
Sylvana: So now I have added the props type to our React components. And now if I go over to the app .psx file, you can see that it's telling me I'm missing an isPro prop. So if I go ahead and uncomment isPro I got rid of the error there. Right? Can we add it as a type annotation instead? I'm going to wait for that question afterwards. Cool.
Sylvana: But right now I'm not doing anything with isPro, so let's go ahead and get rid of this. I'm going to add a curly brace so that I can add my return statement here and actually start returning our component. So I'm going to copy and paste this from up here or from down here, add this into my return statement. This might get a little messy here and get rid of these. Okay. Cool. And I don't want, I'm not taking in courseType yet, so I don't need to add that just yet. And above my return statement, I need to grab isPro off of the props object. So I'm going to do, const {isPro} grab that off of our props subject. Oh, I need to add props here. Cool.
Sylvana: So this is starting to look a lot more of a lot more like our previous component, our original component. Right. So let's go ahead and move over to our browser and you can see that now I am rendering our pro label. Cool.
Sylvana: So we can continue with this by adding all of our different types to our SyllabusHeaderProps interface. So we know that we want to have a courseType and the type for that is a string. We also know we want to have a courseName, which is also a string. And we want to have an onClick, capitol C, which is going to be a function that doesn't take anything in and returns void.
Sylvana: Great. Now I'm actually just going to cut out projects right now, just for the sake of time. Cool. So now we've defined all of the different properties on our props object, and we've given a type for each of them. So I'm going to go ahead and save that, and I'm going to go ahead and move all of our HTML over here. So I hate that, let's see. Apologies. I'm just gonna copy paste here.
Sylvana: Return this just, I guess, an easier way to do this was just to uncomment everything on the bottom rather than copy and paste. But, you know, we learn as we go.
Sylvana: All right. Almost there, click save on that. And then of course I'm getting all of these squiggly lines because I haven't grabbed that off of my props objects. So let me go ahead and do that. I'm going to grab courseName courseType and not projects because we're taking that out. And then onClick. Cool.
Sylvana: So now I should be grabbing everything from my props object and rendering things as they should. But if I go over to my app .psx file, I'm getting yelled at that I am missing properties courseType, courseName, and onClick in this component. So let me go ahead and uncomment those, got rid of the error. Now let's go over to our browser. It looks like I'm missing some CSS, but things are rendering as expected. The props are being rendered. Cool. So I know that was a quick blast through the coding. But let's go ahead and go back and recap what we learned.
Sylvana: Cool. So we started off by talking about what TypeScript is. TypeScript is a language and a tool as we saw, you can run it through the command line, or if your editor allows it, you can also use the IntelliSense feature that is built into your editor. TypeScript can infer the types for your variables when given an initial value or given enough context.
Sylvana: If TypeScript cannot figure out what the type for your variable is, you'll need to add annotations to help TypeScript out. And when writing annotations, there are a lot of different tools that we can use to write our annotations such as union types or literal types or interfaces. And we can use all of those things in our React components. In particular, we can use interfaces to define the shape of the props object.
Sylvana: Cool. So those are the basics of TypeScript. I know that there's a lot and little by little, the more that you use it, the more comfortable you'll get with it. and it'll become a lot easier to even just look at TypeScript. I know at first looking at TypeScript code can feel really overwhelming, but the more and more you practice it, the easier it becomes.
Sylvana: So I've left some resources here for you to continue exploring TypeScript and learn more about it. Sort of reiterate some of the stuff that I went over today. So there are two courses that I recommend if you are interested in learning more about it. One of course is a Codecademy course. It's written by a really great engineer at the company, or it was built in partnership with a really great engineer at Codecademy named Josh Goldberg. And he actually helps build out TypeScript. So it's a really great resource. There's also, if you're more of a visual learner, there’s a really great YouTube crash course. In addition to that, there's also a playground where you can play around with TypeScript. So you don't need to set up like a whole repo. You can just use an online editor. And I also linked some documents and articles that will help you get started and revisit the concepts that we talked about here today.
Sylvana: But yes, thank you all for bearing with me today. I hope that you learned at least just a little bit and at least got a taste for what TypeScript is and maybe got excited to use it more, it is a really useful tool. But it can have a steep learning curve. So be patient with yourself. it'll start clicking eventually. So without further ado. Thank you again for joining me here today. If you have any questions, please drop them in the chat. I know I have like a cue from throughout the presentation, but if you want to connect or ask further questions, please email me @silvanaatcodeacademy.com or reach out to me on LinkedIn. I'm happy to help out and clear up any questions that you may have from this presentation.
Sylvana: Thank you.
Darren: Awesome. yeah. Thank you so much, Savannah, for sharing with us and giving us a demo. I think it's really helpful to hear introduction first and then actually see how we get to do that. So for people who are asking, yes, like we will share the video, the recording to this, and also the slides. So, so don't worry. I know there's a lot of content. I myself, I'm going, going to go back through the recording and try to do it again.
Darren: So now we have a little bit of Q & A time. People already asking the questions, feel free to keep typing them in the chat. Our team will help collect them. Okay, so I'm seeing a hand up, sorry for keeping you waiting. I'm going to ask you to unmute. Okay. Yeah. Please ask the question.
Attendee: All right. You already answered my question, but I want us to know if there's a recorded version of the video, but you already said that too. I'll look it up. I joined it very late.
Sylvana: I also would like to add real quick. I know some people in the chat, asked about slides. I think they're in, and the team will share out slides. We'll after the presentation ends, post the solution on a different branch, it'll be a solution branch, on the repo. So if you get stuck somewhere, you can reference the solution branch, to get yourself unstuck.
Darren: Awesome. So yeah, we have a few questions just in the queue. So I think, I believe it was K who asked, the value that those syntax, the angle brackets, why the text props inside angle brackets, but not as props colon my interface. Does that make sense? Or I can try to copy and paste it. Yeah.
Darren: Let me copy and paste for your question. I should test it. Okay.
Darren: Yeah, it should be in the chat now.
Sylvana: Oh, okay. Gotcha. Okay. cool. Yeah, let me go, let me jump over to the editor. So let me just make sure I understand like where the confusion is coming from, but not as props my interface. Okay. Gotcha. So hopefully this helps clear things up. if we got rid of this, I guess if this was like a regular component, like if we didn't have React.FC. One thing that we could do is we could do this. We could do SyllabusHeaderProps, right? So this would be perfectly fine. Right? You could do this. And this is just saying syllabus header is a function. it's going to return some HTML. It's going to return a React node and the props have this shape. Right. So I think that's what you're asking, right? Like, why can't we do this? This is totally fine. But TypeScript has to figure out what the return type is here. It doesn't really know, it can look at this and say like, oh, okay, I'm getting some HTML. Maybe this is a React node, but TypeScript isn't smart enough to know that a React functional component should always return a Reaction node.
Sylvana: So technically I could like return to and it wouldn't yell at me because they can't figure out what the return type is. So the React.FC is a useful type that is provided to us by React so that we can ensure that our React components are always returning a Reaction node. I know that this syntax of like the less than, and greater than sign is really confusing. But types can also, this is basically, sorry, I don't want to get into like the nitty-gritty of it, but this is just saying that the function, that this is a functional component that takes in a SyllabusHeaderProps. So this React.FC can take something in and then it'll tell TypeScript that the parameters for the functional component is this.
Sylvana: So it's just a bit of an, a more advanced type that they've built out for us. But in a nutshell, it just ensures that your functional component is always returning a React node, but like you said, you could also use the colon here and syllabus header here that could also work. There's just not as much type safety there.
Darren: And, we just have one more question from the Rene, is interface like prototypes and why would we particularly want to use TypeScript instead of JSX?
Sylvana: Yeah. yeah, you're totally right up prop types, and sort of using TypeScript interfaces to define our prop shape is very similar as they sort of get at the same thing, right? But with TypeScript, there's more safety with it. And also all of the added bonuses of the tools that you get, like the auto-completion and like the errors, things like that. But you're right. They are very, very similar tools. I think there's just a little extra fanciness that comes with TypeScript, that's really useful.
Darren: Alright. Awesome. so because of time, I'm going to officially wrap up this event. Sylvana, thank you so much again for taking the time to share with us today. Do you have any final thoughts you'd like to add or share before we wrap up?
Sylvana: No. Thank you all so much for being patient. And like I said, if there is anything I can clear up for you, please feel free to reach out to me. I try to do a good job of responding to everyone very quickly.
Darren: Yeah. Awesome. yeah. Thank you everyone again for joining our event today, and I hope you really enjoy this talk. And, so yeah, if you, if you had more questions, thoughts, like, like Sylvana said earlier, you could feel free to connect with her through LinkedIn or post on the discussion section of event page. The link will be in the chat. Yeah. I think I can see it right now. Right. And this is actually the last event of 2021. And there'll be more events in 2022, but for now I want to share something quite exciting. It's already on the screen right now. In case you haven't seen it, which just launched our new Codementor events platform, on this website, or, on this, on this page that is showing right now, you'll be able to see upcoming events, sign up for the newsletter to be in the loop for future events. And I think perhaps the coolest feature, if I can say so myself, is you can create and host your own virtual events. So I'm really, really looking forward to see, the event ideas that you'll have. So take a look at this when you can, the QR code is up there and the link is also in the chat. Okay. So, yeah, so that's officially the end of this event.
Darren: And thank you so much Sylvana for taking the time to share with us, that's all. So thanks again. And we’ll see you all soon.
Highlights of the talk
What is TypeScript? What problem does it solve?
TypeScript is both a language and a set of tools. The language is a superset of JavaScript, which means it’s built on top of JavaScript and it allows you to add type definitions to your code. TypeScript is also a set of tools. It surfaces errors in your code while you’re developing so it makes writing good code easier.
Let’s say you’re writing in JavaScript, and this is the welcome message you have crafted:
const welcome = () => {
const greeting = ‘welcome!’;
console.log(greeting);
};
If someone were to come in and refactor the code to become:
const welcome = (hasAccess) => {
const greeting = hasAccess ? ‘welcome’ : ‘go away!’;
console.log(greeting);
};
you won’t be able to see any errors while it would cause unintended behavior, which displays go away!
as the greetings every time.
If you were to add TypeScript to your project, and made this a TypeScript file, you would immediately get feedback as you code. TypeScript would show the following error message:
// Error: Expected 1 arguments, but got 0.
// An argument for ‘hasAccess’ was not provided.
Just with this simple scenario, you can appreciate that TypeScript makes coding a lot faster, it catches bugs in your code, and it allows you to refactor your code with a lot more confidence.
What are the fundamental concepts of TypeScript?
Type Inferences:
Typescript uses initial values to infer the type of a variable. It then uses that knowledge to check whether the variable is being used properly.
Type annotations:
When TypeScript cannot properly infer the type, you can use type annotations to explicitly set the type.
Here’s an example:
let myAnnotatedBoolean: boolean;
// Error: type ‘string’ is not assignable to type ‘boolean’
myAnnotatedBoolean = “true”;
Another case you might have to use a type annotation is for function parameters. Sometimes TypeScript can’t infer that hasAccess
is a boolean. So you can use the same syntax to tell TyepScript that the hasAccess
parameter has a type, boolean. If you tried to call this function and tried to give it a number, TypeScript would show an error:
const welcome = (hasAccess: boolean) => {
…
};
// Error: Argument of type ‘number’ is not assignable to parameter type ‘boolean’
welcome(1);
Type Unions:
Used to tell TypeScript that a variable can be one thing or another.
For example:
const myUnionFunction = {
error: strong | undefined
) => {
// Error: object is possibly ‘undefined’
console.log(error.toUpperCase());
// Ok!
If (error) console.log(error.toUpperCase());
};
Literal types:
Used to specify an exact value that a string, number, or boolean must have.
For example, this combines a literal type and a union type:
let myFavoriteNumber: 10 | 14 | 19;
//Error: type ‘2’ is not assignable to type ‘10 | 14 | 19’
myFavoriteNumber = 2;
// Ok!
myFavoriteNumber = 14;
Similarly, this can be used for strings as well:
let mySuit: “Clubs” | “Diamonds” | “Hearts” | “Spades”;
// Error: type ‘Koalas’ is not assignable to type ‘“Clubs” | “Diamonds” | “Hearts” | “Spades”’
mySuit = “Koalas”;
//Ok!
mySuit = “Spades”;
Function types:
Used to annotate the type of a function.
Here’s an example of annotating the type of a function in TypeScript:
let annotatedWelcome: (hasAccess: boolean) => void;
// parameter types can be inferred when a function type is provided
// in this case, TypeScript knows that hasAccess has type ‘boolean’
(parameter) hasAccess: boolean
annotatedWelcome = (hasAccess) => {
const greeting = hasAccess ? “welcome!” : “go away!”;
console.log(greeting);
};
Here’s another example:
let lengthCalculator: (word: string) => number;
lengthCalculator = (word) => word.length;
let errorLogger: () => void;
errorLogger = () => console.log(“whoops”);
Interfaces:
Used to describe the shape of an object in TypeScript.
For example:
Interface Hero {
name: string
superPower: () => void;
}
let ironMan: Hero = {
// Error: type ‘number’ is not assignable to type ‘strong’
name: 17,
// Eroor: type ‘boolean’ is not assignable to type ‘() => void’
superPower: false,
};
An ok value for Iron Man would look something like this:
interface Hero {
name: string;
superPower: () => void;
}
// Ok
let ironMan: Hero = {
name: “Tony Stark”,
superPower: () => console.log(“I am Iron Man”),
};
What is the difference between an interface, object, and class? In what circumstances would you use an interface?
An interface is a type you’d want to use for an object. Let’s say you have a variable, and the value for that value is just an object that has a property name ‘text’ on it. If you want to add an annotation to that variable, you can create an interface to tell TypeScript what the shape of that variable should look like. If you didn’t define the hero interface, you wouldn’t be able to tell TypeScript the type for Iron Man. The way to do that is to do it with interfaces.