handler.cljs 6.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201
  1. (ns frontend.handler
  2. (:require [cljs-bean.core :as bean]
  3. [electron.ipc :as ipc]
  4. [electron.listener :as el]
  5. [frontend.components.editor :as editor]
  6. [frontend.components.page :as page]
  7. [frontend.config :as config]
  8. [frontend.db :as db]
  9. [frontend.db-schema :as db-schema]
  10. [frontend.handler.common :as common-handler]
  11. [frontend.handler.events :as events]
  12. [frontend.handler.file :as file-handler]
  13. [frontend.handler.notification :as notification]
  14. [frontend.handler.page :as page-handler]
  15. [frontend.handler.repo :as repo-handler]
  16. [frontend.handler.ui :as ui-handler]
  17. [frontend.idb :as idb]
  18. [frontend.modules.instrumentation.core :as instrument]
  19. [frontend.modules.shortcut.core :as shortcut]
  20. [frontend.search :as search]
  21. [frontend.search.db :as search-db]
  22. [frontend.state :as state]
  23. [frontend.storage :as storage]
  24. [frontend.util :as util]
  25. [frontend.version :as version]
  26. [goog.object :as gobj]
  27. [lambdaisland.glogi :as log]
  28. [promesa.core :as p]
  29. [frontend.ui :as ui]
  30. [frontend.error :as error]))
  31. (defn set-global-error-notification!
  32. []
  33. (set! js/window.onerror
  34. (fn [message, source, lineno, colno, error]
  35. (when-not (error/ignored? message)
  36. (notification/show!
  37. (str "message=" message "\nsource=" source "\nlineno=" lineno "\ncolno=" colno "\nerror=" error)
  38. :error
  39. ;; Don't auto-hide
  40. false)))))
  41. (defn- watch-for-date!
  42. []
  43. (let [f (fn []
  44. (when-not (state/nfs-refreshing?)
  45. ;; Don't create the journal file until user writes something
  46. (repo-handler/create-today-journal! false))
  47. (when-let [repo (state/get-current-repo)]
  48. (when (and (search-db/empty? repo)
  49. (state/input-idle? repo))
  50. (search/rebuild-indices!))))]
  51. (f)
  52. (js/setInterval f 5000)))
  53. (defn store-schema!
  54. []
  55. (storage/set :db-schema (assoc db-schema/schema
  56. :db/version db-schema/version)))
  57. (defn- get-me-and-repos
  58. []
  59. (let [me (and js/window.user (bean/->clj js/window.user))
  60. logged? (:name me)
  61. repos (if logged?
  62. (:repos me)
  63. [{:url config/local-repo}])]
  64. {:me me
  65. :logged? logged?
  66. :repos repos}))
  67. (defn restore-and-setup!
  68. [me repos logged? old-db-schema]
  69. (let [interval (atom nil)
  70. inner-fn (fn []
  71. (when (and @interval js/window.pfs)
  72. (js/clearInterval @interval)
  73. (reset! interval nil)
  74. (-> (p/all (db/restore!
  75. (assoc me :repos repos)
  76. old-db-schema
  77. (fn [repo]
  78. (file-handler/restore-config! repo false)
  79. (ui-handler/add-style-if-exists!))))
  80. (p/then
  81. (fn []
  82. ;; install after config is restored
  83. (shortcut/refresh!)
  84. (cond
  85. (and (not logged?)
  86. (not (seq (db/get-files config/local-repo)))
  87. ;; Not native local directory
  88. (not (some config/local-db? (map :url repos))))
  89. (repo-handler/setup-local-repo-if-not-exists!)
  90. :else
  91. (state/set-db-restoring! false))
  92. (store-schema!)
  93. (state/pub-event! [:modal/nfs-ask-permission])
  94. (page-handler/init-commands!)
  95. (when (seq (:repos me))
  96. ;; FIXME: handle error
  97. (common-handler/request-app-tokens!
  98. (fn []
  99. (repo-handler/clone-and-pull-repos me))
  100. (fn []
  101. (js/console.error "Failed to request GitHub app tokens."))))
  102. (watch-for-date!)
  103. (file-handler/watch-for-local-dirs!)))
  104. (p/catch (fn [error]
  105. (log/error :db/restore-failed error))))))]
  106. ;; clear this interval
  107. (let [interval-id (js/setInterval inner-fn 50)]
  108. (reset! interval interval-id))))
  109. (defn- handle-connection-change
  110. [e]
  111. (let [online? (= (gobj/get e "type") "online")]
  112. (state/set-online! online?)))
  113. (defn set-network-watcher!
  114. []
  115. (js/window.addEventListener "online" handle-connection-change)
  116. (js/window.addEventListener "offline" handle-connection-change))
  117. (defn- get-repos
  118. []
  119. (let [logged? (state/logged?)
  120. me (state/get-me)]
  121. (p/let [nfs-dbs (idb/get-nfs-dbs)
  122. nfs-dbs (map (fn [db]
  123. {:url db :nfs? true}) nfs-dbs)]
  124. (cond
  125. logged?
  126. (concat
  127. nfs-dbs
  128. (:repos me))
  129. (seq nfs-dbs)
  130. nfs-dbs
  131. :else
  132. [{:url config/local-repo
  133. :example? true}]))))
  134. (defn on-load-events
  135. []
  136. (set! js/window.onload
  137. (fn []
  138. (instrument/init))))
  139. (defn clear-cache!
  140. []
  141. (p/let [_ (idb/clear-local-storage-and-idb!)
  142. _ (when (util/electron?)
  143. (ipc/ipc "clearCache"))]
  144. (js/setTimeout #(js/window.location.reload %) 3000)))
  145. (defn- register-components-fns!
  146. []
  147. (state/set-page-blocks-cp! page/page-blocks-cp)
  148. (state/set-editor-cp! editor/box))
  149. (defn start!
  150. [render]
  151. (set-global-error-notification!)
  152. (let [db-schema (storage/get :db-schema)
  153. {:keys [me logged? repos]} (get-me-and-repos)]
  154. (when me (state/set-state! :me me))
  155. (register-components-fns!)
  156. (state/set-db-restoring! true)
  157. (render)
  158. (on-load-events)
  159. (set-network-watcher!)
  160. (util/indexeddb-check?
  161. (fn [_error]
  162. (notification/show! "Sorry, it seems that your browser doesn't support IndexedDB, we recommend to use latest Chrome(Chromium) or Firefox(Non-private mode)." :error false)
  163. (state/set-indexedb-support! false)))
  164. (events/run!)
  165. (p/let [repos (get-repos)]
  166. (state/set-repos! repos)
  167. (restore-and-setup! me repos logged? db-schema))
  168. (reset! db/*sync-search-indice-f search/sync-search-indice!)
  169. (db/run-batch-txs!)
  170. (file-handler/run-writes-chan!)
  171. (when (util/electron?)
  172. (el/listen!))))
  173. (defn stop! []
  174. (prn "stop!"))