debug_ui.cljs 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248
  1. (ns frontend.db.rtc.debug-ui
  2. "Debug UI for rtc module"
  3. (:require [fipp.edn :as fipp]
  4. [frontend.common.missionary-util :as c.m]
  5. [frontend.db :as db]
  6. [frontend.handler.user :as user]
  7. [frontend.persist-db.browser :as db-browser]
  8. [frontend.state :as state]
  9. [frontend.ui :as ui]
  10. [frontend.util :as util]
  11. [logseq.db :as ldb]
  12. [logseq.shui.ui :as shui]
  13. [missionary.core :as m]
  14. [promesa.core :as p]
  15. [rum.core :as rum]))
  16. (defonce debug-state (:rtc/state @state/state))
  17. (defonce rtc-log-flow (m/watch (:rtc/log @state/state)))
  18. (defn- stop
  19. []
  20. (let [^object worker @db-browser/*worker]
  21. (.rtc-stop2 worker))
  22. (reset! debug-state nil))
  23. (rum/defcs ^:large-vars/cleanup-todo rtc-debug-ui < rum/reactive
  24. (rum/local nil ::logs)
  25. (rum/local nil ::sub-log-canceler)
  26. {:will-mount (fn [state]
  27. (let [canceler
  28. (c.m/run-task
  29. (m/reduce
  30. (fn [logs log]
  31. (let [logs* (if log
  32. (take 10 (conj logs log))
  33. logs)]
  34. (reset! (get state ::logs) logs*)
  35. logs*))
  36. nil rtc-log-flow)
  37. ::sub-logs)]
  38. (reset! (get state ::sub-log-canceler) canceler)
  39. state))
  40. :will-unmount (fn [state]
  41. (when-let [canceler (some-> (get state ::sub-log-canceler) deref)]
  42. (canceler))
  43. state)}
  44. [state]
  45. (let [debug-state* (rum/react debug-state)
  46. rtc-logs @(get state ::logs)
  47. rtc-state (:rtc-state debug-state*)
  48. rtc-lock (:rtc-lock debug-state*)]
  49. [:div
  50. {:on-click (fn [^js e]
  51. (when-let [^js btn (.closest (.-target e) ".ui__button")]
  52. (.setAttribute btn "disabled" "true")
  53. (js/setTimeout #(.removeAttribute btn "disabled") 2000)))}
  54. [:div.flex.gap-2.flex-wrap.items-center.pb-3
  55. (shui/button
  56. {:size :sm
  57. :on-click (fn [_]
  58. (let [^object worker @db-browser/*worker]
  59. (p/let [result (.rtc-get-debug-state2 worker)
  60. new-state (ldb/read-transit-str result)]
  61. (swap! debug-state (fn [old] (merge old new-state))))))}
  62. (shui/tabler-icon "refresh") "state")
  63. (shui/button
  64. {:size :sm
  65. :on-click
  66. (fn [_]
  67. (let [token (state/get-auth-id-token)
  68. ^object worker @db-browser/*worker]
  69. (p/let [result (.rtc-get-graphs2 worker token)
  70. graph-list (ldb/read-transit-str result)]
  71. (swap! debug-state assoc
  72. :remote-graphs
  73. (map
  74. #(into {}
  75. (filter second
  76. (select-keys % [:graph-uuid :graph-name
  77. :graph-status
  78. :graph<->user-user-type
  79. :graph<->user-grant-by-user])))
  80. graph-list)))))}
  81. (shui/tabler-icon "download") "graph-list")
  82. (shui/button
  83. {:size :sm
  84. :on-click #(c.m/run-task
  85. (user/new-task--upload-user-avatar "TEST_AVATAR")
  86. :upload-test-avatar)}
  87. (shui/tabler-icon "upload") "upload-test-avatar")]
  88. [:div.pb-4
  89. [:pre.select-text
  90. (-> {:user-uuid (user/user-uuid)
  91. :graph (:graph-uuid debug-state*)
  92. :rtc-state rtc-state
  93. :rtc-logs rtc-logs
  94. :local-tx (:local-tx debug-state*)
  95. :pending-block-update-count (:unpushed-block-update-count debug-state*)
  96. :remote-graphs (:remote-graphs debug-state*)
  97. :online-users (:online-users debug-state*)
  98. :auto-push? (:auto-push? debug-state*)
  99. :current-page (state/get-current-page)
  100. :blocks-count (when-let [page (state/get-current-page)]
  101. (count (:block/_page (db/get-page page))))}
  102. (fipp/pprint {:width 20})
  103. with-out-str)]]
  104. (if (nil? rtc-lock)
  105. (shui/button
  106. {:variant :outline
  107. :class "text-green-rx-09 border-green-rx-10 hover:text-green-rx-10"
  108. :on-click (fn []
  109. (let [token (state/get-auth-id-token)
  110. ^object worker @db-browser/*worker]
  111. (.rtc-start2 worker (state/get-current-repo) token)))}
  112. (shui/tabler-icon "player-play") "start")
  113. [:div.my-2.flex
  114. [:div.mr-2 (ui/button (str "Toggle auto push updates("
  115. (if (:auto-push? debug-state*)
  116. "ON" "OFF")
  117. ")")
  118. {:on-click
  119. (fn []
  120. (let [^object worker @db-browser/*worker]
  121. (.rtc-toggle-auto-push worker (state/get-current-repo))))})]
  122. [:div (shui/button
  123. {:variant :outline
  124. :class "text-red-rx-09 border-red-rx-08 hover:text-red-rx-10"
  125. :size :sm
  126. :on-click (fn [] (stop))}
  127. (shui/tabler-icon "player-stop") "stop")]])
  128. (when (some? debug-state*)
  129. [:hr]
  130. [:div.flex.flex-row.items-center.gap-2
  131. (ui/button "grant graph access to"
  132. {:icon "award"
  133. :on-click (fn []
  134. (let [token (state/get-auth-id-token)
  135. user-uuid (some-> (:grant-access-to-user debug-state*) parse-uuid)
  136. user-email (when-not user-uuid (:grant-access-to-user debug-state*))]
  137. (when-let [graph-uuid (:graph-uuid debug-state*)]
  138. (let [^object worker @db-browser/*worker]
  139. (.rtc-grant-graph-access2 worker token graph-uuid
  140. (some-> user-uuid vector ldb/write-transit-str)
  141. (some-> user-email vector ldb/write-transit-str))))))})
  142. [:b "➡️"]
  143. [:input.form-input.my-2.py-1
  144. {:on-change (fn [e] (swap! debug-state assoc :grant-access-to-user (util/evalue e)))
  145. :on-focus (fn [e] (let [v (.-value (.-target e))]
  146. (when (= v "input email or user-uuid here")
  147. (set! (.-value (.-target e)) ""))))
  148. :placeholder "input email or user-uuid here"}]])
  149. [:hr.my-2]
  150. [:div.flex.flex-row.items-center.gap-2
  151. (ui/button (str "download graph to")
  152. {:icon "download"
  153. :class "mr-2"
  154. :on-click (fn []
  155. (when-let [graph-name (:download-graph-to-repo debug-state*)]
  156. (when-let [graph-uuid (:graph-uuid-to-download debug-state*)]
  157. (let [^object worker @db-browser/*worker]
  158. (prn :download-graph graph-uuid :to graph-name)
  159. (p/let [token (state/get-auth-id-token)
  160. download-info-uuid (.rtc-request-download-graph worker token graph-uuid)
  161. download-info-uuid (ldb/read-transit-str download-info-uuid)
  162. result (.rtc-wait-download-graph-info-ready
  163. worker token download-info-uuid graph-uuid 60000)
  164. {:keys [_download-info-uuid
  165. download-info-s3-url
  166. _download-info-tx-instant
  167. _download-info-t
  168. _download-info-created-at]
  169. :as result} (ldb/read-transit-str result)]
  170. (when (not= result :timeout)
  171. (assert (some? download-info-s3-url) result)
  172. (.rtc-download-graph-from-s3 worker graph-uuid graph-name download-info-s3-url)))))))})
  173. [:b "➡"]
  174. [:div.flex.flex-row.items-center.gap-2
  175. (shui/select
  176. {:on-value-change (fn [v]
  177. (some->> (parse-uuid v)
  178. str
  179. (swap! debug-state assoc :graph-uuid-to-download)))}
  180. (shui/select-trigger
  181. {:class "!px-2 !py-0 !h-8 border-gray-04"}
  182. (shui/select-value
  183. {:placeholder "Select a graph-uuid"}))
  184. (shui/select-content
  185. (shui/select-group
  186. (for [{:keys [graph-uuid graph-status]} (sort-by :graph-uuid (:remote-graphs debug-state*))]
  187. (shui/select-item {:value graph-uuid :disabled (some? graph-status)} graph-uuid)))))
  188. [:b "+"]
  189. [:input.form-input.my-2.py-1
  190. {:on-change (fn [e] (swap! debug-state assoc :download-graph-to-repo (util/evalue e)))
  191. :on-focus (fn [e] (let [v (.-value (.-target e))]
  192. (when (= v "repo name here")
  193. (set! (.-value (.-target e)) ""))))
  194. :placeholder "repo name here"}]]]
  195. [:div.flex.my-2.items-center.gap-2
  196. (ui/button (str "upload current repo")
  197. {:icon "upload"
  198. :on-click (fn []
  199. (let [repo (state/get-current-repo)
  200. token (state/get-auth-id-token)
  201. remote-graph-name (:upload-as-graph-name debug-state*)
  202. ^js worker @db-browser/*worker]
  203. (.rtc-async-upload-graph2 worker repo token remote-graph-name)))})
  204. [:b "➡️"]
  205. [:input.form-input.my-2.py-1.w-32
  206. {:on-change (fn [e] (swap! debug-state assoc :upload-as-graph-name (util/evalue e)))
  207. :on-focus (fn [e] (let [v (.-value (.-target e))]
  208. (when (= v "remote graph name here")
  209. (set! (.-value (.-target e)) ""))))
  210. :placeholder "remote graph name here"}]]
  211. [:div.pb-2.flex.flex-row.items-center.gap-2
  212. (ui/button (str "delete graph")
  213. {:icon "trash"
  214. :on-click (fn []
  215. (when-let [graph-uuid (:graph-uuid-to-delete debug-state*)]
  216. (let [token (state/get-auth-id-token)
  217. ^object worker @db-browser/*worker]
  218. (prn ::delete-graph graph-uuid)
  219. (.rtc-delete-graph2 worker token graph-uuid))))})
  220. (shui/select
  221. {:on-value-change (fn [v]
  222. (some->> (parse-uuid v)
  223. str
  224. (swap! debug-state assoc :graph-uuid-to-delete)))}
  225. (shui/select-trigger
  226. {:class "!px-2 !py-0 !h-8"}
  227. (shui/select-value
  228. {:placeholder "Select a graph-uuid"}))
  229. (shui/select-content
  230. (shui/select-group
  231. (for [{:keys [graph-uuid graph-status]} (:remote-graphs debug-state*)]
  232. (shui/select-item {:value graph-uuid :disabled (some? graph-status)} graph-uuid)))))]]))