diff --git a/image_service.bb b/image_service.bb new file mode 100755 index 0000000..32dba7b --- /dev/null +++ b/image_service.bb @@ -0,0 +1,7 @@ +#!/usr/bin/env bb + +(ns image-service + (:require [image-service-cli.main])) + +(when (= *file* (System/getProperty "babashka.file")) + (apply image-service-cli.main/-main *command-line-args*)) diff --git a/src/image_service_cli/db.clj b/src/image_service_cli/db.clj new file mode 100644 index 0000000..abea397 --- /dev/null +++ b/src/image_service_cli/db.clj @@ -0,0 +1,22 @@ +(ns image-service-cli.db + (:import (java.time LocalDateTime) + (java.time.format DateTimeFormatter)) + (:require + [image-service-cli.config :refer [config]] + [pod.babashka.go-sqlite3 :as sql])) + +(defn init-db + "Wipes and creates new images table" + [path] + (sql/execute! path + ["drop table images;"]) + (sql/execute! path + ["create table if not exists images (path TEXT, created TEXT);"])) + +(defn insert-image [path & [created-date]] + (let [created-date (or created-date (LocalDateTime/now)) + fmt DateTimeFormatter/ISO_LOCAL_DATE_TIME + created-date-iso (.format created-date fmt) + db-path (:db-path config)] + (sql/execute! db-path + ["insert into images (path, created) values (?, ?);" path created-date-iso]))) diff --git a/src/image_service_cli/index.clj b/src/image_service_cli/index.clj index 2142e74..13a04d8 100644 --- a/src/image_service_cli/index.clj +++ b/src/image_service_cli/index.clj @@ -4,14 +4,15 @@ (:import (java.time LocalDateTime) (java.time.format DateTimeFormatter)) (:require - [pod.babashka.go-sqlite3 :as sqlite] - [babashka.fs :as fs] [image-service-cli.config :refer [config]] + [image-service-cli.db :as db] [babashka.process :refer [shell]] - [clojure.string :as str] - [com.travisshears.gum-utils :as utils])) + [clojure.string :as str])) -(defn s3-root-dirs [] +(defn s3-root-dirs + "Lists the root directories in S3 bucket. + ex return: (\"climbing-grades\" \"image-service-test\" \"micro_blog\" \"micro_blog_dev\" \"oblastle\" \"random\" \"sourcehut\" \"test\")" + [] (let [filter-for-dirs (fn [lines] (filter #(re-find #"^\s*PRE" %) lines)) extract-dir-name (fn [line] (let [match (re-find #"PRE ([^\/]+)" line)] @@ -26,8 +27,15 @@ (map extract-dir-name)))) (def s3-date-formatter (DateTimeFormatter/ofPattern "yyyy-MM-dd HH:mm:ss")) -(defn s3-list-dir [dir] - "List the contents of a directory in S3. Skipping nested directories" + +(defn s3-list-dir + "List the contents of a directory in S3. Skipping nested directories + ex return: ( + {:date + #object[java.time.LocalDateTime 0x3962768b \"2022-08-14T19:22:30\"], + :file-name \"random/russian_switchs.jpeg\"} + ..." + [dir] (as-> (shell {:out :string :extra-env {"AWS_PROFILE" (:aws-profile config)}} "aws s3 ls" (str "s3://" (:s3-bucket config) "/" (:s3-root config) dir "/")) x (:out x) @@ -38,22 +46,13 @@ (map #(list (LocalDateTime/parse (first %) s3-date-formatter) (second %)) x) (map #(hash-map :date (first %) :file-name (second %)) x))) -(defn init-db [path] - (sqlite/execute! path - ["drop table images;"]) - (sqlite/execute! path - ["create table if not exists images (path TEXT, created TEXT);"])) - -(defn save-to-db [db-path record] - (let [fmt DateTimeFormatter/ISO_LOCAL_DATE_TIME - formatted-date (-> record :date (.format fmt)) - file-name (record :file-name)] - (sqlite/execute! db-path - ["insert into images (path, created) values (?, ?);" file-name formatted-date]))) +(defn save-s3-file-to-db [img] + (db/insert-image (:file-name img) (:date img))) (defn run [] - (let [db-path (:db-path config)] - (init-db db-path) - (->> - (flatten (map image-service-cli.index/s3-list-dir (image-service-cli.index/s3-root-dirs))) - (map #(save-to-db db-path %))))) + (let [db-path (:db-path config) + images (->> (s3-root-dirs) (map s3-list-dir) (flatten))] + (println "Wiping image table") + (db/init-db db-path) + (printf "Found %d images\n" (count images)) + (map save-s3-file-to-db images))) diff --git a/src/image_service_cli/main.clj b/src/image_service_cli/main.clj index 230e3ae..a6cdb26 100644 --- a/src/image_service_cli/main.clj +++ b/src/image_service_cli/main.clj @@ -3,7 +3,8 @@ (:require [image-service-cli.index :as index] [image-service-cli.config :refer [config]] - [clojure.pprint :refer [pprint]] + [image-service-cli.db :as db] + [babashka.process :refer [shell]] [pod.babashka.go-sqlite3 :as sql] [cheshire.core :as json] [com.travisshears.gum-utils :as utils])) @@ -29,9 +30,17 @@ max-dimension (utils/prompt-for "Max dimension: ")] (printf "url: %s\n" (get-image-url (:path (utils/select items)) max-dimension)))) +(defn upload-action [file-path & [dir-from-cli]] + (let [dir (if (nil? dir-from-cli) + (utils/prompt-for "dir") + dir-from-cli)] + (printf "uploading file %s to dir %s\n" file-path dir) + (shell {:extra-env {"AWS_PROFILE" (:aws-profile config)}} "aws s3 cp " file-path (str "s3://" (:s3-bucket config) "/" (:s3-root config) dir "/")) + (db/insert-image (str dir "/" file-path)))) + (defn -main [& args] (case (first args) - ;; "upload" (create/run) + "upload" (apply upload-action (rest args)) "gen" (gen-url-action) - "index" (index/run) + "index" (dorun (index/run)) (println "Missing command. Try upload, ls, or index.")))