- Delta เป็นเครื่องมือที่เพิ่มการเน้นไวยากรณ์และฟังก์ชันโปรแกรมดูหน้าให้กับเอาต์พุตของ Git, diff และ grep ช่วยให้อ่าน diff ได้มีประสิทธิภาพและสวยงามขึ้น
- ใน package manager ส่วนใหญ่ ชื่อแพ็กเกจคือ git-delta แต่ไฟล์รันคือ
delta และสามารถตั้งค่า core.pager = delta ใน ~/.gitconfig เพื่อใช้เป็น Git pager ได้
- ฟีเจอร์หลักได้แก่ ธีมเน้นไวยากรณ์เดียวกับ bat, การเน้น diff ระดับคำโดยอิงอัลกอริทึมอนุมานการแก้ไข Levenshtein, มุมมองเปรียบเทียบซ้าย-ขวา, เลขบรรทัด, การนำทางด้วย
n/N และการแสดง merge conflict ที่ปรับปรุงดีขึ้น
- ยังเน้นไวยากรณ์ให้เอาต์พุตของ
git blame, rg, git grep, grep ได้ด้วย และสามารถใช้ --hyperlinks เพื่อทำให้ commit hash อยู่ในรูปแบบลิงก์ของผู้ให้บริการโฮสติ้งอย่าง GitHub, GitLab, SourceHut, Codeberg
- สามารถคงลักษณะให้ใกล้เคียงกับเอาต์พุต Git/diff พื้นฐาน หรือปรับเลย์เอาต์และสไตล์ได้อย่างมาก ทำให้ปรับแต่งสภาพแวดล้อมการรีวิว diff ภายในเทอร์มินัลได้ละเอียด
Delta ทำอะไร
- Delta เป็นโปรแกรมดูหน้าแบบเน้นไวยากรณ์สำหรับเอาต์พุต Git, diff และ grep
- มีเป้าหมายเพื่อทำให้เวลาที่ใช้ในการอ่าน diff มีประสิทธิภาพและเพลิดเพลินขึ้นในสภาพแวดล้อมที่โค้ดเปลี่ยนแปลงตลอดเวลา
- สามารถปรับ เลย์เอาต์และสไตล์ ของ diff ได้อย่างกว้างขวาง และหากต้องการก็สามารถคงไว้ให้ใกล้เคียงกับเอาต์พุต Git/diff พื้นฐานมาก ๆ ได้
การติดตั้งและการตั้งค่าพื้นฐาน
- เอกสารการติดตั้งมีอยู่ที่ Install it
- ใน package manager ส่วนใหญ่ ชื่อแพ็กเกจคือ git-delta และชื่อไฟล์รันคือ
delta
- สามารถเพิ่มการตั้งค่าต่อไปนี้ลงใน
~/.gitconfig เพื่อใช้เป็น Git pager และตัวกรอง diff แบบอินเทอร์แอ็กทีฟได้
[core]
pager = delta
[interactive]
diffFilter = delta --color-only
[delta]
navigate = true # use n and N to move between diff sections
dark = true # or light = true, or omit for auto-detection
[merge]
conflictStyle = zdiff3
- การตั้งค่าเดียวกันสามารถใช้ผ่านคำสั่ง
git config --global ได้เช่นกัน
git config --global core.pager delta
git config --global interactive.diffFilter 'delta --color-only'
git config --global delta.navigate true
git config --global delta.dark true # or `delta.light true`, or omit for auto-detection
git config --global merge.conflictStyle zdiff3
- ดูความช่วยเหลือได้ที่
delta -h, คู่มือฉบับเต็มที่ delta --help และเอกสารออนไลน์ที่ user manual
ฟีเจอร์สำหรับอ่าน diff
- การเน้นไวยากรณ์ ใช้ธีมเน้นไวยากรณ์เดียวกับ bat
- การเน้น diff ระดับคำใช้ อัลกอริทึมอนุมานการแก้ไข Levenshtein
- รองรับมุมมองเปรียบเทียบซ้าย-ขวาและการตัดบรรทัด
- รองรับการแสดงเลขบรรทัด
- สามารถใช้ปุ่ม
n และ N เพื่อย้ายระหว่างไฟล์ใน diff ขนาดใหญ่ หรือระหว่าง diff ในมุมมอง log -p ได้
- ฟีเจอร์นี้เปิดใช้งานด้วย
--navigate
- รองรับเอาต์พุต unified diff แบบดั้งเดิมร่วมกับเอาต์พุตของ Git
- สามารถตรวจจับพื้นหลังเทอร์มินัลแบบสว่าง/มืดได้อัตโนมัติ
รูปแบบการแสดงผลและธีม
- ธีมเน้นไวยากรณ์ ทุกธีมที่ bat มีให้ สามารถใช้ใน Delta ได้เช่นกัน
delta --show-syntax-themes --dark
delta --show-syntax-themes --light
- มุมมองเปรียบเทียบซ้าย-ขวามีเอกสารอยู่ใน Side-by-side view user manual
[delta]
side-by-side = true
- ค่าเริ่มต้นของมุมมองเปรียบเทียบซ้าย-ขวาเปิดใช้เลขบรรทัด และมีการเน้นไวยากรณ์ทั้งในพาเนลซ้ายและขวา
- มุมมองเปรียบเทียบซ้าย-ขวาจะตัดบรรทัดยาวโดยอัตโนมัติ
- ฟีเจอร์เลขบรรทัดมีเอกสารอยู่ใน Line numbers user manual
[delta]
line-numbers = true
การรองรับตามงานของ Git
- การแสดง merge conflict มีให้ในรูปแบบที่ปรับปรุงแล้ว และเอกสารที่เกี่ยวข้องอยู่ที่ Merge conflicts user manual
- เอาต์พุตของ git blame รองรับการเน้นไวยากรณ์ และเมื่อใช้
--hyperlinks จะสามารถทำให้ commit อยู่ในรูปแบบลิงก์ของผู้ให้บริการโฮสติ้งได้
- ผู้ให้บริการโฮสติ้งที่รองรับ: GitHub, GitLab, SourceHut, Codeberg
- เอกสารที่เกี่ยวข้อง: Git blame user manual
- ยังเน้นไวยากรณ์ให้เอาต์พุต grep เช่น
rg, git grep, grep ด้วย
- รองรับฟีเจอร์
--color-moved ของ Git
การจัดสไตล์และโหมดเข้ากันได้
- สามารถคัดลอกโค้ดจาก diff ได้โดยตรง และเครื่องหมาย
-/+ จะถูกลบออกโดยค่าเริ่มต้น
- มีโหมดจำลอง
diff-highlight และ diff-so-fancy
- commit hash สามารถเชื่อมไปยังหน้าของผู้ให้บริการโฮสติ้งในรูปแบบ hyperlinks ของเทอร์มินัลได้
- พาธไฟล์ก็สามารถทำให้อยู่ในรูปแบบไฮเปอร์ลิงก์ที่เปิดได้ในระบบปฏิบัติการ
- สามารถจัดสไตล์ กล่อง/เส้นตกแต่ง ที่ช่วยดึงความสนใจไปยังส่วนหัว commit, ไฟล์ และ hunk ได้
- รองรับสตริงสไตล์ที่รวมสี foreground, สี background และคุณสมบัติฟอนต์ สำหรับองค์ประกอบที่กำหนดสไตล์ได้มากกว่า 20 รายการ
- ภาษาในการกำหนดสไตล์ใช้ภาษา color/style แบบเดียวกับ Git
1 ความคิดเห็น
ความคิดเห็นบน Hacker News
Delta เป็นเครื่องมือแบบตั้งค่าครั้งเดียวแล้วลืมไปได้เลย และพักใหญ่แล้วที่ไม่ได้เห็นเอาต์พุต
git grep/diff/blameแบบ “ดิบ ๆ”ผมใช้มันเสมอกับ diff ทั่วไปนอก Git repository ด้วย และวันนี้เพิ่งรู้ว่าสามารถใช้ร่วมกับ
ripgrepได้ด้วยhttps://dandavison.github.io/delta/grep.html
bat ที่มีคนพูดถึงไปแล้วก็เป็นเครื่องมือแบบตั้งค่าครั้งเดียวแล้วลืมเหมือนกัน เลยตั้ง alias ให้
catเป็นbatและแยก/usr/bin/catซึ่งเป็น “cat แท้ ๆ” ไว้เป็น aliasvcathttps://github.com/sharkdp/bat
\catผมยังจำข้อสังเกตดี ๆ ที่เคยเห็นได้อยู่ คือ syntax highlighting ในปัจจุบันกำลังเน้นผิดสิ่ง
ไวยากรณ์เป็นสิ่งที่มนุษย์แยกแยะได้ดีอยู่แล้ว จึงไม่ควรลงสีที่ไวยากรณ์ แต่ควรเน้น symbol มากกว่า ถ้าให้สีต่างกันกับชื่อตัวแปรและชื่อฟังก์ชันแต่ละตัว เป้าหมายจะไม่ใช่ “นี่คือ symbol” แต่เป็น “แยก symbol ที่แตกต่างกันได้เร็วขึ้น”
แต่เพราะมันยากกว่าการแต่งไวยากรณ์มาก เครื่องมือต่าง ๆ เลยดูเหมือนจะอยู่กับทางที่ง่ายมากกว่าทางที่มีประโยชน์ syntax highlighting ก็ช่วยได้ไม่น้อยเหมือนกัน แต่ผมอยากเห็นว่าเอนจินจับคู่ symbol ทำงานได้ดีจริงแค่ไหน
จำไม่ได้ว่าอ่านต้นฉบับที่ไหน เลยอ้างแหล่งที่มาให้ถูกต้องไม่ได้
ระหว่างค้นหาเจอบทความนี้: https://www.wilfred.me.uk/blog/2014/09/27/the-definitive-gui...
น่าจะมีมาก่อนหน้านี้อีก แต่บทความอธิบายที่เก่าที่สุดเท่าที่หาได้คือบทความปี 2009: https://zwabel.wordpress.com/2009/01/08/c-ide-evolution-from...
https://difftastic.wilfred.me.uk/
https://github.com/Wilfred/difftastic
ส่วนตัวใช้ color-identifiers-mode ใน Emacs
https://github.com/ankurdave/color-identifiers-mode
ผมยังไม่ได้ถูกตรรกะนั้นโน้มน้าวอย่างสมบูรณ์ แต่ก็แอบสนใจอยู่บ้าง
บางครั้งผม highlight เองเพื่อตามตัวแปรและตรวจว่ามีจุดใช้งานที่พลาดไปไหม ซึ่งเข้าใจประโยชน์ในกรณีนั้นดี แต่ไม่แน่ใจว่าสีและคอนทราสต์จะพอสำหรับตามหลายตัวแปรพร้อมกันหรือไม่ และหน้าจออาจดูรกได้
ทางประนีประนอมอาจเป็นการลงสีตัวแปรเองได้สูงสุดประมาณ 3 ตัว แต่กรณีที่ต้องการความช่วยเหลือแบบนั้นก็อาจเป็นสัญญาณตั้งแต่แรกว่าโค้ดอ่านยากอยู่แล้ว แน่นอนว่าการช่วยจัดการ codebase ที่รกก็เป็นการใช้งานที่สมเหตุสมผล
ไม่ได้หวือหวา แต่ถ้าต้องการ diff ระดับคำ ที่พอใช้ได้ด้วย
gitมาตรฐานอย่างเดียว แค่นี้ก็มักจะเพียงพอgit diff --color-words --word-diff-regex='\w+|.'.gitconfigต้องทำอย่างไร?Delta ทำหน้าที่ของมันได้ดีมาก แต่ผมติดปัญหาที่มันตัดบรรทัดยาว ๆ อยู่เรื่อย ๆ
พอเห็นบทความนี้เลยลองเช็กว่าสถานการณ์เปลี่ยนไปหรือยัง และมันเปลี่ยนไปจริง ๆ ตอนนี้ถ้าตั้งค่า
git config --global --replace-all delta.max-line-length 0ก็จะไม่ตัดบรรทัดอีกต่อไปไม่ค่อยแน่ใจว่าทำไมค่านี้ถึงไม่ใช่ค่าเริ่มต้น การอภิปรายเรื่องการเปลี่ยนแปลงอยู่ที่ https://github.com/dandavison/delta/pull/290
เพราะเมื่อทำ syntax highlighting กับบรรทัดที่ยาวมาก เช่นไฟล์
.jsที่ถูก minify ถ้าไม่ตัดอาจช้ามากได้ไหน ๆ ก็พูดถึง diff แล้ว สิ่งที่น่ารำคาญในเอาต์พุต diff ของ Git คือมันแสดง path ของไฟล์โดยเริ่มจากชื่อไฟล์สองชื่อเหมือน Unix diff แบบดั้งเดิม
--- a/some/path/to/file.c+++ b/some/path/to/file.cผมมักใช้
cmd-คลิกใน iTerm เพื่อเปิดไฟล์ใน editor แต่กรณีนี้ใช้ไม่ได้เพราะ prefixa/และb/มีวิธีให้ Git format ชื่อไฟล์ให้ดีกว่านี้ไหม? สองบรรทัดนั้นก็ไม่ได้จำเป็นด้วยซ้ำgit config --global diff.noprefix trueตัวเลือกอื่นเกี่ยวกับ prefix ดูได้ในคู่มือ
ผมใช้ delta กับ difftastic ผสมกันอยู่ และทั้งคู่ยอดเยี่ยม
โดยเฉพาะ difftastic เก่งกับ syntax แบบ tree-sitter AST จึงช้านิดหน่อย แต่ diff ที่รู้จัก AST นั้นดีจริง ๆ
Delta สะอาดตาและเร็วมาก
ทิปที่มีประโยชน์สำหรับเปิด/ปิดฟีเจอร์ side-by-side ของ Delta ตามขนาดหน้าต่าง ตัวอย่างนี้อิง bash ส่วน shell อื่น ๆ ก็ประยุกต์ใช้เองได้
function delta_sidebyside {if [[ COLUMNS -ge 120 ]]; thenDELTA_FEATURES='side-by-side'elseDELTA_FEATURES=''fi}trap delta_sidebyside WINCHCOLUMNSขาด$และน่าจะต้องexportก่อนตั้งค่าDELTA_FEATURESด้วยผมใช้ทั้ง delta และ difftastic และแนะนำเท่าไรก็ไม่พอ
ถ้าใช้ terminal แม้แต่นิดเดียว ก็ควรติดตั้งไว้
ทั้งคู่รองรับใน Magit ของ Emacs และ Lazygit ก็รองรับด้วย
tig ก็ควรลองดู: https://jonas.github.io/tig/
เพราะใช้
git diffธรรมดาที่มีสีมาตลอด เลยอยากชอบสิ่งนี้อยู่เหมือนกัน แต่ดู ซับซ้อนเกินไปขอแจ้งว่าเป็นโปรเจกต์ของผมเอง
git diffแบบดั้งเดิมมีปัญหาอะไรเป็นพิเศษ