From 727995a409632d4c143ba4b6b088c7df40f074e7 Mon Sep 17 00:00:00 2001 From: Case Duckworth Date: Sat, 18 May 2024 21:15:54 -0500 Subject: Scheme bit! --- src/read.scm | 74 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 74 insertions(+) create mode 100644 src/read.scm (limited to 'src/read.scm') diff --git a/src/read.scm b/src/read.scm new file mode 100644 index 0000000..00ffad4 --- /dev/null +++ b/src/read.scm @@ -0,0 +1,74 @@ +(declare (module (jimmy read))) + +(import scheme (chicken base) + (jimmy util) + (only (chicken condition) handle-exceptions) + (only (chicken io) read-lines) + (only (chicken string) string-split)) + +(define-public line-types + ;; (sigil type inlines preproc) + '(("=>" link) + (">" quot) + ("#" hdr1) + ("##" hdr2) + ("###" hdr3) + ("*" list) + ("```" verb) + ;; extra! + (":" meta))) + +(define-public (parse inport) + (parse-lines (read-lines inport) '())) + +(define (line-type line) + (let ((it (assoc (car (string-split line)) line-types))) + (if it (cadr it) + 'para))) + +(define (parse-lines lines document) + (if (null? lines) (reverse document) + (let ((words (string-split (car lines)))) + (cond + ((null? words) + (parse-lines (cdr lines) document)) + ((equal? (car words) "```") + (parse-verbatim (cdr lines) document '())) + ((assoc (car words) line-types) + => (lambda (it) + (apply parse-block lines document '() (cdr it)))) + (else + (parse-block lines document '() 'para '(link) identity)))))) + +(define (parse-verbatim lines document verb) + (cond + ((null? lines) + (parse-lines lines (cons (cons 'verb (reverse verb)) document))) + ((equal? (car lines) "```") + (parse-lines (cdr lines) (cons (cons 'verb (reverse verb)) document))) + (else + (parse-verbatim (cdr lines) document (cons (car lines) verb))))) + +(define (parse-block lines document block type #!optional inlines preproc) + (let ((inlines (or inlines '())) + (preproc (or preproc (lambda (ln) (cdr (string-split ln)))))) + (cond + ((null? lines) + (parse-lines lines (cons (cons type (reverse block)) document))) + ((equal? (car lines) "") + (parse-lines (cdr lines) (cons (cons type (reverse block)) document))) + ((and (not (eq? type (line-type (car lines)))) + (not (memq (line-type (car lines)) inlines))) + (parse-lines lines (cons (cons type (reverse block)) document))) + ((memq (line-type (car lines)) inlines) + (let* ((ln (car lines)) + (ws (string-split ln)) + (lt (cdr (assoc (car ws) line-types)))) + (parse-block (cdr lines) document + (cons (cons (car lt) + ((or (ignore-errors (caddr lt)) cdr) ws)) + block) + type inlines preproc))) + (else + (parse-block (cdr lines) document (cons (preproc (car lines)) block) + type inlines preproc))))) -- cgit 1.4.1-21-gabe81