Merge branch 'feat/db' into refactor/boolean-not-ref-type

pull/11451/head
Tienson Qin 2024-08-03 15:10:53 +08:00
commit a85fcdb842
9 changed files with 95 additions and 78 deletions

View File

@ -264,8 +264,7 @@
(def property-common-schema-attrs (def property-common-schema-attrs
"Property :schema attributes common to all properties" "Property :schema attributes common to all properties"
[[:hide? {:optional true} :boolean] [[:hide? {:optional true} :boolean]])
[:description {:optional true} :string]])
(def internal-property (def internal-property
(vec (vec
@ -371,10 +370,7 @@
[:db/ident {:optional true} logseq-property-ident] [:db/ident {:optional true} logseq-property-ident]
[:block/title {:optional true} :string] [:block/title {:optional true} :string]
[:property.value/content {:optional true} [:or :string :double]] [:property.value/content {:optional true} [:or :string :double]]
[:block/closed-value-property {:optional true} [:set :int]] [:block/closed-value-property {:optional true} [:set :int]] ]
[:block/schema {:optional true}
[:map
[:description {:optional true} :string]]]]
(remove #(#{:block/title} (first %)) block-attrs) (remove #(#{:block/title} (first %)) block-attrs)
page-or-block-attrs))) page-or-block-attrs)))

View File

@ -150,6 +150,10 @@
:hide? true :hide? true
:view-context :page :view-context :page
:public? true}} :public? true}}
:logseq.property/description {:schema
{:type :default
:public? true}}
:logseq.property.table/sorting {:schema :logseq.property.table/sorting {:schema
{:type :coll {:type :coll
:hide? true :hide? true

View File

@ -21,7 +21,7 @@
(defn build-closed-value-block (defn build-closed-value-block
"Builds a closed value block to be transacted" "Builds a closed value block to be transacted"
[block-uuid block-value property {:keys [db-ident icon description]}] [block-uuid block-value property {:keys [db-ident icon]}]
(assert block-uuid (uuid? block-uuid)) (assert block-uuid (uuid? block-uuid))
(cond-> (cond->
(closed-value-new-block block-uuid block-value property) (closed-value-new-block block-uuid block-value property)
@ -31,9 +31,6 @@
icon icon
(assoc :logseq.property/icon icon) (assoc :logseq.property/icon icon)
description
(update :block/schema assoc :description description)
true true
sqlite-util/block-with-timestamps)) sqlite-util/block-with-timestamps))
@ -46,13 +43,13 @@
:ref-type? true}) :ref-type? true})
property-attributes)] property-attributes)]
(into [property-tx] (into [property-tx]
(map (fn [{:keys [db-ident value icon description uuid]}] (map (fn [{:keys [db-ident value icon uuid]}]
(cond-> (cond->
(build-closed-value-block (build-closed-value-block
uuid uuid
value value
property property
{:db-ident db-ident :icon icon :description description}) {:db-ident db-ident :icon icon})
true true
(assoc :block/order (db-order/gen-key)))) (assoc :block/order (db-order/gen-key))))
(:closed-values property))))) (:closed-values property)))))

View File

