diff options
author | Gabriel A. Giovanini <mail@gabrielgio.me> | 2024-04-15 22:17:54 +0200 |
---|---|---|
committer | Gabriel A. Giovanini <mail@gabrielgio.me> | 2024-04-15 22:17:54 +0200 |
commit | 1e36d1ba1ba9659ffd01e06e93ffee670f842ff8 (patch) | |
tree | d9c9d1ac019107c8427aff60bf1537fea1687cc6 /app.go | |
parent | 6dd0c4747aa57227b5898fc639e3f2b643ce013c (diff) | |
download | dict-1e36d1ba1ba9659ffd01e06e93ffee670f842ff8.tar.gz dict-1e36d1ba1ba9659ffd01e06e93ffee670f842ff8.tar.bz2 dict-1e36d1ba1ba9659ffd01e06e93ffee670f842ff8.zip |
feat: Add initial go implementation
At this point this code still classified as playground code.
Diffstat (limited to 'app.go')
-rw-r--r-- | app.go | 160 |
1 files changed, 160 insertions, 0 deletions
@@ -0,0 +1,160 @@ +package main + +import ( + "bufio" + "bytes" + "context" + "fmt" + "io" + "log/slog" + "math" + "os" + "strings" + + "github.com/rivo/tview" +) + +const ( + memory = ":memory:" +) + +func run(ctx context.Context, name string) error { + db, err := Open(memory) + if err != nil { + return err + } + + err = db.Restore(ctx, name) + if err != nil { + return err + } + + list := tview.NewList() + + input := tview.NewInputField(). + SetLabel("S:"). + SetChangedFunc(func(v string) { + list.Clear() + + words, err := db.SelectDict(ctx, v, 100) + if err != nil { + return + } + + for _, w := range words { + list.AddItem(w.Word, w.Line, 0, nil) + } + }). + SetAutocompleteFunc(func(v string) []string { + if len(v) == 0 { + return []string{} + } + + vs, err := db.SelectSpell(ctx, v) + if err != nil { + slog.Error("Error select spelling", "error", err) + return []string{} + } + + return vs + }) + + grid := tview.NewGrid(). + SetRows(1, 0, 3). + AddItem(input, 0, 0, 1, 3, 0, 0, false). + AddItem(list, 1, 0, 1, 3, 0, 0, false) + + err = tview.NewApplication(). + SetRoot(grid, true). + SetFocus(input). + Run() + + return err +} + +func importDict(ctx context.Context, name string) error { + db, err := Open(memory) + if err != nil { + return err + } + err = db.Migrate(ctx) + if err != nil { + return err + } + + file, err := os.Open("dict.txt") + if err != nil { + return err + } + defer file.Close() + + count := 0 + total, err := LineCounter(file) + if err != nil { + return err + } + + _, err = file.Seek(0, 0) + if err != nil { + return err + } + + scanner := bufio.NewScanner(file) + for scanner.Scan() { + if strings.HasPrefix(scanner.Text(), "#") || scanner.Text() == "" { + continue + } + + if err := db.InsertLine(ctx, scanner.Text()); err != nil { + return err + } + count++ + + if (count % 1234) == 0 { + fmt.Print("\033[G\033[K") // move the cursor left and clear the line + per := math.Ceil((float64(count) / float64(total)) * 100.0) + fmt.Printf("%d/%d (%.0f%%)", count, total, per) + } + } + + fmt.Printf("Consolidating") + err = db.Consolidade(ctx) + if err != nil { + return err + } + + err = db.Backup(ctx, name) + if err != nil { + return err + } + return nil +} + +func LineCounter(r io.Reader) (int, error) { + var count int + const lineBreak = '\n' + + buf := make([]byte, bufio.MaxScanTokenSize) + + for { + bufferSize, err := r.Read(buf) + if err != nil && err != io.EOF { + return 0, err + } + + var buffPosition int + for { + i := bytes.IndexByte(buf[buffPosition:], lineBreak) + if i == -1 || bufferSize == buffPosition { + break + } + buffPosition += i + 1 + count++ + } + if err == io.EOF { + break + } + } + + return count, nil +} |