0
Fork 0
mirror of https://github.com/penpot/penpot.git synced 2025-01-10 08:50:57 -05:00

Implement recent files (back and front).

This commit is contained in:
Andrey Antukh 2019-12-11 12:15:06 +01:00
parent 4dad6bef40
commit 44e120d382
6 changed files with 72 additions and 42 deletions

View file

@ -7,9 +7,11 @@
(ns uxbox.services.queries.project-files
(:require
[clojure.spec.alpha :as s]
[cuerdas.core :as str]
[promesa.core :as p]
[uxbox.db :as db]
[uxbox.services.queries :as sq]
[uxbox.services.util :as su]
[uxbox.util.blob :as blob]
[uxbox.util.spec :as us]))
@ -22,7 +24,7 @@
(s/def ::project-id ::us/uuid)
(s/def ::user ::us/uuid)
(def ^:private sql:generic-project-files
(su/defsql sql:generic-project-files
"select pf.*,
array_agg(pp.id) as pages
from project_files as pf
@ -31,21 +33,42 @@
left join project_pages as pp on (pf.id = pp.file_id)
where pu.user_id = $1
and pu.can_edit = true
group by pf.id
order by pf.created_at asc")
group by pf.id")
;; --- Query: Project Files
(def ^:private sql:project-files
(str "with files as (" sql:generic-project-files ")"
" select * from files where project_id = $2"))
(declare retrieve-recent-files)
(declare retrieve-project-files)
(s/def ::project-files
(s/keys :req-un [::user ::project-id]))
(s/keys :req-un [::user]
:opt-un [::project-id]))
(sq/defquery ::project-files
[{:keys [user project-id] :as params}]
(-> (db/query db/pool [sql:project-files user project-id])
[{:keys [project-id] :as params}]
(if (nil? project-id)
(retrieve-recent-files db/pool params)
(retrieve-project-files db/pool params)))
(def ^:private sql:project-files
(str "with files as (" sql:generic-project-files ")"
" select * from files where project_id = $2"
" order by created_at asc"))
(defn retrieve-project-files
[conn {:keys [user project-id]}]
(-> (db/query conn [sql:project-files user project-id])
(p/then' (partial mapv decode-row))))
(su/defsql sql:recent-files
"with files as (~{sql:generic-project-files})
select * from files
order by modified_at desc
limit $2")
(defn retrieve-recent-files
[conn {:keys [user]}]
(-> (db/query conn [sql:recent-files user 20])
(p/then' (partial mapv decode-row))))
;; --- Query: Project File (By ID)

View file

@ -10,6 +10,7 @@
[promesa.core :as p]
[uxbox.db :as db]
[uxbox.services.queries :as sq]
[uxbox.services.util :as su]
[uxbox.util.blob :as blob]
[uxbox.util.spec :as us]))
@ -24,33 +25,20 @@
;; --- Query: Projects
;; (def ^:private projects-sql
;; "select distinct on (p.id, p.created_at)
;; p.*,
;; array_agg(pg.id) over (
;; partition by p.id
;; order by pg.created_at
;; range between unbounded preceding and unbounded following
;; ) as pages
;; from projects as p
;; left join pages as pg
;; on (pg.project_id = p.id)
;; where p.user_id = $1
;; order by p.created_at asc")
(def ^:private projects-sql
(su/defsql sql:projects
"select p.*
from project_users as pu
inner join projects as p on (p.id = pu.project_id)
where pu.can_edit = true
and pu.user_id = $1;")
and pu.user_id = $1
order by p.created_at asc")
(s/def ::projects
(s/keys :req-un [::user]))
(sq/defquery ::projects
[{:keys [user] :as params}]
(-> (db/query db/pool [projects-sql user])
(-> (db/query db/pool [sql:projects user])
(p/then' (partial mapv decode-row))))
;; --- Helpers

View file

@ -7,6 +7,7 @@
(ns uxbox.services.util
(:require
[clojure.tools.logging :as log]
[cuerdas.core :as str]
[vertx.core :as vc]
[uxbox.core :refer [system]]
[uxbox.util.uuid :as uuid]
@ -24,6 +25,10 @@
;; (log/info "service" type "processed in" elapsed)
;; data))})
(defmacro defsql
[sym str]
`(def ~sym (str/istr ~str)))
(defn raise-not-found-if-nil
[v]
(if (nil? v)

View file

@ -36,7 +36,7 @@
(watch [this state s]
(swap! storage assoc :auth data)
(rx/of du/fetch-profile
(rt/navigate :dashboard/projects)))))
(rt/navigate :dashboard-projects)))))
(defn logged-in?
[v]

View file

@ -122,8 +122,9 @@
(ptk/reify ::fetch-files
ptk/WatchEvent
(watch [_ state stream]
(->> (rp/query :project-files {:project-id project-id})
(rx/map files-fetched)))))
(let [params (if (nil? project-id) {} {:project-id project-id})]
(->> (rp/query :project-files params)
(rx/map files-fetched))))))
;; --- Fetch File (by ID)
@ -247,3 +248,13 @@
(let [path-params {:file-id file-id}
query-params {:page-id (first page-ids)}]
(rx/of (rt/nav :workspace path-params query-params)))))))
(defn go-to-project
[id]
(s/assert (s/nilable ::us/uuid) id)
(ptk/reify ::go-to-project
ptk/WatchEvent
(watch [_ state stream]
(if (nil? id)
(rx/of (rt/nav :dashboard-projects {} {}))
(rx/of (rt/nav :dashboard-projects {} {:project-id (str id)}))))))

View file

@ -30,6 +30,7 @@
(def +ordering-options+
{:name "ds.ordering.by-name"
:modified "ds.ordering.by-last-update"
:created "ds.ordering.by-creation-date"})
;; --- Refs
@ -49,6 +50,7 @@
(case ordering
:name (cljs.core/sort-by :name files)
:created (reverse (cljs.core/sort-by :created-at files))
:modified (reverse (cljs.core/sort-by :modified-at files))
files))
(defn contains-term?
@ -65,8 +67,8 @@
;; --- Menu (Filter & Sort)
(mf/defc menu
[{:keys [opts files] :as props}]
(let [ordering (:order opts :created)
[{:keys [id opts files] :as props}]
(let [ordering (:order opts :modified)
filtering (:filter opts "")
on-term-change
@ -94,12 +96,14 @@
[:div
;; Sorting
;; TODO: convert to separate component?
[:span (tr "ds.ordering")]
[:select.input-select {:on-change on-order-change
:value (pr-str ordering)}
(for [[key value] (seq +ordering-options+)]
(let [key (pr-str key)]
[:option {:key key :value key} (tr value)]))]]
(when id
[:*
[:span (tr "ds.ordering")]
[:select.input-select {:on-change on-order-change
:value (pr-str ordering)}
(for [[key value] (seq +ordering-options+)]
(let [key (pr-str key)]
[:option {:key key :value key} (tr value)]))]])]
;; Search
;; TODO: convert to separate component?
@ -174,7 +178,7 @@
(mf/defc grid
[{:keys [opts files] :as props}]
(let [order (:order opts :created)
(let [order (:order opts :modified)
filter (:filter opts "")
files (->> files
(filter-by filter)
@ -217,8 +221,7 @@
[{:keys [id name selected?] :as props}]
(let [local (mf/use-state {})
editable? (not (nil? id))
on-click (fn [event]
(st/emit! (rt/nav :dashboard-projects {} {:project-id (str id)})))]
on-click #(st/emit! (udp/go-to-project id))]
[:li {:on-click on-click
;; :on-double-click on-double-click
:class-name (when selected? "current")}
@ -248,7 +251,7 @@
"new project +"]]
[:li {:style {:marginBottom "20px"}
:on-click #(st/emit! (rt/nav :dashboard/projects {} {}))
:on-click #(st/emit! (udp/go-to-project nil))
:class-name (when (nil? id) "current")}
[:span.element-title "Recent"]]
@ -273,7 +276,7 @@
(let [opts (mf/deref opts-iref)
files (mf/deref files-ref)]
[:*
[:& menu {:opts opts :files files}]
[:& menu {:id id :opts opts :files files}]
[:section.dashboard-grid.library
[:& grid {:id id :opts opts :files files}]]]))