Skip to content

Commit

Permalink
General cleanup and bump to 0.12.1
Browse files Browse the repository at this point in the history
== lodox-html-writer ==
- Augment write-docs/2 docstring and add `[[doto/255]]`, which is
  useful for testing purposes, as well as informative
- Clean up format-docstring/4 using pattern matching
- Clean up format-wikilinks/3 a little and add libs to the list of
  searched "modules"

== lodox-util ==
- Add (recursive) docstrings to search-funcs/2{2,3}
  - Consider rewriting these
- Clean up search-funcs/3 using if/2 and lodox-p:null?/1

== README ==
- Fix the URI template table and a few typos
- Add "Docstring Formats" section
  - Include future plans commented out
  - Mention wikilinks and provide example

Also, update generated documentation, close #30 and close #3.
  • Loading branch information
yurrriq committed Jan 18, 2016
1 parent addc0f8 commit a5a4b7b
Show file tree
Hide file tree
Showing 10 changed files with 255 additions and 189 deletions.
40 changes: 33 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ Finally, add Lodox to your `plugins` list:
[% ...
{lodox, ".*",
{git, "git://github.com/quasiquoting/lodox.git",
{tag, "0.12.0"}}}]}.
{tag, "0.12.1"}}}]}.
```

The recommended place for the Lodox plugin entry is the global [rebar3](https://github.com/rebar/rebar3) config, `~/.config/rebar3/rebar.config`,
Expand Down Expand Up @@ -60,7 +60,7 @@ rebar3 do compile, lfe lodox

If all goes well, the output will look something like:

Generated lodox v0.12.0 docs in /path/to/lodox/doc
Generated lodox v0.12.1 docs in /path/to/lodox/doc

And, as promised, [generated documentation](http://quasiquoting.org/lodox/) will be in the `doc` subdirectory of
your project.
Expand Down Expand Up @@ -99,35 +99,61 @@ The URI is a template that may contain the following keys:
</colgroup>
<thead>
<tr>
<th scope="col" class="org-left">Template</th>
<th scope="col" class="org-left">Key</th>
<th scope="col" class="org-left">Description</th>
</tr>
</thead>

<tbody>
<tr>
<td class="org-left">`{filepath}`</td>
<td class="org-left">filepath</td>
<td class="org-left">the file path from the root of the repository</td>
</tr>


<tr>
<td class="org-left">`{line}`</td>
<td class="org-left">line</td>
<td class="org-left">the line number of the source file</td>
</tr>


<tr>
<td class="org-left">`{version}`</td>
<td class="org-left">version</td>
<td class="org-left">the version of the project</td>
</tr>
</tbody>
</table>

N.B. In order for `{version}` to work properly, you must add the corresponding
tag. For example, if you `.app` file contains `{vsn, "1.2.3"}` you must add the
tag. For example, if your `.app` file contains `{vsn, "1.2.3"}` you must add the
tag, `​"1.2.3"​`, to your repo.

## Docstring Formats

*[ Modified from [Codox documentation](https://github.com/weavejester/codox#docstring-formats). ]*

By default, docstrings are rendered by Lodox as Markdown via [pandoc](http://pandoc.org). If `pandoc`
is not available, Lodox will fall back to [erlmarkdown](https://github.com/erlware/erlmarkdown).

It is strongly recommended that you install [pandoc](http://pandoc.org), as it is much more robust.

In a future version, you will be able to override this behaviour by specifying
an explicit format for your docstrings.

Markdown docstrings also support wikilink-style relative links, for referencing
other definitions. Definitions in the current module will be matched first, and
then Lodox will try to find a best match out of all the definitions it's
documenting.

N.B. Module-less definitions in `.lfe` files in the `include` directory,
e.g. [lodox-macros](include/lodox-macros.lfe), will also be included in the search.

```lfe
(defun bar (x)
"See [[foo/2]] and [[baz:square/1]] for other examples."
...)
```

# License

Lodox is licensed under [the MIT License](http://yurrriq.mit-license.org).
Expand Down
2 changes: 1 addition & 1 deletion doc
94 changes: 50 additions & 44 deletions org/Lodox.org
Original file line number Diff line number Diff line change
Expand Up @@ -412,7 +412,10 @@ describing the docs that were generated.
(write-docs project #m()))

(defun write-docs (project opts)
"Take raw documentation info and turn it into formatted HTML."
"Take raw documentation info and turn it into formatted HTML.
Write to and return `output-path` in `opts`. Default: `\"doc\"`

