နားလည်ထားရမယ့် အချက်
Branch label တစ်ခုဆိုတာ commit အသစ်လုပ်တိုင်း ရှေ့ကို ရွေ့သွားတယ် — ဒါက branch ရဲ့ အဓိကရည်ရွယ်ချက်ပါပဲ။ Tag ကတော့ ဆန့်ကျင်ဘက်ပါ — commit တစ်ခုတည်းကို အမြဲတမ်း သတ်မှတ်ပေးပြီး နောက်ပိုင်း ဘယ်လောက်များများ commit ထပ်ရွေ့လျားမသွားတော့ပါ။
Tag တွေက အရေးပါတဲ့ အချိန်တွေအတွက် ဖန်တီးထားတာပါ — production ပေါ်ကို တင်လိုက်တဲ့ commit အတိအကျ၊ customer run နေတဲ့ commit အတိအကျ၊ milestone ပြီးဆုံးသွားတဲ့ commit အတိအကျ ပေါ့။
| Tag အမျိုးအစား | အဓိပ္ပါယ် |
|---|---|
| Lightweight tag | commit တစ်ခုကို ညွှန်ပြတဲ့ နာမည်တစ်ခုသက်သက်ပါ — `git tag <name>` |
| Annotated tag | ကိုယ်ပိုင် author, date, message ပါဝင်ပြီး sign လုပ်နိုင်သော object အပြည့်အစုံ — `git tag -a <name> -m "..."` |
သိမ်းထားချင်တဲ့ (သို့) team နဲ့ share ချင်တဲ့ tag တိုင်းအတွက် annotated tag ကို default အနေနဲ့ သုံးတာ ပိုကောင်းပါတယ်၊ ဘယ်သူက ဘာကြောင့် tag တင်တယ်ဆိုတာ မှတ်တမ်းကျန်ခဲ့လို့ပါ။
Tag တွေက history ထဲက အရေးပါတဲ့ အချက်တွေကို သတ်မှတ်ပြီးရင် team တစ်ခုအနေနဲ့ tag နာမည်ချင်း အဓိပ္ပါယ်ပေါ်လွင်အောင် shared naming scheme တစ်ခု လိုအပ်ပါတယ်။ ဒါကို ဖြေရှင်းပေးတာက semantic versioning ပါ — v2.4.1 လို MAJOR.MINOR.PATCH ပုံစံနဲ့ version number ရေးတာပါ။
- MAJOR — existing user တွေရဲ့ code ကို ချိုးဖျက်နိုင်တဲ့ breaking change
- MINOR — backward-compatible အနေနဲ့ ထည့်ထားတဲ့ feature အသစ်
- PATCH — ဘယ်သူမှ မမှီခိုတဲ့ behavior ကို မပြောင်းဘဲ ပြင်ထားတဲ့ bug fix
Convention ပါ၊ Enforcement မဟုတ်ပါ
Git က ဒါတွေကို ဘာမှ enforce မလုပ်ပါဘူး။ Typo fix တစ်ခုတည်းကို v99.0.0 လို့ tag တင်လို့ရပြီး Git က ကန့်ကွက်မှာ မဟုတ်ပါဘူး — semantic versioning ဆိုတာ human တွေနဲ့ tool တွေ သဘောတူထားတဲ့ convention တစ်ခုပါ။
- Tag
- commit တစ်ခုတည်းကို အမြဲညွှန်ပြထားပြီး ရွှေ့လျားမသွားတဲ့ နာမည်တစ်ခု — release တွေလို အရေးပါသော အချက်များကို မှတ်သားရန် အသုံးပြုသည်။
- Semantic Versioning
- MAJOR.MINOR.PATCH ပုံစံဖြင့် version နံပါတ်ပေးသော convention တစ်ခု — အပိုင်းတစ်ခုစီက breaking change၊ feature အသစ်၊ bug fix စသည့် အပြောင်းအလဲအမျိုးအစားကို ညွှန်ပြသည်။
TAG VS BRANCH: WHO MOVES
------------------------
TAG VS BRANCH: WHO MOVES
-------------------------
main (branch) ---------------------------> moves forward
|
o---o---o---o---o---o <- new commits keep landing here
^
|
v1.0.0 (tag) <- stays pinned to this one commit
forever, even as main moves onလက်တွေ့ scenario နဲ့ ချိတ်ကြည့်မယ်
Commit ကို tag တင်ပါ
သတ်မှတ်ချင်တဲ့ commit ပေါ်မှာ `git tag v1.0.0` (lightweight) သို့ `git tag -a v1.1.0 -m "message"` (annotated) ကို run ပါ။
Tag များကို list ကြည့်ပါ
`git tag` တစ်ခုတည်းက repo ထဲက tag အားလုံးကို alphabetical အစဉ်လိုက် ပြပါတယ်။
Tag ကို စစ်ဆေးပါ
`git show v1.0.0` က ညွှန်ပြထားတဲ့ commit ကို print ထုတ်ပါတယ်၊ annotated tag ဆိုရင် tag ကိုယ်ပိုင် author, date, message ကို အရင်ပြပါတယ်။
Tag ကို push ပါ
`git push origin v1.1.0` နဲ့ ရှင်းရှင်းလင်းလင်း push ပါ၊ (သို့) `git push --tags` နဲ့ အားလုံးကို push ပါ။
Tag တွေက auto push မဖြစ်ပါ
Plain `git push` က commit တွေကိုသာ ပို့ပေးပြီး tag မပါဝင်ပါဘူး။ Explicit push မလုပ်မချင်း teammate တွေက tag အသစ်ကို မမြင်ရပါဘူး။
အတူတူ စမ်းရေးကြည့်မယ်
git init -q -b main
git config user.name "Thuta Learner"
git config user.email "learner@example.com"
export GIT_AUTHOR_NAME="Thuta Learner"
export GIT_AUTHOR_EMAIL="learner@example.com"
export GIT_COMMITTER_NAME="Thuta Learner"
export GIT_COMMITTER_EMAIL="learner@example.com"
echo "console.log('v1');" > app.js
git add app.js
GIT_AUTHOR_DATE="2026-01-01T09:00:00" GIT_COMMITTER_DATE="2026-01-01T09:00:00" \
git commit -m "Initial release logic"
echo "console.log('v1.1');" >> app.js
git add app.js
GIT_AUTHOR_DATE="2026-01-01T10:00:00" GIT_COMMITTER_DATE="2026-01-01T10:00:00" \
git commit -m "Add greeting feature"
echo "console.log('fix');" >> app.js
git add app.js
GIT_AUTHOR_DATE="2026-01-01T11:00:00" GIT_COMMITTER_DATE="2026-01-01T11:00:00" \
git commit -m "Fix off-by-one bug"
git log --oneline
git tag v1.0.0 HEAD~2
git tag -a v1.1.0 -m "Add greeting feature and bug fix"
git tag
git show v1.0.0 --stat
git show v1.1.0 --stat$ git log --oneline
fba08e9 Fix off-by-one bug
7744f86 Add greeting feature
9b07fe7 Initial release logic
$ git tag
v1.0.0
v1.1.0
$ git show v1.0.0 --stat
commit 9b07fe7c5e1dc5e087a0f2c53bf8bd78caf6e93f
Author: Thuta Learner <learner@example.com>
Date: Thu Jan 1 09:00:00 2026 +0900
Initial release logic
app.js | 1 +
1 file changed, 1 insertion(+)
$ git show v1.1.0 --stat
tag v1.1.0
Tagger: Thuta Learner <learner@example.com>
Date: Thu Jan 1 11:30:00 2026 +0900
Add greeting feature and bug fix
commit fba08e984fb5ba335e158b32b88bdcd5f003ea7b
Author: Thuta Learner <learner@example.com>
Date: Thu Jan 1 11:00:00 2026 +0900
Fix off-by-one bug
app.js | 1 +
1 file changed, 1 insertion(+)၅ မိနစ် စမ်းကြည့်
သင့် repo တစ်ခုမှာ commit နှစ်ခု လုပ်ပါ၊ ပြီးရင် ပိုအစောကျတဲ့ commit ကို v1.0.0 (lightweight) အဖြစ်၊ နောက်ကျတဲ့ commit ကို v1.1.0 (annotated, ဘာပြောင်းလဲသွားလဲ ဖော်ပြတဲ့ message ပါ) အဖြစ် tag တင်ပါ။ နှစ်ခုစလုံး ရှိကြောင်း သေချာအောင် `git tag` ကို run ပါ၊ ပြီးရင် တစ်ခုစီအပေါ် `git show` ကို သုံးပြီး lightweight tag နဲ့ annotated tag အတွက် ဘာတွေ print ထုတ်လဲ ကွာခြားချက်ကို မှတ်သားပါ။
သတိလေးတစ်ချက်
Tag တွေက မရွှေ့ပါဘူး — commit မှားတာကို tag တင်မိရင် tag ကို ဖျက်ပြီး (`git tag -d`) ပြန်ဖန်တီးရပါလိမ့်မယ်၊ 'update in place' ဆိုတာ မရှိပါဘူး။
Plain `git push` က tag တွေကို remote ဆီ ပို့မပေးပါဘူး၊ `git push --tags` ကို မေ့သွားရင် teammate တွေက သင်ဖန်တီးထားတဲ့ tag ကို ဘယ်တော့မှ မမြင်ရပါဘူး။
Git Documentation: git-tag — Git & GitHub