persist_var.cljs 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107
  1. (ns frontend.util.persist-var
  2. (:require [frontend.config :as config]
  3. [frontend.state :as state]
  4. [frontend.fs :as fs]
  5. [frontend.util :as util]
  6. [cljs.reader :as reader]
  7. [promesa.core :as p]))
  8. (defn- load-path [location]
  9. (config/get-file-path (state/get-current-repo) (str config/app-name "/" location ".edn")))
  10. (defprotocol ILoad
  11. (-load [this])
  12. (-loaded? [this]))
  13. (defprotocol ISave
  14. (-save [this]))
  15. (defprotocol IResetValue
  16. (-reset-value! [this new graph]))
  17. (deftype PersistVar [*value location]
  18. IResetValue
  19. (-reset-value! [_ new graph]
  20. (reset! *value (assoc-in @*value [graph :value] new)))
  21. ILoad
  22. (-load [_]
  23. (if (config/demo-graph?)
  24. (p/resolved nil)
  25. (let [repo (state/get-current-repo)
  26. dir (config/get-repo-dir repo)
  27. path (load-path location)]
  28. (p/let [file-exists? (fs/file-exists? dir path)]
  29. (when file-exists?
  30. (-> (p/chain (fs/stat dir path)
  31. (fn [stat]
  32. (when stat
  33. (fs/read-file dir path)))
  34. (fn [content]
  35. (when (not-empty content)
  36. (try (cljs.reader/read-string content)
  37. (catch js/Error e
  38. (println (util/format "read persist-var failed: %s" (load-path location)))
  39. (js/console.dir e)))))
  40. (fn [value]
  41. (when (some? value)
  42. (swap! *value (fn [o]
  43. (-> o
  44. (assoc-in [repo :loaded?] true)
  45. (assoc-in [repo :value] value)))))))
  46. (p/catch (fn [e]
  47. (println (util/format "load persist-var failed: %s: %s" (load-path location) e))))))))))
  48. (-loaded? [_]
  49. (get-in @*value [(state/get-current-repo) :loaded?]))
  50. ISave
  51. (-save [_]
  52. (if (config/demo-graph?)
  53. (p/resolved nil)
  54. (let [path (load-path location)
  55. repo (state/get-current-repo)
  56. content (str (get-in @*value [repo :value]))
  57. dir (config/get-repo-dir repo)]
  58. (fs/write-file! repo dir path content {:skip-compare? true}))))
  59. IDeref
  60. (-deref [_this]
  61. (get-in @*value [(state/get-current-repo) :value]))
  62. IReset
  63. (-reset!
  64. ;; "Deprecated - use (.reset-value! o) instead."
  65. [_ new-value]
  66. (swap! *value (fn [_] (assoc-in @*value [(state/get-current-repo) :value] new-value))))
  67. IPrintWithWriter
  68. (-pr-writer [_ w _opts]
  69. (write-all w (str "#PersistVar[" @*value ", loc: " location "]"))))
  70. (def *all-persist-vars (atom []))
  71. (defn load-vars []
  72. (p/all (mapv -load @*all-persist-vars)))
  73. (defn persist-var
  74. "This var is stored at logseq/LOCATION.edn"
  75. [init-value location]
  76. (let [var (->PersistVar (atom {(state/get-current-repo)
  77. {:value init-value
  78. :loaded? false}})
  79. location)]
  80. (swap! *all-persist-vars conj var)
  81. var))
  82. (defn persist-save [v]
  83. {:pre [(satisfies? ISave v)]}
  84. (-save v))
  85. (comment
  86. (do
  87. (def bbb (persist-var 1 "aaa"))
  88. (-save bbb)
  89. ))