Skip to content

Instantly share code, notes, and snippets.

@marianoguerra
Created October 19, 2015 12:54
Show Gist options
  • Save marianoguerra/f03913ea07c47d4e60a9 to your computer and use it in GitHub Desktop.
Save marianoguerra/f03913ea07c47d4e60a9 to your computer and use it in GitHub Desktop.
example of using on-next with datascript, trying to understand component composition and queries
(ns iorioui.core
(:require
[goog.dom :as gdom]
[om.next :as om :refer-macros [defui]]
[om.dom :as dom]
[com.rpl.specter :as s]
[datascript.core :as d]
[cljs-http.client :as http]
[cljs.core.async :refer [<! >! put! chan]])
(:require-macros
[cljs.core.async.macros :refer [go]]))
(enable-console-print!)
(def conn (d/create-conn {}))
(d/transact! conn [{:db/id -1
:app/title "Hello, DataScript!"
:app/count 0}])
(defmulti read om/dispatch)
(defmethod read :app/count
[{:keys [state selector]} _ _]
{:value (d/q '[:find [(pull ?e ?selector) ...]
:in $ ?selector
:where [?e :app/title]]
(d/db state) selector)})
(defmulti mutate om/dispatch)
(defmethod mutate 'app/increment
[{:keys [state]} _ entity]
{:action (fn [] (d/transact! state
[(update-in entity [:app/count] inc)]))})
(defn navbar [title]
(dom/nav #js {:className "navbar navbar-inverse navbar-fixed-top"}
(dom/div #js {:className "navbar-header"}
(dom/a #js {:className "navbar-brand" :href "#"}
title))))
(defn bs-col-class [props]
(let [{:keys [sm md lg sm-offset md-offset lg-offset class]} props]
(str (when sm (str "col-sm-" sm))
(when md (str " col-md-" md))
(when lg (str " col-lg-" lg))
(when sm-offset (str " col-sm-offset-" sm-offset))
(when md-offset (str " col-md-offset-" md-offset))
(when lg-offset (str " col-lg-offset-" lg-offset))
(when class (str " " class)))))
(defn bs-col [props & childs]
(dom/div #js {:className (bs-col-class props)} childs))
(defn sidebar-link [{:keys [active url content]}]
(dom/li #js {:className (if active "active" "")}
(dom/a #js {:href (if url url "#")}
content)))
(defn sidebar [items]
(bs-col {:sm 3 :md 2 :class "sidebar"}
(dom/ul #js {:className "nav nav-sidebar"}
(map sidebar-link items))))
(defn page-header [title]
(dom/h1 #js {:className "page-header"} title))
(defn page [title & content]
(bs-col {:sm 9 :sm-offset 3 :md 10 :md-offset 2 :class "main"}
(page-header title)
content))
(defn container-fluid [& items]
(dom/div #js {:className "contaner-fluid"} items))
(defn bs-row [& items]
(dom/div #js {:className "row"} items))
(defui Counter
static om/IQuery
(query [this]
[{:app/count [:db/id :app/title :app/count]}])
Object
(render [this]
(let [{:keys [app/title app/count] :as entity}
(get-in (om/props this) [:app/count 0])]
(dom/div nil
(dom/h2 nil title)
(dom/span nil (str "Count: " count))
(dom/button
#js {:onClick
(fn [e]
(om/transact! this
`[(app/increment ~entity)]))}
"Click me!")))))
(def counter (om/factory Counter))
(defui App
static om/IQuery
(query [this]
(let [subquery (om/get-query Counter)]
subquery))
Object
(render [this]
(let [sub1 (om/props this)]
(container-fluid
(bs-row
(navbar "IorioDB")
(sidebar [{:active true :content "Users"}
{:content "Groups"}
{:content "Permissions"}])
(page "Users"
(counter sub1)
(counter sub1)))))))
(def reconciler
(om/reconciler
{:state conn
:parser (om/parser {:read read :mutate mutate})}))
(om/add-root! reconciler
App (gdom/getElement "main-app-area"))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment