#lang racket/base

;; requires racket >= 5.3 because of submodules

;; Lowlevel interface

(module low-level racket/base

  (require ffi/unsafe ffi/unsafe/define)

  (provide (all-defined-out))

  (define-ffi-definer defcmark (ffi-lib "libcmark"))

  (define _cmark_node_type
    (_enum '(none
             ;; Block
             document block-quote list item code-block
             html paragraph header hrule
             ;; Inline
             text softbreak linebreak code inline-html
             emph strong link image)))
  (define _cmark_list_type
    (_enum '(no_list bullet_list ordered_list)))
  (define _cmark_delim_type
    (_enum '(no_delim period_delim paren_delim)))
  (define _cmark_opts
    (_bitmask '(sourcepos = 1 hardbreaks = 2 normalize = 4 smart = 8)))

  (define-cpointer-type _node)

  (defcmark cmark_markdown_to_html
    (_fun [bs : _bytes] [_int = (bytes-length bs)] _cmark_opts
          -> [r : _bytes] -> (begin0 (bytes->string/utf-8 r) (free r))))

  (defcmark cmark_parse_document
    (_fun [bs : _bytes] [_int = (bytes-length bs)] _cmark_opts
          -> _node))

  (defcmark cmark_render_html
    (_fun _node _cmark_opts
          -> [r : _bytes] -> (begin0 (bytes->string/utf-8 r) (free r))))

  (defcmark cmark_node_new              (_fun _cmark_node_type -> _node))
  (defcmark cmark_node_free             (_fun _node -> _void))

  (defcmark cmark_node_next             (_fun _node -> _node/null))
  (defcmark cmark_node_previous         (_fun _node -> _node/null))
  (defcmark cmark_node_parent           (_fun _node -> _node/null))
  (defcmark cmark_node_first_child      (_fun _node -> _node/null))
  (defcmark cmark_node_last_child       (_fun _node -> _node/null))

  (defcmark cmark_node_get_user_data    (_fun _node -> _racket))
  (defcmark cmark_node_set_user_data    (_fun _node _racket -> _bool))
  (defcmark cmark_node_get_type         (_fun _node -> _cmark_node_type))
  (defcmark cmark_node_get_type_string  (_fun _node -> _bytes))
  (defcmark cmark_node_get_literal      (_fun _node -> _string))
  (defcmark cmark_node_set_literal      (_fun _node _string -> _bool))
  (defcmark cmark_node_get_header_level (_fun _node -> _int))
  (defcmark cmark_node_set_header_level (_fun _node _int -> _bool))
  (defcmark cmark_node_get_list_type    (_fun _node -> _cmark_list_type))
  (defcmark cmark_node_set_list_type    (_fun _node _cmark_list_type -> _bool))
  (defcmark cmark_node_get_list_delim   (_fun _node -> _cmark_delim_type))
  (defcmark cmark_node_set_list_delim   (_fun _node _cmark_delim_type -> _bool))
  (defcmark cmark_node_get_list_start   (_fun _node -> _int))
  (defcmark cmark_node_set_list_start   (_fun _node _int -> _bool))
  (defcmark cmark_node_get_list_tight   (_fun _node -> _bool))
  (defcmark cmark_node_set_list_tight   (_fun _node _bool -> _bool))
  (defcmark cmark_node_get_fence_info   (_fun _node -> _string))
  (defcmark cmark_node_set_fence_info   (_fun _node _string -> _bool))
  (defcmark cmark_node_get_url          (_fun _node -> _string))
  (defcmark cmark_node_set_url          (_fun _node _string -> _bool))
  (defcmark cmark_node_get_title        (_fun _node -> _string))
  (defcmark cmark_node_set_title        (_fun _node _string -> _bool))
  (defcmark cmark_node_get_start_line   (_fun _node -> _int))
  (defcmark cmark_node_get_start_column (_fun _node -> _int))
  (defcmark cmark_node_get_end_line     (_fun _node -> _int))
  (defcmark cmark_node_get_end_column   (_fun _node -> _int))

  (defcmark cmark_node_unlink           (_fun _node -> _void))
  (defcmark cmark_node_insert_before    (_fun _node _node -> _bool))
  (defcmark cmark_node_insert_after     (_fun _node _node -> _bool))
  (defcmark cmark_node_prepend_child    (_fun _node _node -> _bool))
  (defcmark cmark_node_append_child     (_fun _node _node -> _bool))
  (defcmark cmark_consolidate_text_nodes (_fun _node -> _void))

  )

;; Rackety interface

(module high-level racket/base

  (require (submod ".." low-level) ffi/unsafe)

  (provide cmark-markdown-to-html)
  (define (cmark-markdown-to-html str [options '(normalize smart)])
    (cmark_markdown_to_html (if (bytes? str) str (string->bytes/utf-8 str))
                            options))

  (require (for-syntax racket/base racket/syntax))
  (define-syntax (make-getter+setter stx)
    (syntax-case stx ()
      [(_ name) (with-syntax ([(getter setter)
                               (map (λ(op) (format-id #'name "cmark_node_~a_~a"
                                                      op #'name))
                                    '(get set))])
                  #'(cons getter setter))]))
  (define-syntax-rule (define-getters+setters name [type field ...] ...)
    (define name (list (list 'type (make-getter+setter field) ...) ...)))
  (define-getters+setters getters+setters
    [header header_level] [code-block fence_info]
    [link url title] [image url title]
    [list list_type list_delim list_start list_tight])

  (provide cmark->sexpr)
  (define (cmark->sexpr node)
    (define text (cmark_node_get_literal node))
    (define type (cmark_node_get_type node))
    (define children
      (let loop ([node (cmark_node_first_child node)])
        (if (not node) '()
            (cons (cmark->sexpr node) (loop (cmark_node_next node))))))
    (define info
      (cond [(assq type getters+setters)
             => (λ(gss) (map (λ(gs) ((car gs) node)) (cdr gss)))]
            [else '()]))
    (define (assert-no what-not b)
      (when b (error 'cmark->sexpr "unexpected ~a in ~s" what-not type)))
    (cond [(memq type '(document paragraph header block-quote list item
                        emph strong link image))
           (assert-no 'text text)
           (list type info children)]
          [(memq type '(text code code-block html inline-html
                        softbreak linebreak hrule))
           (assert-no 'children (pair? children))
           (list type info text)]
          [else (error 'cmark->sexpr "unknown type: ~s" type)]))

  (provide sexpr->cmark)
  (define (sexpr->cmark sexpr) ; assumes valid input, as generated by the above
    (define (loop sexpr)
      (define type (car sexpr))
      (define info (cadr sexpr))
      (define data (caddr sexpr))
      (define node (cmark_node_new type))
      (let ([gss (assq type getters+setters)])
        (when gss
          (unless (= (length (cdr gss)) (length info))
            (error 'sexpr->cmark "bad number of info values in ~s" sexpr))
          (for-each (λ(gs x) ((cdr gs) node x)) (cdr gss) info)))
      (cond [(string? data) (cmark_node_set_literal node data)]
            [(not data) (void)]
            [(list? data)
             (for ([child (in-list data)])
               (cmark_node_append_child node (sexpr->cmark child)))]
            [else (error 'sexpr->cmark "bad data in ~s" sexpr)])
      node)
    (define root (loop sexpr))
    (register-finalizer root cmark_node_free)
    root)

  ;; Registers a `cmark_node_free` finalizer
  (provide cmark-parse-document)
  (define (cmark-parse-document str [options '(normalize smart)])
    (define root (cmark_parse_document
                  (if (bytes? str) str (string->bytes/utf-8 str))
                  options))
    (register-finalizer root cmark_node_free)
    root)

  (provide cmark-render-html)
  (define (cmark-render-html root [options '(normalize smart)])
    (cmark_render_html root options)))

#; ;; sample use
(begin
  (require 'high-level racket/string)
  (cmark-render-html
   (cmark-parse-document
    (string-join '("foo"
                   "==="
                   ""
                   "> blah"
                   ">"
                   "> blah *blah* `bar()` blah:"
                   ">"
                   ">     function foo() {"
                   ">       bar();"
                   ">     }")
                 "\n"))))