N.B. [[write-docs/2]] makes great use of [[doto/255]] under the hood."
(let* ((`#(ok ,cwd) (file:get_cwd))
(`#m(output-path ,output-path app-dir ,app-dir)
(maps:merge `#m(output-path "doc" app-dir ,cwd) opts))
Expand Down Expand Up @@ -454,17 +457,15 @@ describing the docs that were generated.
(format-docstring project module func (maps:get 'format func 'markdown)))

(defun format-docstring
([project _ m 'plaintext]
(pre '(class "plaintext") (h (mref m 'doc))))
([project mod m 'markdown]
(case (mref m 'doc)
("" "")
(doc
(format-wikilinks
project (markdown->html (unicode:characters_to_list doc))
(if (is_map mod)
(maps:get 'name mod 'undefined)
(mref m 'name)))))))
([_project _mod (map 'doc "") _format] "")
([_project _mod `#m(doc ,doc) 'plaintext] (pre '(class "plaintext") (h doc)))
([project mod `#m(doc ,doc) 'markdown] (when (is_map mod))
(let ((name (maps:get 'name mod 'undefined))
(html (markdown->html (unicode:characters_to_list doc))))
(format-wikilinks project html name)))
([project mod `#m(name ,name doc ,doc) 'markdown]
(let ((html (markdown->html (unicode:characters_to_list doc))))
(format-wikilinks project html name))))

(defun markdown->html (markdown)
"Given a Markdown string, convert it to HTML.
Expand All @@ -480,27 +481,26 @@ Use [pandoc] if available, otherwise [erlmarkdown].
(os:cmd)))))

(defun format-wikilinks
([`#m(modules ,modules) html starting-mod]
([`#m(libs ,libs modules ,modules) html init]
(case (re:run html "\\[\\[([^\\[]+/\\d+)\\]\\]"
'[global #(capture all_but_first)])
('nomatch html)
(`#(match ,matches)
(-> (match-lambda
([`#(,start ,length)]
(let ((match (lists:sublist html (+ 1 start) length)))
(case (lodox-util:search-funcs modules match starting-mod)
('undefined
'false)
(mfa
(let ((`#(,mod [,_ . ,fname])
(lists:splitwith (lambda (c) (=/= c #\:)) mfa)))
`#(true #(,(re-escape (++ "[[" match "]]"))
,(link-to (func-uri mod fname)
(if (=:= (atom_to_list starting-mod) mod)
(h fname)
(h (++ mod ":" fname))))))))))))
(lists:filtermap (lists:flatten matches))
(->> (fold-replace html))))
('nomatch html))))
(let ((to-search (++ modules libs)))
(-> (match-lambda
([`#(,start ,length)]
(let* ((match (lists:sublist html (+ 1 start) length))
(mfa (lodox-util:search-funcs to-search match init)))
(if (=/= mfa 'undefined)
(let ((`#(,mod [,_ . ,fname])
(lists:splitwith (lambda (c) (=/= c #\:)) mfa)))
`#(true #(,(re-escape (++ "[[" match "]]"))
,(link-to (func-uri mod fname)
(if (=:= (atom_to_list init) mod)
(h fname)
(h (++ mod ":" fname)))))))))))
(lists:filtermap (lists:flatten matches))
(->> (fold-replace html))))))))

(defun index-by (k ms) (lists:foldl (lambda (m mm) (mset mm (mref m k) m)) (map) ms))

Expand Down Expand Up @@ -1328,23 +1328,29 @@ elements satisfying [[pattern?/1]] or a term that satisfies [[pattern?/1]]."
(export (search-funcs 2) (search-funcs 3)))

(defun search-funcs (modules partial-func)
"Find the best-matching `def{un,macro}`.

Given a list of modules and a partial `def{un,macro}` string, return the first
matching definition. If none is found, return `` 'undefined ``.

Equivalent to [[search-funcs/3]] with `` 'undefined `` as `starting-mod`."
(search-funcs modules partial-func 'undefined))

(defun search-funcs (modules partial-func starting-mod)
(let* ((suffix (if (lists:member #\/ partial-func)
partial-func
`(#\/ . ,partial-func)))
(matches (lists:filter
(lambda (func-name) (lists:suffix suffix func-name))
(exported-funcs modules))))
(case (lists:dropwhile
(lambda (func-name)
(=/= (atom_to_list starting-mod) (module func-name)))
matches)
(`(,func . ,_) func)
('() (case matches
(`(,func . ,_) func)
('() 'undefined))))))
"Like [[search-funcs/2]], but give precedence to matches in `starting-mod`."
(let* ((suffix (if (lists:member #\: partial-func)
partial-func
(cons #\: partial-func)))
(matches (lists:filter
(lambda (func-name) (lists:suffix suffix func-name))
(exported-funcs modules)))
(external (lists:dropwhile
(lambda (func-name)
(=/= (atom_to_list starting-mod) (module func-name)))
matches)))
(if (lodox-p:null? external)
(if (lodox-p:null? matches) 'undefined (car matches))
(car external))))
#+END_SRC
#+BEGIN_SRC lfe :exports none :padline no
#+END_SRC
Expand Down

0 comments on commit a5a4b7b

Please sign in to comment.