peterh/liner
peterh/liner là thư viện Go cung cấp line editor cho CLI: nhập lệnh tương tác, history, auto-completion và xử lý phím giống readline / linenoise . Phù hợp khi cần nâng cấp UX cho công cụ terminal viết…
Kết luận: partial · Công nghệ: go · cli · line-editor · readline · terminal-ui
peterh/liner là thư viện Go cung cấp line editor cho CLI: nhập lệnh tương tác, history, auto-completion và xử lý phím giống readline/linenoise. Phù hợp khi cần nâng cấp UX cho công cụ terminal viết bằng Go mà không phải tự xử lý raw input; dự án đã có ~1.1k stars nên đủ tin cậy để dùng ngay ở mức utility library.
📖 Giới thiệu chi tiết
🧩 Nó là gì?
peterh/liner là một thư viện Go giúp bạn tạo ô nhập lệnh tương tác trong terminal, giống kiểu người dùng gõ lệnh trong shell. Nó hỗ trợ chỉnh sửa dòng đang nhập, lưu lịch sử nhập, gợi ý tự động và chạy được đa nền tảng.
🎯 Giải quyết vấn đề gì? Dành cho ai?
Khi viết công cụ CLI bằng Go, nếu chỉ dùng fmt.Scanln hoặc đọc input thủ công, trải nghiệm nhập liệu thường khá “thô”: không có lịch sử, không dùng phím mũi tên tốt, không có gợi ý, khó xử lý Ctrl-C.
peterh/liner giải quyết phần đó cho bạn.
Dự án này phù hợp với:
- Người viết CLI bằng Go cần prompt tương tác, ví dụ: console quản trị, REPL, shell nhỏ, công cụ nội bộ.
- Người muốn có trải nghiệm gần giống
readlinehoặclinenoisenhưng dùng thư viện thuần Go. - Dự án cần build đa nền tảng, kể cả Unix-like và Windows.
- Người không muốn tự xử lý raw terminal input, phím đặc biệt, history và completion.
⚙️ Hoạt động ra sao?
liner.NewLiner()tạo một line editor, tức là bộ xử lý nhập một dòng trong terminal.Prompt("...")hiển thị câu hỏi hoặc dấu nhắc, rồi chờ người dùng nhập.- Người dùng có thể dùng các phím quen thuộc như
Left,Right,Home,End,Backspace,Ctrl-A,Ctrl-E,Ctrl-R. - History cho phép lưu và đọc lại các dòng đã nhập trước đó, thường bằng phím
UpvàDown. - Completion cho phép gợi ý khi người dùng nhấn
Tab. SetCompleternhận một hàm tự viết để quyết định danh sách gợi ý.AppendHistorythêm dòng vừa nhập vào lịch sử.ReadHistoryvàWriteHistorygiúp đọc/ghi lịch sử từ file.- Thư viện được viết bằng pure Go, nghĩa là không cần
cgo, dễ cross-compile sang nhiều hệ điều hành.
🆚 Khi nào nên dùng / không nên
Nên dùng peterh/liner khi:
- Bạn viết ứng dụng terminal bằng Go và muốn người dùng nhập lệnh thoải mái hơn.
- Bạn cần history, auto-completion, xử lý phím mũi tên,
Ctrl-C,Ctrl-D. - Bạn muốn một thư viện gọn, thực dụng, dễ nhúng vào dự án.
- Bạn cần chạy đa nền tảng mà không muốn phụ thuộc vào thư viện C.
Không nên dùng khi:
- CLI của bạn chỉ nhận tham số qua command line, ví dụ
mytool --name bob, không cần nhập tương tác. - Bạn cần giao diện terminal phức tạp kiểu full-screen UI, nhiều panel, bảng, form; khi đó nên xem các thư viện TUI khác.
- Bạn cần đầy đủ mọi hành vi nâng cao giống GNU
readline;linercố tình bỏ một số tính năng chỉ có trên vài nền tảng để giữ hành vi nhất quán.
So sánh nhanh:
fmt.Scanln: đơn giản hơn, nhưng gần như không có trải nghiệm chỉnh sửa dòng.readline: mạnh và quen thuộc, nhưng có thể kéo theo phụ thuộc nền tảng hoặc thư viện C.linenoise: nhẹ, là nguồn cảm hứng củaliner, nhưngpeterh/linerđược viết cho Go và tiện dùng trực tiếp trong dự án Go.
🚀 Bắt đầu nhanh
Cài thư viện:
go get github.com/peterh/liner
Ví dụ tối thiểu:
package main
import (
"fmt"
"log"
"os"
"path/filepath"
"strings"
"github.com/peterh/liner"
)
var (
historyFile = filepath.Join(os.TempDir(), ".liner_example_history")
names = []string{"john", "james", "mary", "nancy"}
)
func main() {
line := liner.NewLiner()
defer line.Close()
line.SetCtrlCAborts(true)
line.SetCompleter(func(input string) []string {
var suggestions []string
for _, name := range names {
if strings.HasPrefix(name, strings.ToLower(input)) {
suggestions = append(suggestions, name)
}
}
return suggestions
})
if file, err := os.Open(historyFile); err == nil {
line.ReadHistory(file)
file.Close()
}
input, err := line.Prompt("What is your name? ")
if err == nil {
fmt.Println("Hello,", input)
line.AppendHistory(input)
} else if err == liner.ErrPromptAborted {
log.Println("Aborted")
} else {
log.Println("Error reading line:", err)
}
if file, err := os.Create(historyFile); err == nil {
line.WriteHistory(file)
file.Close()
}
}
Chạy thử:
go run main.go
Khi chạy, bạn có thể:
- Nhập tên rồi nhấn
Enter. - Nhấn
Tabđể thử gợi ý từ danh sáchjohn,james,mary,nancy. - Dùng phím
Upđể lấy lại lịch sử đã nhập. - Nhấn
Ctrl-Cđể hủy prompt nếu đã bậtSetCtrlCAborts(true).
✅ Điểm mạnh & ⚠️ Hạn chế
✅ Điểm mạnh:
- Thuần Go, không cần
cgo, dễ build và cross-compile. - Có sẵn history, auto-completion và nhiều phím chỉnh sửa dòng quen thuộc.
- Hỗ trợ cả Unix-like và Windows.
- Dễ tích hợp vào CLI Go hiện có.
- Phù hợp để nâng cấp trải nghiệm nhập liệu mà không phải tự xử lý terminal phức tạp.
- Dự án có khoảng
1.1k stars, đủ tin cậy để dùng như một utility library.
⚠️ Hạn chế:
- Không phải thư viện dựng giao diện terminal đầy đủ.
- Một số tính năng đặc thù nền tảng bị bỏ qua để giữ hành vi nhất quán.
- Không nhằm thay thế hoàn toàn GNU
readlinetrong các ca sử dụng rất nâng cao. - Bạn vẫn cần tự thiết kế logic lệnh, parse input và xử lý nghiệp vụ của ứng dụng.