Browse code
Jsonifier: conver key/line pairs to arrays of json objects
Ed Langley authored on 06/08/2018 17:53:21
Showing 4 changed files
Showing 4 changed files
9 | 10 |
new file mode 100644 |
... | ... |
@@ -0,0 +1,42 @@ |
1 |
+(eval-when (:compile-toplevel :load-toplevel :execute) |
|
2 |
+ (ql:quickload '(:yason |
|
3 |
+ :alexandria |
|
4 |
+ :fwoar.lisputils))) |
|
5 |
+ |
|
6 |
+(defun group (break lis) |
|
7 |
+ (loop with result = (list) |
|
8 |
+ for (key . val) in lis |
|
9 |
+ when (equal key break) do (push () result) |
|
10 |
+ do (push (cons key val) (car result)) |
|
11 |
+ finally (return result))) |
|
12 |
+ |
|
13 |
+(defun group-by-first (lis) |
|
14 |
+ (group (caar lis) lis)) |
|
15 |
+ |
|
16 |
+(defun collect-pairs (reader) |
|
17 |
+ (loop for line = (funcall reader *standard-input* nil) |
|
18 |
+ while line |
|
19 |
+ for parts = (fwoar.string-utils:split #\space line :count 2) |
|
20 |
+ collect (fw.lu:vector-destructuring-bind (key val) parts |
|
21 |
+ (cons key val)))) |
|
22 |
+ |
|
23 |
+(let* ((lines '("TITLE foo" "URL bar" "TITLE baz" "URL qwer" nil)) |
|
24 |
+ (cur lines)) |
|
25 |
+ (defun reader (&rest r) |
|
26 |
+ (declare (ignore r)) |
|
27 |
+ (when (null cur) |
|
28 |
+ (setf cur lines)) |
|
29 |
+ (prog1 (car cur) |
|
30 |
+ (setf cur (cdr cur))))) |
|
31 |
+ |
|
32 |
+(defun main (&optional (reader 'read-line)) |
|
33 |
+ (yason:with-output (*standard-output* :indent t) |
|
34 |
+ (yason:with-array () |
|
35 |
+ (apply 'yason:encode-array-elements |
|
36 |
+ (mapcar 'alexandria:alist-hash-table |
|
37 |
+ (group-by-first |
|
38 |
+ (collect-pairs reader))))))) |
|
39 |
+ |
|
40 |
+ |
|
41 |
+(defun dump () |
|
42 |
+ (sb-ext:save-lisp-and-die "jsonifier" :toplevel 'main :executable t)) |
0 | 43 |
new file mode 100644 |
... | ... |
@@ -0,0 +1,32 @@ |
1 |
+(defpackage :type-providers |
|
2 |
+ (:use :cl ) |
|
3 |
+ (:export )) |
|
4 |
+(in-package :type-providers) |
|
5 |
+ |
|
6 |
+(defun load-keys (file) |
|
7 |
+ (fset:reduce 'fset:union |
|
8 |
+ (fset:image 'fset:domain |
|
9 |
+ (edn:parse (alexandria:read-file-into-string file) |
|
10 |
+ 'edn:fset-lossy)))) |
|
11 |
+ |
|
12 |
+(define-condition non-exhaustive-switch (style-warning) |
|
13 |
+ ((keys :initarg :keys :reader nes-keys) |
|
14 |
+ (cases :initarg :cases :reader nes-cases)) |
|
15 |
+ (:report (lambda (c s) |
|
16 |
+ (format s "Missing cases: ~s" |
|
17 |
+ (fset:set-difference (nes-keys c) |
|
18 |
+ (fset:convert 'fset:set (nes-cases c))))))) |
|
19 |
+ |
|
20 |
+(defmacro field-switch ((s file) &body body) |
|
21 |
+ (let* ((keys (load-keys file))) |
|
22 |
+ `(lambda (,s) |
|
23 |
+ (let (,@(fset:convert 'list |
|
24 |
+ (fset:image (lambda (x) |
|
25 |
+ `(,(intern (symbol-name x) |
|
26 |
+ *package*) |
|
27 |
+ (fset:lookup ,s ,x))) |
|
28 |
+ keys))) |
|
29 |
+ ,@body)))) |
|
30 |
+ |
|
31 |
+(field-switch (s "types.edn") |
|
32 |
+ ) |