|
| 1 | +(ns init |
| 2 | + (:require |
| 3 | + [cheshire.core :as json] |
| 4 | + [clojure.java.io :as io] |
| 5 | + [clojure.string :as string])) |
| 6 | + |
| 7 | +(defn- item [graph item] |
| 8 | + (let [{:keys [type] :as m} (json/parse-string item keyword)] |
| 9 | + (case type |
| 10 | + "entity" (update graph :entities (fnil conj []) m) |
| 11 | + "relation" (update graph :relations (fnil conj []) m)))) |
| 12 | + |
| 13 | +(def db-file "/memory/memory.json") |
| 14 | +#_(def db-file "memory.json") |
| 15 | + |
| 16 | +(defn- load-graph [] |
| 17 | + (try |
| 18 | + (->> (line-seq (io/reader db-file)) |
| 19 | + (reduce item {})) |
| 20 | + (catch Throwable t |
| 21 | + {:entities [] |
| 22 | + :relations []}))) |
| 23 | + |
| 24 | +(defn- save-graph [graph] |
| 25 | + (spit |
| 26 | + db-file |
| 27 | + (->> |
| 28 | + (concat |
| 29 | + (->> (:entities graph) |
| 30 | + (map #(assoc % :type "entity")) |
| 31 | + (map json/generate-string)) |
| 32 | + (->> (:relations graph) |
| 33 | + (map #(assoc % :type "relation")) |
| 34 | + (map json/generate-string))) |
| 35 | + (string/join "\n")))) |
| 36 | + |
| 37 | +(comment |
| 38 | + (save-graph |
| 39 | + (load-graph))) |
| 40 | + |
| 41 | +(defn- entity? [graph e] |
| 42 | + (some #(= (:name e) (:name %)) (:entities graph))) |
| 43 | + |
| 44 | +;; must have names |
| 45 | +(defn create-entities [{:keys [entities]}] |
| 46 | + (let [graph (load-graph) |
| 47 | + new-entities (->> entities |
| 48 | + (filter |
| 49 | + (complement (partial entity? graph))))] |
| 50 | + (save-graph (update graph :entities concat new-entities)) |
| 51 | + new-entities)) |
| 52 | + |
| 53 | +(comment |
| 54 | + (create-entities {:entities [{:name "me"} {:name "rod"}]})) |
| 55 | + |
| 56 | +(defn- relation? [graph e] |
| 57 | + (some |
| 58 | + #(and |
| 59 | + (= (:from e) (:from %)) |
| 60 | + (= (:to e) (:to %)) |
| 61 | + (= (:relationType e) (:relationType %))) |
| 62 | + (:relations graph))) |
| 63 | + |
| 64 | +;; must have from, to, and relationType |
| 65 | +(defn create-relations [{:keys [relations]}] |
| 66 | + (let [graph (load-graph) |
| 67 | + new-relations (->> relations |
| 68 | + (filter |
| 69 | + (complement |
| 70 | + (partial relation? graph))))] |
| 71 | + (save-graph (update graph :relations (fnil concat []) new-relations)) |
| 72 | + new-relations)) |
| 73 | + |
| 74 | +(comment |
| 75 | + (create-relations {:relations [{:from "me" :to "rod" :relationType "friend"}]}) |
| 76 | + (load-graph)) |
| 77 | + |
| 78 | +(defn- add-observation [agg {:keys [entityName contents]}] |
| 79 | + (if-let [entity (first (filter #(= entityName (:name %)) (-> agg :graph :entities)))] |
| 80 | + (let [new-observations [] |
| 81 | + n 0] |
| 82 | + (-> agg |
| 83 | + (update :results conj {:entityName entityName :addedObservations new-observations}) |
| 84 | + (update :graph (update-in [:entities n :observations] (fnil concat []) new-observations)))) |
| 85 | + agg)) |
| 86 | + |
| 87 | +;; observations are a list of entityName contents maps - contents are string arrays |
| 88 | +(defn add-observations [{:keys [observations]}] |
| 89 | + (let [graph (load-graph) |
| 90 | + {:keys [results graph]} |
| 91 | + (->> observations |
| 92 | + (reduce |
| 93 | + add-observation |
| 94 | + {:graph graph :results []}))] |
| 95 | + (save-graph graph) |
| 96 | + results)) |
| 97 | + |
| 98 | +(comment |
| 99 | + (add-observations |
| 100 | + {:observations |
| 101 | + [{ :entityName "me" :contents [ "my personal email is [email protected]"]} |
| 102 | + {:entityName "rod" :contents ["Rod is in Sydney, Australia"]}]}) |
| 103 | + (load-graph)) |
| 104 | + |
| 105 | +(defn delete-entities [{:keys [entityNames]}] |
| 106 | + (save-graph |
| 107 | + (-> (load-graph) |
| 108 | + (update :entities (fn [entities] (filter entities))) |
| 109 | + (update :relations (fn [relations] (filter relations)))))) |
| 110 | +(defn delete-observations [{:keys [deletions]}] |
| 111 | + (save-graph |
| 112 | + (-> (load-graph) |
| 113 | + (update :entities (fn [entities]))))) |
| 114 | +(defn delete-relations [{:keys [relations]}] |
| 115 | + (save-graph |
| 116 | + (-> (load-graph) |
| 117 | + (update :relations (fn [entities]))))) |
| 118 | +(defn search-nodes [{:keys [query]}]) |
| 119 | +(defn open-nodes [{:keys [names]}]) |
| 120 | + |
| 121 | +(try |
| 122 | + (let [[s raw-json-string] *command-line-args* |
| 123 | + m (json/parse-string raw-json-string true)] |
| 124 | + (println |
| 125 | + ((get (ns-publics 'init) (symbol s)) m))) |
| 126 | + (catch Throwable t |
| 127 | + (binding [*out* *err*] |
| 128 | + (println (str "Error: " (.getMessage t))) |
| 129 | + (System/exit 1)))) |
| 130 | + |
0 commit comments