@ -82,34 +82,32 @@
(defn- property-with-values (defn- property-with-values
[db block] [db block]
(when (entity-plus/db-based-graph? db) (when (entity-plus/db-based-graph? db)
(let [block (d/entity db (:db/id block)) (let [block (d/entity db (:db/id block))]
block-properties (when (seq (:block/properties block)) (->> (:block/properties block)
(mapcat vals
(fn [[_property-id property-values]] (mapcat
(let [values (if (and (coll? property-values) (fn [property-values]
(map? (first property-values))) (let [values (->>
property-values (if (and (coll? property-values)
#{property-values}) (map? (first property-values)))
value-ids (when (every? map? values) property-values
(->> (map :db/id values) #{property-values})
(filter (fn [id] (or (int? id) (keyword? id)))))) (remove sqlite-util/page?))
value-blocks (->> value-ids (when (every? map? values)
(when (seq value-ids) (->> (map :db/id values)
(map (filter (fn [id] (or (int? id) (keyword? id))))))
(fn [id] (d/pull db '[*] id)) value-blocks (->>
value-ids)) (when (seq value-ids)
;; FIXME: why d/pull returns {:db/id db-ident} instead of {:db/id number-eid}? (map
(map (fn [block] (fn [id] (d/pull db '[*] id))
(let [from-property-id (get-in block [:logseq.property/created-from-property :db/id])] value-ids))
(if (keyword? from-property-id) ;; FIXME: why d/pull returns {:db/id db-ident} instead of {:db/id number-eid}?
(assoc-in block [:logseq.property/created-from-property :db/id] (:db/id (d/entity db from-property-id))) (keep (fn [block]
block))))) (let [from-property-id (get-in block [:logseq.property/created-from-property :db/id])]
page (when (seq values) (if (keyword? from-property-id)
(when-let [page-id (:db/id (:block/page (d/entity db (:db/id (first values)))))] (assoc-in block [:logseq.property/created-from-property :db/id] (:db/id (d/entity db from-property-id)))
(d/pull db '[*] page-id)))] block)))))]
(remove nil? (concat [page] value-blocks)))) value-blocks)))))))
(:block/properties block)))]
block-properties)))
(defn get-block-children-ids (defn get-block-children-ids
"Returns children UUIDs" "Returns children UUIDs"

View File

@ -397,32 +397,24 @@
(seq properties)))) (seq properties))))
(defn- build-closed-value-tx (defn- build-closed-value-tx
[db property resolved-value {:keys [id icon description] [db property resolved-value {:keys [id icon]}]
:or {description ""}}]
(let [block (when id (d/entity db [:block/uuid id])) (let [block (when id (d/entity db [:block/uuid id]))
block-id (or id (ldb/new-block-id)) block-id (or id (ldb/new-block-id))
icon (when-not (and (string? icon) (string/blank? icon)) icon) icon (when-not (and (string? icon) (string/blank? icon)) icon)
description (string/trim description)
description (when-not (string/blank? description) description)
tx-data (if block tx-data (if block
[(let [schema (:block/schema block)] [(cond->
(cond-> (outliner-core/block-with-updated-at
(outliner-core/block-with-updated-at (merge
(merge {:block/uuid id
{:block/uuid id :block/closed-value-property (:db/id property)}
:block/closed-value-property (:db/id property) (if (db-property-type/original-value-ref-property-types (get-in property [:block/schema :type]))
:block/schema (if description {:property.value/content resolved-value}
(assoc schema :description description) {:block/title resolved-value})))
(dissoc schema :description))} icon
(if (db-property-type/original-value-ref-property-types (get-in property [:block/schema :type])) (assoc :logseq.property/icon icon))]
{:property.value/content resolved-value}
{:block/title resolved-value})))
icon
(assoc :logseq.property/icon icon)))]
(let [max-order (:block/order (last (:property/closed-values property))) (let [max-order (:block/order (last (:property/closed-values property)))
new-block (-> (db-property-build/build-closed-value-block block-id resolved-value new-block (-> (db-property-build/build-closed-value-block block-id resolved-value
property {:icon icon property {:icon icon})
:description description})
(assoc :block/order (db-order/gen-key max-order nil)))] (assoc :block/order (db-order/gen-key max-order nil)))]
[new-block [new-block
(outliner-core/block-with-updated-at (outliner-core/block-with-updated-at
@ -434,7 +426,7 @@
(defn upsert-closed-value! (defn upsert-closed-value!
"id should be a block UUID or nil" "id should be a block UUID or nil"
[conn property-id {:keys [id value] :as opts}] [conn property-id {:keys [id value description] :as opts}]
(assert (or (nil? id) (uuid? id))) (assert (or (nil? id) (uuid? id)))
(let [db @conn (let [db @conn
property (d/entity db property-id) property (d/entity db property-id)
@ -472,9 +464,20 @@
nil nil
:else :else
(ldb/transact! conn (let [tx-data (build-closed-value-tx @conn property resolved-value opts)]
(build-closed-value-tx @conn property resolved-value opts) (ldb/transact! conn tx-data {:outliner-op :save-block})
{:outliner-op :save-block}))))))
(when (seq description)
(if-let [desc-ent (and id (:logseq.property/description (d/entity db [:block/uuid id])))]
(ldb/transact! conn
[(outliner-core/block-with-updated-at {:db/id (:db/id desc-ent)
:block/title description})]
{:outliner-op :save-block})
(set-block-property! conn
;; new closed value is first in tx-data
[:block/uuid (or id (:block/uuid (first tx-data)))]
:logseq.property/description
description)))))))))
(defn add-existing-values-to-closed-values! (defn add-existing-values-to-closed-values!
"Adds existing values as closed values and returns their new block uuids" "Adds existing values as closed values and returns their new block uuids"

View File

@ -255,7 +255,7 @@
:description "choice 4"}) :description "choice 4"})
updated-b (d/entity @conn [:block/uuid (:block/uuid b)])] updated-b (d/entity @conn [:block/uuid (:block/uuid b)])]
(is (= 4 (db-property/closed-value-content updated-b))) (is (= 4 (db-property/closed-value-content updated-b)))
(is (= "choice 4" (:description (:block/schema updated-b)))))))) (is (= "choice 4" (db-property/property-value-content (:logseq.property/description updated-b))))))))
(deftest delete-closed-value! (deftest delete-closed-value!
(let [closed-value-uuid (random-uuid) (let [closed-value-uuid (random-uuid)

View File

@ -65,7 +65,7 @@
(cond-> {:block/title class-name (cond-> {:block/title class-name
:build/properties (cond-> {:url url} :build/properties (cond-> {:url url}
(class-m "rdfs:comment") (class-m "rdfs:comment")
(assoc :description (get-comment-string (class-m "rdfs:comment") renamed-pages)))} (assoc :logseq.property/description (get-comment-string (class-m "rdfs:comment") renamed-pages)))}
parent-class' parent-class'
(assoc :build/class-parent (keyword (strip-schema-prefix parent-class'))) (assoc :build/class-parent (keyword (strip-schema-prefix parent-class')))
(seq properties) (seq properties)
@ -117,12 +117,12 @@
schema (cond-> {:type schema-type} schema (cond-> {:type schema-type}
;; This cardinality rule should be adjusted as we use schema.org more ;; This cardinality rule should be adjusted as we use schema.org more
(= schema-type :node) (= schema-type :node)
(assoc :cardinality :many) (assoc :cardinality :many))]
(property-m "rdfs:comment")
(assoc :description (get-comment-string (property-m "rdfs:comment") renamed-pages)))]
{(keyword (strip-schema-prefix (property-m "@id"))) {(keyword (strip-schema-prefix (property-m "@id")))
(cond-> {:block/schema schema (cond-> {:block/schema schema
:build/properties {:url url}} :build/properties (cond-> {:url url}
(property-m "rdfs:comment")
(assoc :logseq.property/description (get-comment-string (property-m "rdfs:comment") renamed-pages)))}
(= schema-type :node) (= schema-type :node)
(assoc :build/schema-classes (mapv (comp keyword strip-schema-prefix) range-includes)))})) (assoc :build/schema-classes (mapv (comp keyword strip-schema-prefix) range-includes)))}))
@ -256,8 +256,13 @@
(get-schema-type (get-range-includes property-m) class-map))) (get-schema-type (get-range-includes property-m) class-map)))
frequencies) frequencies)
"\n")) "\n"))
(apply merge (assoc
(mapv #(->property-page % class-map options) select-properties))) (apply merge
(mapv #(->property-page % class-map options) select-properties))
;; Have to update schema for now as validation doesn't take into account existing properties
:logseq.property/description {:block/schema {:public? true :type :default}
:build/properties {:url "https://schema.org/description"
:logseq.property/description "A description of the item."}}))
(defn- get-all-classes-and-properties (defn- get-all-classes-and-properties
"Get all classes and properties from raw json file" "Get all classes and properties from raw json file"
@ -267,7 +272,8 @@
(if (string? type') [type'] type'))) (if (string? type') [type'] type')))
"rdfs:Class") "rdfs:Class")
schema-data) schema-data)
all-properties* (get-all-properties schema-data options) ;; Use built-in description
all-properties* (remove #(= "schema:description" (% "@id")) (get-all-properties schema-data options))
property-tuples (map #(vector (% "@id") :property) all-properties*) property-tuples (map #(vector (% "@id") :property) all-properties*)
class-tuples (map #(vector (% "@id") :class) all-classes*) class-tuples (map #(vector (% "@id") :class) all-classes*)
page-tuples (map #(vector (str "schema:" %) :node) existing-pages) page-tuples (map #(vector (str "schema:" %) :node) existing-pages)
@ -276,6 +282,7 @@
renamed-properties (detect-property-conflicts-and-get-renamed-properties renamed-properties (detect-property-conflicts-and-get-renamed-properties
property-tuples page-tuples options) property-tuples page-tuples options)
renamed-pages (merge renamed-classes renamed-properties) renamed-pages (merge renamed-classes renamed-properties)
;; Note: schema:description refs don't get renamed but they aren't used
;; Updates keys like @id, @subClassOf ;; Updates keys like @id, @subClassOf
rename-page-ids (fn [m] rename-page-ids (fn [m]
(w/postwalk (fn [x] (w/postwalk (fn [x]

View File

@ -238,6 +238,7 @@
db-mixins/query db-mixins/query
(rum/local nil ::property-name) (rum/local nil ::property-name)
(rum/local nil ::property-schema) (rum/local nil ::property-schema)
(rum/local nil ::property-description)
{:init (fn [state] {:init (fn [state]
(let [*values (atom :loading)] (let [*values (atom :loading)]
(p/let [result (db-async/<get-block-property-values (state/get-current-repo) (p/let [result (db-async/<get-block-property-values (state/get-current-repo)
@ -248,6 +249,7 @@
(let [[property _opts] (:rum/args state)] (let [[property _opts] (:rum/args state)]
(reset! (::property-name state) (:block/title property)) (reset! (::property-name state) (:block/title property))
(reset! (::property-schema state) (:block/schema property)) (reset! (::property-schema state) (:block/schema property))
(reset! (::property-description state) (db-property/property-value-content (:logseq.property/description property)))
(state/set-state! :editor/property-configure? true) (state/set-state! :editor/property-configure? true)
state)) state))
:will-unmount (fn [state] :will-unmount (fn [state]
@ -260,6 +262,7 @@
(when-not (= :loading values) (when-not (= :loading values)
(let [*property-name (::property-name state) (let [*property-name (::property-name state)
*property-schema (::property-schema state) *property-schema (::property-schema state)
*property-description (::property-description state)
property (db/sub-block (:db/id property)) property (db/sub-block (:db/id property))
built-in? (ldb/built-in? property) built-in? (ldb/built-in? property)
disabled? (or built-in? config/publishing?) disabled? (or built-in? config/publishing?)
@ -391,15 +394,24 @@
(swap! *property-schema assoc :hide? (not hide?)) (swap! *property-schema assoc :hide? (not hide?))
(save-property-fn))})]) (save-property-fn))})])
(let [description (or (:description @*property-schema) "")] (let [description (or @*property-description "")]
[:div.grid.grid-cols-5.gap-1.items-start.leading-8 [:div.grid.grid-cols-5.gap-1.items-start.leading-8
[:label.col-span-2 "Description:"] [:label.col-span-2 "Description:"]
[:div.col-span-3 [:div.col-span-3
[:div.mt-1 [:div.mt-1
(shui/textarea (shui/textarea
{:on-change (fn [e] {:on-change (fn [e]
(swap! *property-schema assoc :description (util/evalue e))) (reset! *property-description (util/evalue e)))
:on-blur save-property-fn :on-blur (fn []
(if-let [ent (:logseq.property/description property)]
(db/transact! (state/get-current-repo)
[(outliner-core/block-with-updated-at
{:db/id (:db/id ent) :block/title @*property-description})]
{:outliner-op :save-block})
(db-property-handler/set-block-property!
(:db/id property)
:logseq.property/description
@*property-description)))
:disabled disabled? :disabled disabled?
:default-value description})]]])]])))) :default-value description})]]])]]))))
@ -716,7 +728,7 @@
[:div.flex.flex-1 [:div.flex.flex-1
(if (and (:class-schema? opts) (:page-configure? opts)) (if (and (:class-schema? opts) (:page-configure? opts))
[:div.property-description.text-sm.opacity-70 [:div.property-description.text-sm.opacity-70
(inline-text {} :markdown (get-in property [:block/schema :description]))] (inline-text {} :markdown (db-property/property-value-content (:logseq.property/description property)))]
[:div.property-value.flex.flex-1 [:div.property-value.flex.flex-1
(pv/property-value block property v opts)])]]])))) (pv/property-value block property v opts)])]]]))))

View File

@ -63,7 +63,7 @@
(let [block (second (:rum/args state)) (let [block (second (:rum/args state))
value (or (str (db-property/closed-value-content block)) "") value (or (str (db-property/closed-value-content block)) "")
icon (:logseq.property/icon block) icon (:logseq.property/icon block)
description (or (get-in block [:block/schema :description]) "")] description (or (db-property/property-value-content (:logseq.property/description block)) "")]
(assoc state (assoc state
::value (atom value) ::value (atom value)
::icon (atom icon) ::icon (atom icon)