Uses cursors for simplicity, uses common grid bottom

This commit is contained in:
2023-10-23 23:46:01 -07:00
parent 84d6f455ff
commit 48347bb8c5
8 changed files with 98 additions and 90 deletions

View File

@@ -125,6 +125,15 @@
[] nil)) [] nil))
(defn synthetic-cursor [v prefix]
(let [internal-cursor (cursor v)]
(reify ICursor
(path [this]
(into prefix (path internal-cursor)))
(state [this]
(state internal-cursor)))))
(defn transact! [cursor f] (defn transact! [cursor f]
"Changes value beneath cursor by passing it to a single-argument "Changes value beneath cursor by passing it to a single-argument
function f. Old value will be passed as function argument. Function function f. Old value will be passed as function argument. Function

View File

@@ -248,7 +248,8 @@
(defn client-override* [override] (defn client-override* [override]
(com/data-grid-row (-> {:x-ref "p" (com/data-grid-row (-> {:x-ref "p"
:data-key "show" :data-key "show"
:x-data (hx/json {:show (boolean (not (:new? override)))})} :x-data (hx/json {:show (boolean (doto (not (fc/field-value (:new? override)))
println))})}
hx/alpine-mount-then-appear) hx/alpine-mount-then-appear)
(fc/with-field :db/id (fc/with-field :db/id
(com/hidden {:name (fc/field-name) (com/hidden {:name (fc/field-name)
@@ -378,19 +379,12 @@
:id "client-override-table"} :id "client-override-table"}
(fc/cursor-map (fc/cursor-map
#(client-override* %)) #(client-override* %))
(com/data-grid-row
{:class "new-row"} (com/data-grid-new-row {:colspan 3
(com/data-grid-cell {:colspan 3 :index (count (fc/field-value))
:class "bg-gray-100"} :hx-get (bidi/path-for ssr-routes/only-routes
[:div.flex.justify-center :admin-account-client-override-new)}
(com/a-button {:hx-get (bidi/path-for ssr-routes/only-routes "New override"))))
:admin-account-client-override-new)
:color :secondary
:hx-include "#edit-form"
:hx-vals (hiccup/raw "js:{index: countRows(\"#client-override-table\")}")
:hx-target "#edit-form .new-row"
:hx-swap "beforebegin"}
"New override")])))))
] ]
[:div [:div
@@ -401,14 +395,13 @@
"Save account")])]])])) "Save account")])]])]))
(defn new-client-override [{ {:keys [index]} :query-params}] (defn new-client-override [{ {:keys [index]} :query-params}]
(let [index (or index 0) (html-response
account {:account/client-overrides (conj (into [] (repeat index {})) (fc/start-form-with-prefix
{:db/id (str (java.util.UUID/randomUUID)) [:account/client-overrides (or index 0)]
:new? true})}] ;; TODO schema decode is not working {:db/id (str (java.util.UUID/randomUUID))
(html-response :new? true}
(fc/start-form account [] []
(fc/with-cursor (get-in fc/*current* [:account/client-overrides index]) (client-override* fc/*current*))))
(client-override* fc/*current*))))))
(defn account-edit-dialog [request] (defn account-edit-dialog [request]
(let [account (some-> request :route-params :db/id (#(dc/pull (dc/db conn) default-read %)))] (let [account (some-> request :route-params :db/id (#(dc/pull (dc/db conn) default-read %)))]

View File

@@ -543,31 +543,18 @@
:content-fn (some-fn :vendor/name #(pull-attr (dc/db conn) :vendor/name %))})])) :content-fn (some-fn :vendor/name #(pull-attr (dc/db conn) :vendor/name %))})]))
(fc/with-field :transaction-rule/accounts (fc/with-field :transaction-rule/accounts
(list (com/data-grid {:headers [(com/data-grid-header {} "Account")
(com/data-grid {:headers [(com/data-grid-header {} "Account") (com/data-grid-header {:class "w-32"} "Location")
(com/data-grid-header {:class "w-32"} "Location") (com/data-grid-header {:class "w-16"} "%")
(com/data-grid-header {:class "w-16"} "%") (com/data-grid-header {:class "w-16"})]
(com/data-grid-header {:class "w-16"})] :id "transaction-rule-account-table"}
:id "transaction-rule-account-table"} (fc/cursor-map #(transaction-rule-account-row* entity %))
(fc/cursor-map #(transaction-rule-account-row* entity %)) (com/data-grid-new-row {:colspan 4
(com/data-grid-row :hx-get (bidi/path-for ssr-routes/only-routes
{:class "new-row"} :admin-transaction-rule-new-account)
(com/data-grid-cell {:colspan 4 :index (count (fc/field-value))
:class "bg-gray-100"} :tr-params (hx/bind-alpine-vals {} {:client-id "clientId"})}
[:div.flex.justify-center "New account")))
(com/a-button {:hx-get (bidi/path-for ssr-routes/only-routes
:admin-transaction-rule-new-account)
:color :secondary
:hx-include "#edit-form"
:hx-ext "rename-params"
;; TODO
:hx-rename-params-ex (cheshire/generate-string {"transaction-rule/client" "client-id"
"index" "index"})
:hx-vals (hiccup/raw "js:{index: countRows(\"#transaction-rule-account-table\")}")
:hx-target "#edit-form .new-row"
:hx-swap "beforebegin"}
"New account")])))
(com/errors {:errors (fc/field-errors)})))
(fc/with-field :transaction-rule/transaction-approval-status (fc/with-field :transaction-rule/transaction-approval-status
(com/validated-field {:label "Approval status" (com/validated-field {:label "Approval status"
@@ -578,7 +565,6 @@
:size :small :size :small
:orientation :horizontal}))) :orientation :horizontal})))
;; TODO componentize
]] ]]
[:div [:div
[:div#form-errors (when (:errors fc/*form-errors*) [:div#form-errors (when (:errors fc/*form-errors*)
@@ -593,21 +579,21 @@
;; pull out the single field to swap ;; pull out the single field to swap
(defn new-account [{{:keys [client-id index]} :query-params}] (defn new-account [{{:keys [client-id index]} :query-params}]
(let [index (or index 0) ;; TODO schema decode is not working (html-response
transaction-rule {:transaction-rule/client (dc/pull (dc/db conn) '[:client/name :client/locations :db/id] (fc/start-form-with-prefix
client-id) [:transaction-rule/accounts (or index 0)]
:transaction-rule/accounts (conj (into [] (repeat index {} )) {:db/id (str (java.util.UUID/randomUUID))
{:db/id (str (java.util.UUID/randomUUID)) :transaction-rule-account/location "Shared"
:transaction-rule-account/location "Shared" :new? true}
:new? true})}] []
(html-response (transaction-rule-account-row*
(fc/start-form transaction-rule [] ;; TODO store a pointer to the "head " cursor for errors instead of nesting them
(fc/with-cursor (get-in fc/*current* [:transaction-rule/accounts index]) ;; makes it so you don't have to do this
(transaction-rule-account-row*
;; TODO store a pointer to the "head " cursor for errors instead of nesting them {:transaction-rule/client (dc/pull (dc/db conn) '[:client/name :client/locations :db/id]
;; makes it so you don't have to do this client-id)}
transaction-rule
fc/*current*)))))) fc/*current*))))
;; TODO check to see if it should be called "Shared" or "shared" for the value ;; TODO check to see if it should be called "Shared" or "shared" for the value

View File

@@ -59,6 +59,7 @@
(def data-grid-row data-grid/row-) (def data-grid-row data-grid/row-)
(def data-grid-cell data-grid/cell-) (def data-grid-cell data-grid/cell-)
(def data-grid-right-stack-cell data-grid/right-stack-cell-) (def data-grid-right-stack-cell data-grid/right-stack-cell-)
(def data-grid-new-row data-grid/new-row-)
(defn link [params & children] (defn link [params & children]
(into [:a (update params :class str " font-medium text-blue-600 dark:text-blue-500 hover:underline ")] (into [:a (update params :class str " font-medium text-blue-600 dark:text-blue-500 hover:underline ")]

View File

@@ -3,8 +3,10 @@
[auto-ap.ssr-routes :as ssr-routes] [auto-ap.ssr-routes :as ssr-routes]
[auto-ap.ssr.components.card :refer [content-card-]] [auto-ap.ssr.components.card :refer [content-card-]]
[auto-ap.ssr.components.paginator :refer [paginator-]] [auto-ap.ssr.components.paginator :refer [paginator-]]
[auto-ap.ssr.components.buttons :refer [a-button-]]
[bidi.bidi :as bidi] [bidi.bidi :as bidi]
[hiccup2.core :as hiccup])) [hiccup2.core :as hiccup]
[auto-ap.ssr.hx :as hx]))
(defn header- [params & rest] (defn header- [params & rest]
(into [:th.px-4.py-3 {:scope "col" :class (:class params) (into [:th.px-4.py-3 {:scope "col" :class (:class params)
@@ -103,3 +105,23 @@
[:div {:class "htmx-indicator absolute -translate-x-1/2 -translate-y-1/2 top-2/4 left-1/2 overflow-hidden w-full h-full"} [:div {:class "htmx-indicator absolute -translate-x-1/2 -translate-y-1/2 top-2/4 left-1/2 overflow-hidden w-full h-full"}
[:div {:class "flex items-center justify-center w-full h-full border border-gray-200 rounded-lg bg-gray-50 dark:bg-gray-800 dark:border-gray-700 bg-opacity-50" } [:div {:class "flex items-center justify-center w-full h-full border border-gray-200 rounded-lg bg-gray-50 dark:bg-gray-800 dark:border-gray-700 bg-opacity-50" }
[:div {:class "px-3 py-1 text-xs font-medium leading-none text-center text-blue-800 bg-blue-200 rounded-full animate-pulse dark:bg-blue-900 dark:text-blue-200"} "loading..."]]])]) [:div {:class "px-3 py-1 text-xs font-medium leading-none text-center text-blue-800 bg-blue-200 rounded-full animate-pulse dark:bg-blue-900 dark:text-blue-200"} "loading..."]]])])
(defn new-row- [{:keys [index colspan tr-params] :as params} & content]
(row-
(merge {:class "new-row"
:x-data (hx/json {:newRowIndex index})
}
tr-params)
(cell- {:colspan colspan
:class "bg-gray-100"}
[:div.flex.justify-center
(a-button- (merge
(dissoc params :index :colspan)
{
"@click" "$dispatch('newRow', {index: newRowIndex++})"
:color :secondary
:hx-trigger "newRow"
:hx-vals (hiccup/raw "js:{index: event.detail.index}")
:hx-target "closest .new-row"
:hx-swap "beforebegin"})
content)])))

View File

@@ -2,17 +2,26 @@
(:require [auto-ap.ssr.utils :refer [path->name2]] (:require [auto-ap.ssr.utils :refer [path->name2]]
[auto-ap.cursor :as cursor])) [auto-ap.cursor :as cursor]))
(def ^:dynamic *prefix* [])
(def ^:dynamic *form-data*) (def ^:dynamic *form-data*)
(def ^:dynamic *form-errors*) (def ^:dynamic *form-errors*)
(def ^:dynamic *prev-cursor* nil) (def ^:dynamic *prev-cursor* nil)
(def ^:dynamic *current* nil) (def ^:dynamic *current* nil)
(defmacro start-form [form-data errors & rest] (defmacro start-form [form-data errors & rest]
`(binding [*form-data* ~form-data `(binding [*form-data* ~form-data
*form-errors* (or ~errors {})] *form-errors* (or ~errors {})]
(binding [*current* (cursor/cursor *form-data*)] (binding [*current* (if (cursor/cursor? *form-data*)
*form-data*
(cursor/cursor *form-data*))]
~@rest))) ~@rest)))
(defmacro start-form-with-prefix [prefix form-data errors & rest]
`(binding [*prefix* ~prefix]
(start-form ~form-data ~errors ~@rest)))
(defmacro with-cursor [cursor & rest] (defmacro with-cursor [cursor & rest]
`(binding [*current* ~cursor] `(binding [*current* ~cursor]
~@rest)) ~@rest))
@@ -24,7 +33,7 @@
(defn field-name (defn field-name
([] (field-name *current*)) ([] (field-name *current*))
([cursor] ([cursor]
(apply path->name2 (cursor/path cursor)))) (apply path->name2 (into (or *prefix* []) (cursor/path cursor)))))
(defn field-value (defn field-value
([] (field-value *current*)) ([] (field-value *current*))

View File

@@ -32,9 +32,9 @@
"x-transition:leave-end" "opacity-0")) "x-transition:leave-end" "opacity-0"))
(defn alpine-mount-then-appear [{:keys [data-key] :as params}] (defn alpine-mount-then-appear [{:keys [data-key] :as params}]
(merge (-> {"x-data" (json {data-key false}) (merge (-> {:x-data (json {data-key false})
"x-init" (format "$nextTick(() => %s=true)" (name data-key)) :x-init (format "$nextTick(() => %s=true)" (name data-key))
"x-show" (name data-key)} :x-show (name data-key)}
alpine-appear alpine-appear
alpine-disappear) alpine-disappear)
(dissoc params :data-key))) (dissoc params :data-key)))

View File

@@ -323,19 +323,11 @@
(com/data-grid-header {} )] (com/data-grid-header {} )]
:id "client-table"} :id "client-table"}
(fc/cursor-map #(client-row* %)) (fc/cursor-map #(client-row* %))
(com/data-grid-row (com/data-grid-new-row {:colspan 2
{:class "new-row"} :index (count (fc/field-value))
(com/data-grid-cell {:colspan 2 :hx-get (bidi/path-for ssr-routes/only-routes
:class "bg-gray-100"} :user-client-new)}
[:div.flex.justify-center "Assign new client"))))]
(com/a-button {:hx-get (bidi/path-for ssr-routes/only-routes
:user-client-new)
:color :secondary
:hx-include "#edit-form"
:hx-vals (hiccup/raw "js:{index: countRows(\"#client-table\")}")
:hx-target "#edit-form .new-row"
:hx-swap "beforebegin"}
"New override")])))))]
[:div [:div
[:div [:div#form-errors (when (:errors fc/*form-errors*) [:div [:div#form-errors (when (:errors fc/*form-errors*)
[:span.error-content [:span.error-content
@@ -374,14 +366,10 @@
:headers {"hx-trigger" "modalopen"}))) :headers {"hx-trigger" "modalopen"})))
(defn new-client [{ {:keys [index]} :query-params}] (defn new-client [{ {:keys [index]} :query-params}]
(let [index (or index 0) (html-response
account {:user/clients (conj (into [] (repeat index {})) (fc/start-form-with-prefix [:user/clients (or index 0)] {:db/id nil
{:db/id nil :new? true} []
:new? true})}] ;; TODO schema decode is not working (client-row* fc/*current*))))
(html-response
(fc/start-form account []
(fc/with-cursor (get-in fc/*current* [:user/clients index])
(client-row* fc/*current*))))))
(def key->handler (def key->handler
(apply-middleware-to-all-handlers (apply-middleware-to-all-handlers