Coverage report: /home/ati/workspace/perec/persistence/transformer.lisp
Kind | Covered | All | % |
expression | 270 | 479 | 56.4 |
branch | 35 | 68 | 51.5 |
Key
Not instrumented
Conditionalized out
Executed
Not executed
Both branches taken
One branch taken
Neither branch taken
1
;; -*- mode: Lisp; Syntax: Common-Lisp; -*-
3
;;; Copyright (c) 2006 by the authors.
5
;;; See LICENCE for details.
12
(defun equaln (value-1 value-2 count)
17
(return-from equaln #f)))
20
(defcondition* slot-type-error (type-error)
22
:type persistent-effective-slot-definition))
24
(lambda (condition stream)
26
"~@<The value ~2I~:_~S ~I~_in slot ~A is not of type ~2I~_~S.~:>"
27
(type-error-datum condition)
28
(slot-definition-name (slot-of condition))
29
(type-error-expected-type condition)))))
31
(defmacro def-transformer-wrapper (name &body forms)
32
`(defun ,name (slot type function column-number)
33
(declare (ignorable slot type column-number))
36
(def-transformer-wrapper unbound-reader
37
(bind ((unbound-rdbms-value (iter (repeat column-number) (collect nil))))
38
(lambda (rdbms-values)
39
(if (equaln unbound-rdbms-value rdbms-values column-number)
41
(funcall function rdbms-values)))))
43
(def-transformer-wrapper non-unbound-reader
44
(lambda (rdbms-values)
45
(prog1-bind slot-value (funcall function rdbms-values)
46
(when (eq +unbound-slot-value+ slot-value)
48
(error 'unbound-slot :instance nil :name (slot-definition-name slot))
49
(error 'type-error :datum slot-value :expected-type type))))))
51
(def-transformer-wrapper unbound-writer
52
(bind ((unbound-rdbms-value (iter (repeat column-number) (collect nil))))
54
(if (eq +unbound-slot-value+ slot-value)
56
(funcall function slot-value)))))
58
(def-transformer-wrapper non-unbound-writer
60
(if (eq +unbound-slot-value+ slot-value)
62
(error 'unbound-slot :instance nil :name (slot-definition-name slot))
63
(error 'type-error :datum slot-value :expected-type type))
64
(funcall function slot-value))))
69
(def-transformer-wrapper null-reader
70
(bind ((nil-rdbms-value (iter (repeat column-number) (collect nil))))
71
(lambda (rdbms-values)
72
(if (equaln nil-rdbms-value rdbms-values column-number)
74
(funcall function rdbms-values)))))
76
(def-transformer-wrapper non-null-reader
77
(lambda (rdbms-values)
78
(prog1-bind slot-value (funcall function rdbms-values)
81
(error 'slot-type-error :slot slot :datum slot-value :expected-type type)
82
(error 'type-error :datum slot-value :expected-type type))))))
84
(def-transformer-wrapper null-writer
85
(bind ((nil-rdbms-value (iter (repeat column-number) (collect nil))))
88
(funcall function slot-value)
91
(def-transformer-wrapper non-null-writer
94
(funcall function slot-value)
96
(error 'slot-type-error :slot slot :datum slot-value :expected-type type)
97
(error 'type-error :datum slot-value :expected-type type)))))
102
(def-transformer-wrapper unbound-or-null-reader
103
(bind ((unbound-rdbms-value (iter (repeat column-number) (collect nil)))
104
(nil-rdbms-value (list* #t (cdr unbound-rdbms-value))))
105
(lambda (rdbms-values)
106
(cond ((equaln unbound-rdbms-value rdbms-values column-number)
107
+unbound-slot-value+)
108
((equaln nil-rdbms-value rdbms-values column-number)
110
(t (funcall function (cdr rdbms-values)))))))
112
(def-transformer-wrapper unbound-or-null-writer
113
(bind ((unbound-rdbms-value (iter (repeat column-number) (collect nil)))
114
(nil-rdbms-value (list* #t (cdr unbound-rdbms-value))))
116
(cond ((eq +unbound-slot-value+ slot-value)
120
(t (list* #t (funcall function slot-value)))))))
125
(defun base64->object-reader (rdbms-values)
126
(with-input-from-sequence (stream
127
(with-input-from-string (base64 (first rdbms-values))
128
(decode-base64-bytes base64)))
131
(defun object->base64-writer (slot-value)
133
(with-output-to-string (base64)
135
(with-output-to-sequence (stream)
136
(store slot-value stream))
142
(defun identity-reader (rdbms-values)
143
(first rdbms-values))
145
(defun identity-writer (slot-value)
151
(defun object->number-reader (rdbms-values)
152
(bind ((value (first rdbms-values)))
153
(if (typep value 'number)
155
(parse-number value))))
160
(defun object->integer-reader (rdbms-values)
161
(bind ((value (first rdbms-values)))
162
(if (typep value 'number)
164
(parse-integer value))))
169
(defun string->symbol-reader (rdbms-values)
170
(symbol-from-canonical-name (first rdbms-values)))
172
(defun symbol->string-writer (slot-value)
173
(list (canonical-symbol-name slot-value)))
178
(defun string->list-reader (rdbms-values)
179
(read-from-string (first rdbms-values)))
181
(defun list->string-writer (slot-value)
182
(list (write-to-string slot-value)))
187
(defun char->boolean-reader (rdbms-values)
188
(bind ((value (first rdbms-values)))
189
(cond ((eq #\t value) #t)
191
(t (error 'type-error :datum value :expected-type 'boolean)))))
193
(defun boolean->char-writer (slot-value)
198
(defun integer->boolean-reader (rdbms-values)
199
(bind ((value (first rdbms-values)))
200
(cond ((= 0 value) #t)
202
(t (error 'type-error :datum value :expected-type 'boolean)))))
204
(defun boolean->integer-writer (slot-value)
209
(defun string->boolean-reader (rdbms-values)
210
(bind ((value (first rdbms-values)))
211
(cond ((equal "t" value) #t)
212
((equal "f" value) #f)
213
(t (error 'type-error :datum value :expected-type 'boolean)))))
215
(defun boolean->string-writer (slot-value)
220
(defun object->boolean-reader (rdbms-values)
221
(bind ((value (first rdbms-values)))
222
(cond ((eq #t value) #t)
226
((and (typep value 'integer)
228
((and (typep value 'integer)
230
((equal "t" value) #t)
231
((equal "f" value) #f)
232
((equal "TRUE" value) #t)
233
((equal "FALSE" value) #f)
234
(t (error 'type-error :datum value :expected-type 'boolean)))))
239
(defun slot-definition-type-member-elements (type)
240
(cdr (if (eq 'member (first type))
243
:key #L(when (listp !1)
246
(defun integer->member-reader (type)
247
(bind ((member-elements (slot-definition-type-member-elements type)))
248
(lambda (rdbms-values)
249
(bind ((value (first rdbms-values)))
250
(aif (nth value member-elements)
252
(error 'type-error :datum value :expected-type type))))))
254
(defun member->integer-writer (type)
255
(bind ((member-elements (slot-definition-type-member-elements type)))
259
for value in member-elements
260
when (eq value slot-value)
261
do (return-from found (list i)))
262
(error 'type-error :datum slot-value :expected-type type)))))
264
(defun string->member-reader (type)
265
(bind ((member-elements (slot-definition-type-member-elements type)))
266
(lambda (rdbms-values)
267
(aprog1 (string->symbol-reader rdbms-values)
268
(assert (member it member-elements))))))
270
(defun member->string-writer (type)
271
(bind ((member-elements (slot-definition-type-member-elements type)))
273
(assert (member slot-value member-elements))
274
(symbol->string-writer slot-value))))
279
(defun string->local-time-reader (rdbms-values)
280
(bind ((*default-timezone* +utc-zone+))
281
(parse-timestring (first rdbms-values) :date-time-separator #\Space)))
283
(defun local-time->string-writer (slot-value)
285
(format-timestring slot-value :date-time-separator #\Space :use-zulu-p #f)))
287
(defun integer->local-time-reader (rdbms-values)
288
(local-time :universal (first rdbms-values) :timezone +utc-zone+))
290
(defun local-time->integer-writer (slot-value)
292
(universal-time slot-value)))
297
(defun object-reader (rdbms-values)
298
(load-instance (make-oid :id (first rdbms-values) :class-name (symbol-from-canonical-name (second rdbms-values)))
299
:skip-existence-check #t))
301
(defun object-writer (slot-value)
302
(oid-values slot-value))