diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..aaec576 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,36 @@ +FROM --platform=linux/amd64 golang:alpine AS build + +RUN apk add git sqlite sqlite-dev build-base build-base + +WORKDIR /src/ + +COPY go.* /src/ + +RUN go mod download -x + +COPY . /src + +#Compiler Settings +ENV CGO_ENABLED=1 + +# for full parings check out https://go.dev/doc/install/source#environment +ENV GOOS=linux +# this will be the target cpu arch +# Can be amd64 arm64 386 ppc64 +ENV GOARCH=amd64 + +RUN go build -o /out/app -tags "fts5" . + +# if you need certificates use: alpine +# otherwise just use: scratch +FROM alpine AS run + +RUN apk add build-base + +COPY --from=build /out/app / + +ENV MARK_STORE_LOCATION=/data +# if needed +EXPOSE 1995 + +ENTRYPOINT [ "/app", "search"] diff --git a/cmd/web-search.go b/cmd/web-search.go index 10e49ac..5db339a 100644 --- a/cmd/web-search.go +++ b/cmd/web-search.go @@ -114,6 +114,7 @@ var searchCmd = &cobra.Command{ log.Println(err.Error()) return } + go db.FSWatcher() http.Handle("/static/", http.StripPrefix("/static/", http.FileServer(http.FS(static.FS)))) http.HandleFunc("/search", func(w http.ResponseWriter, r *http.Request) { diff --git a/go.mod b/go.mod index 233370d..09d22a0 100644 --- a/go.mod +++ b/go.mod @@ -4,16 +4,17 @@ go 1.23.0 require ( github.com/PuerkitoBio/goquery v1.9.2 + github.com/a-h/templ v0.3.960 github.com/charmbracelet/bubbles v0.21.0 github.com/charmbracelet/bubbletea v1.3.6 github.com/charmbracelet/huh v0.5.2 github.com/cli/browser v1.3.0 + github.com/fsnotify/fsnotify v1.9.0 github.com/mattn/go-sqlite3 v1.14.22 github.com/spf13/cobra v1.8.1 ) require ( - github.com/a-h/templ v0.3.960 // indirect github.com/charmbracelet/colorprofile v0.3.2 // indirect github.com/charmbracelet/x/cellbuf v0.0.13 // indirect ) @@ -23,11 +24,11 @@ require ( github.com/atotto/clipboard v0.1.4 // indirect github.com/aymanbagabas/go-osc52/v2 v2.0.1 // indirect github.com/catppuccin/go v0.2.0 // indirect - github.com/charmbracelet/lipgloss v1.1.0 // indirect + github.com/charmbracelet/lipgloss v1.1.0 github.com/charmbracelet/x/ansi v0.10.1 // indirect github.com/charmbracelet/x/exp/strings v0.0.0-20240722160745-212f7b056ed0 // indirect github.com/charmbracelet/x/input v0.1.3 // indirect - github.com/charmbracelet/x/term v0.2.1 // indirect + github.com/charmbracelet/x/term v0.2.1 github.com/charmbracelet/x/windows v0.1.2 // indirect github.com/dustin/go-humanize v1.0.1 // indirect github.com/erikgeiser/coninput v0.0.0-20211004153227-1c3628e74d0f // indirect @@ -36,12 +37,12 @@ require ( github.com/lucasb-eyer/go-colorful v1.2.0 // indirect github.com/mattn/go-isatty v0.0.20 // indirect github.com/mattn/go-localereader v0.0.1 // indirect - github.com/mattn/go-runewidth v0.0.16 // indirect + github.com/mattn/go-runewidth v0.0.16 github.com/mitchellh/hashstructure/v2 v2.0.2 // indirect - github.com/muesli/ansi v0.0.0-20230316100256-276c6243b2f6 // indirect + github.com/muesli/ansi v0.0.0-20230316100256-276c6243b2f6 github.com/muesli/cancelreader v0.2.2 // indirect - github.com/muesli/reflow v0.3.0 // indirect - github.com/muesli/termenv v0.16.0 // indirect + github.com/muesli/reflow v0.3.0 + github.com/muesli/termenv v0.16.0 github.com/rivo/uniseg v0.4.7 // indirect github.com/sahilm/fuzzy v0.1.1 // indirect github.com/spf13/pflag v1.0.5 // indirect diff --git a/go.sum b/go.sum index 1641345..85f9ad2 100644 --- a/go.sum +++ b/go.sum @@ -59,6 +59,10 @@ github.com/dustin/go-humanize v1.0.1 h1:GzkhY7T5VNhEkwH0PVJgjz+fX1rhBrR7pRT3mDkp github.com/dustin/go-humanize v1.0.1/go.mod h1:Mu1zIs6XwVuF/gI1OepvI0qD18qycQx+mFykh5fBlto= github.com/erikgeiser/coninput v0.0.0-20211004153227-1c3628e74d0f h1:Y/CXytFA4m6baUTXGLOoWe4PQhGxaX0KpnayAqC48p4= github.com/erikgeiser/coninput v0.0.0-20211004153227-1c3628e74d0f/go.mod h1:vw97MGsxSvLiUE2X8qFplwetxpGLQrlU1Q9AUEIzCaM= +github.com/fsnotify/fsnotify v1.7.0 h1:8JEhPFa5W2WU7YfeZzPNqzMP6Lwt7L2715Ggo0nosvA= +github.com/fsnotify/fsnotify v1.7.0/go.mod h1:40Bi/Hjc2AVfZrqy+aj+yEI+/bRxZnMJyTJwOpGvigM= +github.com/fsnotify/fsnotify v1.9.0 h1:2Ml+OJNzbYCTzsxtv8vKSFD9PbJjmhYF14k/jKC7S9k= +github.com/fsnotify/fsnotify v1.9.0/go.mod h1:8jBTzvmWwFyi3Pb8djgCCO5IBqzKJ/Jwo8TRcHyHii0= github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8= diff --git a/http/api.go b/http/api.go index cdbfe55..3d053d3 100644 --- a/http/api.go +++ b/http/api.go @@ -49,6 +49,7 @@ func CreateBookmarkHandler(db *store.DB) http.Handler { } w.WriteHeader(http.StatusCreated) w.Write(fmt.Appendf([]byte{}, `{"id": %d}`, id)) + go db.SyncChanges() })) } @@ -70,6 +71,7 @@ func UpdateBookmarkHandler(db *store.DB) http.Handler { return } w.WriteHeader(http.StatusNoContent) + go db.SyncChanges() })) } diff --git a/store/database.go b/store/database.go index 0573abe..62ca1c5 100644 --- a/store/database.go +++ b/store/database.go @@ -10,7 +10,9 @@ import ( "path" "runtime" "strings" + "sync" + "github.com/fsnotify/fsnotify" "github.com/mattn/go-sqlite3" ) @@ -156,6 +158,14 @@ type DB struct { StoreLoc string ChangesStoreLoc string Hostname string + + syncLock sync.Mutex +} + +func (db *DB) SyncChanges() { + db.syncLock.Lock() + syncronizeLocalChangesToDisk(db, path.Join(db.ChangesStoreLoc, db.Hostname)) + db.syncLock.Unlock() } func (db *DB) Close() error { @@ -172,6 +182,29 @@ func (db *DB) Close() error { return db.DB.Close() } +func (db *DB) FSWatcher() { + watcher, err := fsnotify.NewWatcher() + if err != nil { + log.Println(err) + return + } + defer watcher.Close() + + watcher.Add(db.ChangesStoreLoc) + + for { + select { + case err := <-watcher.Errors: + fmt.Println("had error watching", err.Error()) + case event := <-watcher.Events: + if event.Has(fsnotify.Write) || event.Has(fsnotify.Rename) { + syncronizeFromHostsToDB(db, db.Hostname, db.ChangesStoreLoc) + log.Println("sync-event!") + } + } + } +} + func EnsureTables(db *DB, tables ...requirement) error { for _, table := range tables { _, err := db.Exec(table.definition)