changelog shortlog graph tags branches changeset files file revisions raw help

Mercurial > demo / annotate examples/db/xdb/xdb.lisp

changeset 44: 99d4ab4f8d53
parent: 81b7333f27f8
author: Richard Westhaver <ellis@rwest.io>
date: Sun, 11 Aug 2024 01:50:18 -0400
permissions: -rw-r--r--
description: update
41
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
1
 (in-package :xdb)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
2
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
3
 ;;; XDB
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
4
 (defclass xdb ()
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
5
   ((location :initarg :location
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
6
              :accessor location
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
7
              :initform (required-argument "Location is required"))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
8
    (collections :initarg :collections
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
9
                 :accessor collections
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
10
                 :initform (make-hash-table :test 'equal))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
11
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
12
 (defclass dbs ()
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
13
   ((databases :initarg :databases
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
14
         :accessor databases
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
15
         :initform (make-hash-table :test 'equal))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
16
    (base-path :initarg :base-path
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
17
               :initform "/tmp/db/"
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
18
               :accessor base-path)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
19
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
20
 (defmethod get-db ((dbs dbs) name)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
21
   (gethash name (databases dbs)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
22
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
23
 (defun parse-db-path (path)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
24
   (make-pathname :directory
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
25
                  (list* :relative
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
26
                         (etypecase path
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
27
                           (cons path
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
28
                            path)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
29
                           (string path
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
30
                            (list path))))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
31
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
32
 (defmethod add-db ((dbs dbs) name &key base-path load-from-file-p)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
33
   (unless (gethash name (databases dbs))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
34
     (let* ((base-path (or base-path (base-path dbs)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
35
            (db-path (merge-pathnames (parse-db-path name) base-path))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
36
            (db (make-instance 'xdb :location db-path)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
37
       (ensure-directories-exist db-path)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
38
       (setf (gethash name (databases dbs)) db)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
39
       (if load-from-file-p
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
40
           (load-db db :load-from-file-p load-from-file-p)))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
41
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
42
 (defparameter *dbs* nil)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
43
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
44
 (defun dbs ()
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
45
   *dbs*)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
46
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
47
 (defmethod initialize-doc-container ((collection collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
48
   (setf (docs collection) (make-array 0 :adjustable t :fill-pointer 0)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
49
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
50
 (defmethod map-docs (result-type function (collection collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
51
                      &rest more-collections)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
52
   (let ((result
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
53
           (map result-type function (docs collection))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
54
     (loop for collection in more-collections
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
55
           for results = (map result-type function (docs collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
56
           if result-type
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
57
           do (setf result (concatenate result-type result results)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
58
     result))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
59
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
60
 (defmethod find-duplicate-doc ((collection collection) doc &key function)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
61
   (let ((test (or function #'duplicate-doc-p)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
62
     (map-docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
63
      nil
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
64
      (lambda (docx)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
65
        (when (funcall test doc docx)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
66
          (return-from find-duplicate-doc docx)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
67
      collection)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
68
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
69
 (defmethod add-doc ((collection collection) doc &key duplicate-doc-p-func)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
70
   (when doc
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
71
     (if duplicate-doc-p-func
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
72
         (let ((dup (find-duplicate-doc collection doc :function duplicate-doc-p-func)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
73
           (if (not dup)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
74
               (vector-push-extend doc (docs collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
75
               (setf dup doc) ;;doing this because
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
76
               ))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
77
         (vector-push-extend doc (docs collection)))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
78
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
79
 (defmethod store-doc ((collection collection) doc
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
80
                       &key (duplicate-doc-p-func #'duplicate-doc-p))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
81
   (let ((dup (and duplicate-doc-p-func
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
82
                   (find-duplicate-doc collection doc
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
83
                                       :function duplicate-doc-p-func))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
84
     ;; a document might be considered duplicate based on the data 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
85
     ;;contained and not its eql status as lisp object so we have to replace
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
86
     ;;it in the array with the new object effectively updating the data.
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
87
     (if dup
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
88
         (setf dup doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
89
         (vector-push-extend doc (docs collection)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
90
     (serialize-doc collection doc))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
91
   collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
92
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
93
 (defmethod serialize-doc ((collection collection) doc &key)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
94
   (let ((path (make-pathname :type "log" :defaults (db::path collection))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
95
     (ensure-directories-exist path)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
96
     (db::save-doc collection doc path))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
97
   doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
98
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
99
 (defmethod serialize-docs (collection &key duplicate-doc-p-func)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
100
   (map-docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
101
    nil
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
102
    (lambda (doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
103
      (store-doc collection doc
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
104
                 :duplicate-doc-p-func duplicate-doc-p-func))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
105
    collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
106
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
107
 (defmethod load-from-file ((collection collection) file)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
108
   (when (probe-file file)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
109
     (db::load-data collection file
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
110
                (lambda (object)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
111
                  (add-doc collection object)))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
112
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
113
 (defmethod get-collection ((db xdb) name)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
114
   (gethash name (collections db)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
115
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
116
 (defun make-new-collection (name db &key collection-class)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
117
   (let ((collection
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
118
          (make-instance collection-class
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
119
                          :name name
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
120
                          :path (merge-pathnames name (location db)))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
121
     (initialize-doc-container collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
122
     collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
123
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
124
 (defmethod add-collection ((db xdb) name
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
125
                            &key (collection-class 'collection) load-from-file-p)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
126
   (let ((collection (or (gethash name (collections db))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
127
                         (setf (gethash name (collections db))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
128
                               (make-new-collection name db
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
129
                                                    :collection-class collection-class)))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
130
     (ensure-directories-exist (db::path collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
131
     (when load-from-file-p
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
132
       (load-from-file collection
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
133
                       (make-pathname :defaults (db::path collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
134
                                      :type "snap"))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
135
       (load-from-file collection
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
136
                       (make-pathname :defaults (db::path collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
137
                                      :type "log")))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
138
     collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
139
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
140
 (defun append-date (name)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
141
   (format nil "~a-~a" name (file-date)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
142
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
143
 (defmethod snapshot ((collection collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
144
   (let* ((backup (merge-pathnames "backup/" (db::path collection)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
145
          (log (make-pathname :type "log" :defaults (db::path collection)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
146
          (snap (make-pathname :type "snap" :defaults (db::path collection)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
147
          (backup-name (append-date (db::name collection)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
148
          (log-backup (make-pathname :name backup-name
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
149
                                     :type "log"
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
150
                                     :defaults backup))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
151
          (snap-backup (make-pathname :name backup-name
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
152
                                      :type "snap"
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
153
                                      :defaults backup)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
154
     (ensure-directories-exist backup)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
155
     (when (probe-file snap)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
156
       (rename-file snap snap-backup))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
157
     (when (probe-file log)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
158
       (rename-file log log-backup))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
159
     (db::save-data collection snap)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
160
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
161
 (defmethod snapshot ((db xdb))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
162
   (maphash (lambda (key value)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
163
              (declare (ignore key))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
164
              (snapshot value))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
165
            (collections db)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
166
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
167
 (defmethod load-db ((db xdb) &key load-from-file-p)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
168
   (let ((unique-collections (make-hash-table :test 'equal)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
169
     (dolist (path (directory (format nil "~A/*.*" (location db))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
170
       (when (pathname-name path)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
171
         (setf (gethash (pathname-name path) unique-collections)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
172
               (pathname-name path))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
173
     (maphash  #'(lambda (key value)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
174
                   (declare (ignore key))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
175
                   (add-collection db value :load-from-file-p load-from-file-p))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
176
               unique-collections)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
177
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
178
 (defmethod get-docs ((db xdb) collection-name &key return-type)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
179
   (let ((col (gethash collection-name (collections db))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
180
     (if return-type
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
181
         (coerce return-type
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
182
                 (docs col))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
183
         (docs col))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
184
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
185
 (defmethod get-doc (collection value  &key (element 'key) (test #'equal))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
186
   (map-docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
187
          nil
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
188
          (lambda (doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
189
            (when (funcall test (get-val doc element) value)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
190
              (return-from get-doc doc)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
191
          collection))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
192
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
193
 (defmethod get-doc-complex (test element value collection &rest more-collections)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
194
   (apply #'map-docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
195
          nil
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
196
          (lambda (doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
197
            (when (apply test (list (get-val doc element) value))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
198
              (return-from get-doc-complex doc)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
199
          collection
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
200
          more-collections))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
201
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
202
 (defmethod find-doc (collection &key test)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
203
   (if test
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
204
       (map-docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
205
        nil
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
206
        (lambda (doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
207
          (when (funcall test doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
208
            (return-from find-doc doc)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
209
        collection)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
210
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
211
 (defmethod find-doc-complex (test collection &rest more-collections)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
212
   (apply #'map-docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
213
          (lambda (doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
214
            (when (funcall test doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
215
              (return-from find-doc-complex doc)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
216
          collection
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
217
          (cdr more-collections)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
218
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
219
 (defmethod find-docs (return-type test collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
220
   (coerce (loop for doc across (docs collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
221
                 when (funcall test doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
222
                 collect doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
223
           return-type))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
224
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
225
 (defclass union-docs ()
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
226
   ((docs :initarg :docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
227
          :accessor :docs)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
228
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
229
 (defmethod union-collection (return-type (collection collection) &rest more-collections)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
230
   (make-instance
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
231
    'union-docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
232
    :docs (apply #'map-docs (list return-type collection more-collections))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
233
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
234
 (defclass join-docs ()
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
235
   ((docs :initarg :docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
236
           :accessor :docs)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
237
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
238
 (defclass join-result ()
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
239
   ((docs :initarg :docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
240
           :accessor :docs)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
241
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
242
 (defun sort-key (doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
243
   (get-val doc 'key))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
244
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
245
 ;; TODO: How to update log if collection is sorted? Make a snapshot?
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
246
 (defmethod sort-collection ((collection collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
247
                             &key return-sort
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
248
                             (sort-value-func #'sort-key) (sort-test-func  #'>))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
249
   (setf (docs collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
250
         (sort (docs collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
251
               sort-test-func
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
252
               :key sort-value-func))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
253
   (if return-sort
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
254
       (docs collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
255
       t))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
256
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
257
 (defmethod db::sort-collection-temporary ((collection collection)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
258
                             &key (sort-value-func #'sort-key) (sort-test-func  #'>))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
259
   (let ((sorted-array (copy-array (docs collection))))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
260
    (setf sorted-array
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
261
          (sort sorted-array
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
262
                sort-test-func
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
263
                :key sort-value-func))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
264
    sorted-array))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
265
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
266
 (defun sort-docs (docs &key (sort-value-func #'sort-key) (sort-test-func  #'>))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
267
   :documentation "Sorts array/list of docs and returns the sorted array."
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
268
   (sort docs
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
269
         sort-test-func
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
270
         :key sort-value-func))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
271
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
272
 ;;Add method for validation when updating a collection.
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
273
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
274
 (defclass xdb-sequence ()
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
275
   ((key :initarg :key
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
276
          :accessor key)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
277
    (value :initarg :value
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
278
           :accessor value)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
279
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
280
 (defmethod enable-sequences ((xdb xdb))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
281
   (add-collection xdb "sequences" 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
282
                 :collection-class 'collection
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
283
                 :load-from-file-p t))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
284
 
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
285
 (defmethod next-sequence ((xdb xdb) key)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
286
   (let ((doc (get-doc (get-collection xdb "sequences") key)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
287
     (unless doc
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
288
       (setf doc (make-instance 'xdb-sequence :key key :value 0)))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
289
     (incf (get-val doc 'value))
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
290
     (store-doc (get-collection xdb "sequences")
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
291
                 doc)
81b7333f27f8 more examples
Richard Westhaver <ellis@rwest.io>
parents:
diff changeset
292
     (get-val doc 'value)))