📦 Go – Packages Explained with Examples, Structure & Best Practices (2025 Guide)
🧲 Introduction – What Are Packages in Go?
In Go, a package is a way to group related code (functions, types, variables) into modular units. Packages promote code reuse, encapsulation, and maintainability. Every Go program is made up of packages, with main being the entry point.
🎯 In this section, you’ll learn:
- How to declare, import, and use packages
- Directory structure and naming conventions
- Export rules and package initialization
- Custom and standard library packages
✅ Basic Package Syntax
Every Go file starts with a package declaration.
package mathutil
func Add(a, b int) int {
return a + b
}
✅ This file is part of the mathutil package.
📥 Importing a Package
package main
import (
"fmt"
"math"
)
func main() {
fmt.Println(math.Sqrt(16)) // Output: 4
}
✅ Use the import keyword to bring in standard or custom packages.
🧱 Creating a Custom Package
Folder Structure:
myproject/
├── main.go
└── utils/
└── mathutil.go
mathutil.go:
package utils
func Square(n int) int {
return n * n
}
main.go:
package main
import (
"fmt"
"myproject/utils"
)
func main() {
fmt.Println(utils.Square(5)) // Output: 25
}
✅ Organize reusable logic into folders and reference using their import path.
🔓 Exported vs Unexported Identifiers
| Identifier Name | Accessible Outside Package? |
|---|---|
Add() | ✅ Yes (starts with capital) |
multiply() | ❌ No (starts with lowercase) |
✅ Only capitalized names are exported and visible to other packages.
🪛 Init Function in Packages
func init() {
fmt.Println("utils package initialized")
}
✅ The init() function runs automatically once when the package is imported.
🧩 Aliasing and Dot Import
import m "math"
fmt.Println(m.Pi)
✅ Use aliasing for shorter references.
import . "fmt"
Println("No fmt prefix used") // Not recommended for clarity
❌ Dot import brings all identifiers into the local scope—use sparingly.
🧠 Best Practices
| Best Practice | Reason |
|---|---|
| ✅ Use lowercase package names | Idiomatic and consistent |
| ✅ Keep package focused on one concern | Improves modularity |
| ❌ Avoid circular imports | Leads to dependency issues |
| ✅ Capitalize exported identifiers | Signals visibility clearly |
| ✅ Use meaningful init() logic | Avoid hidden side effects |
📌 Summary – Recap & Next Steps
Packages are the foundation of Go’s modular programming. They enable you to build reusable, testable, and organized codebases using clear separation of logic and responsibility.
🔍 Key Takeaways:
- Declare each file with a
packagename - Use
importto include standard or custom packages - Capitalized names are exported
- Use folder structure to manage custom packages
⚙️ Next: Explore Go Modules for Dependency Management, or learn How to Publish Your Own Go Package.
❓ FAQs – Go Packages
❓ What is the difference between a package and a module in Go?
✅ A package is a unit of code, while a module is a collection of packages with versioning support (go.mod).
❓ Can a Go file contain multiple packages?
❌ No. All files in a folder should belong to the same package.
❓ When does the init() function run in a package?
✅ When the package is first imported—before main() executes.
❓ How do I create reusable packages in Go?
✅ Put your code in its own folder with a package declaration and import it as needed.
❓ Are all functions in a package automatically exported?
❌ No. Only identifiers starting with a capital letter are exported.
Share Now :
