[২.২] প্যাকেজ ( Packages )
এখন পর্যন্ত আমরা সব কোড একটা ফাইলে করে আসছি কিন্তু আমাদের কোডের সাইজ যদি অনেক বেশি হয় তাহলে এক জায়গায় এত কোড, বিষয়টা কমপ্লেক্স হয়ে যাবে । এবারে আমরা প্যাকেজ সম্পর্কে জানব যার দ্বারা আমাদের কোড ভেঙে ভেঙে আরো গোছানো পন্থায় করতে পারি ।
প্যাকেজ মূলত একটি ফোল্ডার যেখানে কিছু Go ফাইল থাকে এবং তাতে ওই প্যাকেজ সম্পর্কিত কিছু কোড থাকে । আমরা না জেনেও এখন পর্যন্ত প্যাকেজ ব্যবহার করে আসছি, যেমন, “fmt” একটি প্যাকেজ আবার “math” একটি প্যাকেজ, আমরা কোডও করে আসছি “main” প্যাকেজে ।
একটি প্যাকেজে বিভিন্ন ধরনের ফাংশন থাকতে পারে এবং যেগুলো পাবলিক বা বড় হাতের অক্ষর দিয়ে শুরু সেগুলো আমরা অন্য প্যাকেজ থেকে প্যাকেজের নাম এবং তারপরে ডট দিয়ে অ্যাক্সেস করতে পারি । যেমন Println() একটি ফাংশন যেটি “fmt” প্যাকেজে আছে তাই আমরা fmt.Println() দিয়ে ফাংশনটি অ্যাক্সেস করতে পারি । যদি ফাংশনটি পাবলিক না হতো তাহলে তা শুধুমাত্র ঐ প্যাকেজ বা ফোল্ডারের মধ্যে তা অ্যাক্সেস করা যেত। Go তে কিছু ডিফল্ট প্যাকেজ থাকে যেমন fmt, math, time, strings, os, strconv ইত্যাদি । আমরা চাইলে সহজেই প্যাকেজ তৈরি করতে পারি।
প্যাকেজ তৈরি করার জন্য আমরা আমাদের প্রজেক্ট ডিরেক্টরীতে একটি ফোল্ডার তৈরি করব এবং ফোল্ডারের ভেতরে Go ফাইলে কোড লিখব। এই ফোল্ডারের মধ্যে সকল Go ফাইলের প্রথমে package লিখে এর পরে ফোল্ডারের নামটি লিখতে হবে কারণ বাইডিফল্ট ফোল্ডারের নামই প্যাকেজের নাম হয় । এরপর সেখানে আমরা আমাদের প্রয়োজনমতো কোড লিখতে পারি । আমরা চাইলে প্যাকেজের মধ্যেও প্যাকেজ বানাতে পারি ।
প্যাকেজের নামকরণের ক্ষেত্রে সাধারণত কিছু নিয়ম ফলো করা হয় –
- প্যাকেজের নাম সবগুলো ছোট হাতের অক্ষরে হয়।
- প্যাকেজের নাম সাধারনত সংক্ষিপ্ত হয় যেমন format এর বদলে fmt যদি সম্ভব হয়।
- প্যাকেজের নাম সাধারণত এক শব্দে হয় এবং যদি কখনো একাধিক শব্দ প্রয়োজন হয় তবে তাদের মাঝখানে কোন আন্ডারস্কোর বা বড় হাতের অক্ষর হয় না। যেমন, strconv ।
কোন প্যাকেজের একটি ফাইলে আমরা এভাবে কোড করতে পারি –
// earth.go
package solarsystem
import "fmt"
func Hello() {
fmt.Println("Hello from earth!")
}
এই কোড অন্য কোন প্যাকেজ থেকে অ্যাক্সেস করতে হলে আমাদের প্যাকেজটি ইমপোর্ট করতে হবে এবং প্যাকেজের নাম ও তারপর ডট দিয়ে আমরা তার ফাংশন বা ফিল্ড গুলো অ্যাক্সেস করতে পারব। আমাদের নেস্টেড প্যাকেজ থাকতে পারে তাই কোনো প্যাকেজ অ্যাক্সেস করার জন্য ইমপোর্ট সেকশনে প্যাকেজের পুরো পাথটি দিতে হবে –
// main.go
package main
import "galaxy/milkyway/solarsystem" //imported package
func main() {
solarsystem.Hello()
}
এভাবে আমরা খুব সহজেই প্যাকেজ বানাতে পারি, অন্যান্য প্রজেক্টে ব্যাবহার করতে পারি এবং চাইলে প্যাকেজটি গিটহাবেও রাখতে পারি । আবার প্রয়োজনে গিটহাব থেকে কোন প্যাকেজ ইমপোর্ট করে ব্যবহার করতে পারি । ইমপোর্ট করে ব্যবহার করার জন্য আমরা go get কমান্ডের সাথে প্যাকেজের url ব্যাবহার করে প্যাকেজটি প্রজেক্টে অ্যাড করে নিতে পারব। উল্লেখ্য, Go এর 1.17 ভার্সনের পর থেকে go get এর পরিবর্তে go install কমান্ড টি ব্যবহার করা শ্রেয়। কেননা ভার্সন 1.18 থেকে go get ব্যবহার করে আর প্যাকেজ বিল্ড করা যাবে না। এই ব্যাপারে বিস্তারিত জানতে, এই লিংকটি সাহায্য করবে যেমন –
go get github.com/Google/uuid
এরপর আমরা এ প্যাকেজটি আমাদের প্রজেক্টে ব্যবহার করতে পারব –
import "github.com/Google/uuid"
বাল্ক ইম্পোর্টিং হল Go-এর আরেকটি বৈশিষ্ট্য যা আমাদের একবারে একাধিক প্যাকেজ ইমপোর্ট করতে দেয়। এর জন্য, আমাদেরকে প্রথম বন্ধনীর ভিতরে লাইনব্রেক দ্বারা পৃথক করে, আমরা যে প্যাকেজগুলি ইমপোর্ট করতে চাই তা তালিকাভুক্ত করতে হবে, যেমনঃ
package main
import (
"fmt"
"strings"
)
func main() {
fmt.Println(strings.ToUpper("nice you're doing great!"))
}
আউটপুটঃ
NICE YOU'RE DOING GREAT!
Go তে ইমপোর্ট করার সময় কোনো প্যাকেজকে আমরা চাইলেই সংক্ষিপ্ত নাম দিয়েও সংজ্ঞায়িত করতে পারি। এটা Go তে ইমপোর্ট এলিয়াস (alias) নামে পরিচিত।
package main
import (
"fmt"
m "math"
)
func main() {
x := m.Sqrt(4)
fmt.Println(x)
}
আউটপুটঃ
2
Go তে ইমপোর্ট alias ব্যবহার করার বিভিন্ন সুবিধা রয়েছে যেমন:
- নামকরণের দ্বন্দ্ব এড়ানো: যখন দুটি প্যাকেজের একই নাম থাকে, তখন একই ফাইলে উভয়টিকে ইমপোর্ট করলে নামকরণের বিরোধ হতে পারে। একটি উপনাম ব্যবহার করে, আমরা প্রতিটি প্যাকেজকে ভিন্ন ভিন্ন নাম দিতে পারি এবং দ্বন্দ্ব এড়াতে পারি।
- প্যাকেজের নাম সংক্ষিপ্ত করা: Go-এর কিছু প্যাকেজের নাম দীর্ঘ হতে পারে, যা কোডটি পড়া কঠিন করে তোলে। একটি উপনাম ব্যবহার করে, আমরা প্যাকেজটিকে একটি ছোট, এবং আরও পাঠযোগ্য নাম দিতে পারি।
- কোড স্পষ্টতা: একটি উপনাম ব্যবহার করে, আমরা ইমপোর্ট করা প্যাকেজগুলির অর্থপূর্ণ নাম দিয়ে কোডটিকে আরও পাঠযোগ্য করে তুলতে পারি। এটি অন্যান্য ডেভেলপারদের জন্য আমাদের কোড বোঝা সহজ করে তুলতে পারে।