Check out a free preview of the full Build Go Apps That Scale on AWS course

The "Go Modules & Imports" Lesson is part of the full, Build Go Apps That Scale on AWS course featured in this preview video. Here's what you'd learn in this lesson:

Melkey demonstrates how Go modules can be divided into separate folders or packages and imported based on their package name. Capitalization of property names within a module will tell the compiler if the property is public or private.

Preview
Close

Transcript from the "Go Modules & Imports" Lesson

[00:00:00]
>> All right, yeah, so I found structs a little challenging when I first got introduced to them, and I haven't even touched on interfaces. But interface is a concept that I personally really enjoy, but I never understood them until I saw how they were used in a practical application.

[00:00:19]
So I'm saving that for after, but just remember, interfaces and structs are a core component of how Go implements its logic. If you look at a lot of packages that define Go, they always have an interface type. I'm gonna go example as to why that is in just a little bit here.

[00:00:36]
But I think that's it for structs, I think they're super important. The whole thing of pointers and references is kind of cool too if you never use it. I know I never did until Go. So, again, that's one of those things I started learning. As I started using go, it just made me kind of be aware of the depth of software engineering and software programming more once I started using it.

[00:00:56]
Okay, cool. All that's super nice. There's one more. Let's go into imports. We're doing alive. Let's go into imports. A lot of people are asking about this. So, make a new pack directly called imports, but this time the file, I want you to name it imports.go, okay? And then for the package instead of main, you package imports.

[00:01:19]
All right, so lots of great questions around importing and exporting in Go. This is a very, very famous gotcha in Go. So let's just make, I don't know. Let's create a new struct. Let's go Ticket struct, and it's gonna have two fields, not fun. Funk, sorry. Let's go type ticket struck, and say it's two fields.

[00:01:45]
Let's say the ticket's gonna have an ID, which is gonna be an INT and then, event, which is small e, okay? So we have both right now. And then let's create a function on our ticket. So func. Let's make a receiver so T, Ticket and let's just say, printEvent that took me way too long to come up with.

[00:02:11]
So it's not gonna take any argument. All it's going to do is do a fmt.Println on t.event. Okay, cool. Ignore the yellow squiggly for a second. If we go back to the first main.go file we created, remember this Hello World one. Let's hop back into that for just a second.

[00:02:37]
If you want to import something from a neighboring package. You may be thinking, okay, will I do something like this and then go import? No, Go doesn't have this notation for relative imports. If you go back to our go.mod file here, this module not only played a role for us to define something that could be consumed by other parties, but it's also how we define our own packages in our own scoped application.

[00:03:03]
So go back to main.go, and right under the F format, we'll do femgo/name of the package. We named it, I forget, what do we named it? Imports, right? And this is a bad name. I probably shouldn't even packages, but I just hope you get the gist here from basics.

[00:03:24]
Changes to femme basics, okay? We are composite language again. Import not used, so again, go does not like when you don't use stuff. So here, let's say we create a new ticket, right? So we can do new ticket is, To import dot ticket, and then we can do the ID, let's say just 123.

[00:03:46]
But, we cannot have the event fields. If I put an event and I put a front end masters course. I'm really not a creative individual. We're getting yelled at, right? It's gonna say a Unknown field event instruct literal of type imports ticket, which is strange because if you dig down into ticket, we have event defined here.

[00:04:07]
But this is where that capitalization and making functions and properties public comes into place. Even though our ticket struck is capitalized with a T, and we've actually used it over here, we're able to create a new Ticket. And with the ID but we can't put event because e is not capitalized here.

[00:04:24]
So here we can just change this to be a capital E. We'll go down here, change this to capital E as well. To go back to remain.go, we can just change this from lowercase to capital and now we have our new ticket, right? And we could do format, println, and I should say new ticket.

[00:04:45]
And if you run this, again, this is the root main.go file, so all you need to do is go run main.go. You now see we have 1, 2, 3 FEM course as a properties or ticket. But we have a function method on that type. So if we go back up here and we'll do new ticket.event, those are the only properties that we have on our type right now, on our ticket type or ticket struck.

[00:05:14]
And again, that is because if you go back to our imports.go, our print is not capitalized. So once we capitalize the P, and we go back, we can now call new ticket.Printevent, right? And now if we run this code from course 123 FCM course. Yes.
>> If you have the qualified name with the GitHub.com etc, does that have to be included in the import for a local package?

[00:05:50]
>> No, not the whole thing.
>> Okay
>> Only be the actual go.mod name of the package and define it. So only like the Go blueprint part or like the name of the package. The entire Definition. Actually, wait, I'm wrong. As a person importing the package, it is that whole definition, okay?

[00:06:08]
So you're right, you would have to put GitHub.com/, etc, etc. If I'm someone who depends on it or whatever, as the person creating the package, right? You can maintain that Go mod or the whole thing as the whole string, or you can shorten it to be something aliased when you're developing it.

[00:06:26]
Because around the whole thing, when you're kind of creating that software, can become cumbersome. I want to say client-facing, but more on user-facing, you would have to still depend on the entire string. So we do go get, let's say entire name package, GitHub.com/xyz, whatever. Let's just say that for example, and as someone who's gonna consume it, what you have to do is literally put GitHub.com/xyz.

[00:06:53]
But as a reference, you can see here we have our imports, right? But we're not putting fembasics/imports, when we're calling the method, it's only imports.ticket. So what would it be? It would be the last portion that you're bringing in. So it would be xyz.MethodFromPackage, okay? And to avoid collision, right?

[00:07:16]
Let's say I have GitHub.com/xyz. And for whatever reason, I also named my package xyz. Which xyz is gonna take, the compiler says, hey, you can't use another xyz, so you can actually just add an alias prepended like GitHub. That's a bad example. Outside xyz, right? And then you can use the package like that, okay?

[00:07:41]
So, you can change the name of the import if in case it's collisions. Did that answer your question? Was that, cool? Thank you. Yes.
>> So with that, you probably wouldn't normally name a package imports.
>> You would not.
>> If your imports was all about tickets, is it normal to see like ticket.ticket?

[00:08:01]
>> Yeah, great. Yeah, thank you. You're right, don't name any imported package as import. This was a bad example to try to showcase the module of how importing works, but in practicality, it kind of loses that mojo. If you were to, let's say make a new package. It's a more practical example and we're gonna see this when we build our AWS software.

[00:08:24]
You will have something called database, right? As the directory. And within your database, you'll have database.go. And in your package name, in the scope of your actual application, it's completely fine to have package database. And then functions that define the type of your database, functions that define methods that interact with the database.

[00:08:45]
But this is a completely reasonable, I made a typo, but it's a completely reasonable way to structure Go code. And we're gonna go into this and more once you write more Go code.

Learn Straight from the Experts Who Shape the Modern Web

  • In-depth Courses
  • Industry Leading Experts
  • Learning Paths
  • Live Interactive Workshops
Get Unlimited Access Now